2015-09-16 6 views
10

मैं इस सीएसवी जैसे मूल्यों के साथ तिथियों को साजिश करने की कोशिश कर रहा हूं।क्या matplotlib के साथ टाइमलाइन प्लॉट करना संभव है?

Tue 2 Jun 16:55:51 CEST 2015,3 
Wed 3 Jun 14:51:49 CEST 2015,3 
Fri 5 Jun 10:31:59 CEST 2015,3 
Sat 6 Jun 20:47:31 CEST 2015,3 
Sun 7 Jun 13:58:23 CEST 2015,3 
Mon 8 Jun 14:56:49 CEST 2015,2 
Tue 9 Jun 23:39:11 CEST 2015,1 
Sat 13 Jun 16:55:26 CEST 2015,2 
Sun 14 Jun 15:52:34 CEST 2015,3 
Sun 14 Jun 16:17:24 CEST 2015,3 
Mon 15 Jun 13:23:18 CEST 2015,1 
... 

इम पहले ही जवाब यहाँ के समान कुछ कर रही: Matplotlib timelines

लेकिन डेटा दृश्य उस तरह को देखकर की अच्छी जानकारी प्राप्त करने के लिए वास्तव में कठिन है। तो मुझे लगता है कि im अवधि प्लॉट करने के लिए कोशिश कर रहा है और मैं एक महत्वपूर्ण y- अक्ष की आवश्यकता नहीं है कि, केवल x अक्ष तिथियों के साथ और मूल्यों रंग हो सकता है

कुछ इस तरह:

---===-===---**** 
DDDDDDDDDDDDDDDDD 

-=* = type of values (using colors for example, but any representation would do) 
D = dates 

मैं न इसी तरह कुछ भी नहीं देख matplotlib उदाहरण

colorbars लगता है कि वे काम कर सकते हैं पर देख रहे हैं लगता है, लेकिन काफी नहीं है, क्योंकि अक्ष तारीख अंतराल http://matplotlib.org/examples/api/colorbar_only.html

उत्तर

12

जैसे होने की जरूरत है, यह गुणात्मक डेटा ताकि आप है एक स्थानिक वाई अक्ष का उपयोग नहीं करना चाहते हैं?

enter image description here

से:

import matplotlib.pyplot as plt 
import pandas as pd 

dates = ["Tue 2 Jun 16:55:51 CEST 2015", 
"Wed 3 Jun 14:51:49 CEST 2015", 
"Fri 5 Jun 10:31:59 CEST 2015", 
"Sat 6 Jun 20:47:31 CEST 2015", 
"Sun 7 Jun 13:58:23 CEST 2015", 
"Mon 8 Jun 14:56:49 CEST 2015", 
"Tue 9 Jun 23:39:11 CEST 2015", 
"Sat 13 Jun 16:55:26 CEST 2015", 
"Sun 14 Jun 15:52:34 CEST 2015", 
"Sun 14 Jun 16:17:24 CEST 2015", 
"Mon 15 Jun 13:23:18 CEST 2015"] 

values = [3,3,3,3,3,2,1,2,3,3,1] 

X = pd.to_datetime(dates) 
fig, ax = plt.subplots(figsize=(6,1)) 
ax.scatter(X, [1]*len(X), c=values, 
      marker='s', s=100) 
fig.autofmt_xdate() 

# everything after this is turning off stuff that's plotted by default 

ax.yaxis.set_visible(False) 
ax.spines['right'].set_visible(False) 
ax.spines['left'].set_visible(False) 
ax.spines['top'].set_visible(False) 
ax.xaxis.set_ticks_position('bottom') 

ax.get_yaxis().set_ticklabels([]) 
day = pd.to_timedelta("1", unit='D') 
plt.xlim(X[0] - day, X[-1] + day) 
plt.show() 
+0

मैंने एक उत्तर जोड़ा जिसके साथ मैं ढूंढ रहा था ... मैंने अभी भी आपका स्वीकार किया है क्योंकि यह एक बहुत साफ उदाहरण है और मुझे अक्ष में तारीखों के लिए ऐसा कुछ नहीं मिला। यह अच्छा होगा अगर इसे सबकुछ खींचने के बजाए लाइब्रेरी का उपयोग करके बेक किया जा सके :) –

+0

यदि पुस्तकालयों में सबकुछ कुछ भी हो सकता है तो वे भ्रमित रूप से विशाल होंगे। यदि आप इस तरह की साजिश का एक से अधिक बार उपयोग कर रहे हैं, तो एक फ़ंक्शन बनाएं - पास 'स्कैटर' (या आपके पीआईएल संस्करण में 'ड्रा' फ़ंक्शंस के माध्यम से बहस करता है। – cphlewis

11

संपादित करें: जब से मैं वहाँ किसी भी समाधान तरह फ्लॉप, मैं अपने ही जनहित याचिका के साथ बेक:

Resulting visualisation:

यह परिणाम है

यह कोड है:

#!/usr/bin/env python3 
from datetime import datetime, timedelta 
from dateutil.relativedelta import relativedelta 
import csv 
import matplotlib.pyplot as plt 
import matplotlib.dates as pltdate 
from PIL import Image, ImageDraw 

lines = [] 
with open('date') as f: 
    lines = list(csv.reader(f)) 
    frmt = '%a %d %b %X %Z %Y' 
    dates = [datetime.strptime(line[0], frmt) for line in lines] 
    data = [line[1] for line in lines] 

#datesnum = pltdate.date2num(dates) 
#fig, ax = plt.subplots() 
#ax.plot_date(datesnum, data, 'o') 

#plt.show() 

#generate image 
WIDTH, HEIGHT = 4000, 400 
BORDER = 70 
W = WIDTH - (2 * BORDER) 
H = HEIGHT - (2 * BORDER) 


colors = { '0': "lime", '1' : (255,200,200), '2' : (255,100,100), '3' : (255,0,0) } 

image = Image.new("RGB", (WIDTH, HEIGHT), "white") 
min_date = dates[0] 
max_date = datetime.now() 
#print(min_date) 
#print(max_date) 
interval = max_date - min_date 
#print(interval.days) 

#draw frame 
draw = ImageDraw.Draw(image) 
draw.rectangle((BORDER, BORDER, WIDTH-BORDER, HEIGHT-BORDER), fill=(128,128,128), outline=(0,0,0)) 

#draw circles 
circle_w = 10 
range_secs = W/interval.total_seconds() 
#print(range_secs) 
for i in range(len(dates)): 
    wat = dates[i] - min_date 
    offset_sec = (dates[i] - min_date).total_seconds() 
    offset = range_secs * offset_sec 
    x = BORDER + offset 
    draw.ellipse((x, BORDER + 50, x + circle_w, BORDER + 50 + circle_w), outline=colors[data[i]]) 
    #draw.text((x, BORDER + 75), str(i), fill=colors[data[i]]) 

#draw rectangles 
range_days = W/(interval.days + 1) 
#print("range_days",range_days) 
current_date = min_date 
date_month = min_date + relativedelta(months=1) 
current_index = 0 
for i in range(interval.days + 1): 
    max_color = '0' 
    while dates[current_index].date() == current_date.date(): 
     if int(data[current_index]) > int(max_color): 
      max_color = data[current_index] 
     current_index += 1 
     if current_index > len(dates) - 1: 
      current_index = 0 
    x = BORDER + range_days * i 
    draw.rectangle((x, BORDER + 100, x+range_days, BORDER + 100 + 50), fill=colors[max_color], outline=(0,0,0)) 
    if current_date == date_month: 
     draw.line((x, BORDER + 100 +50, x, H + BORDER + 20), fill="black") 
     draw.text((x, H + BORDER + 20), str(date_month.date()), fill="black") 
     date_month = date_month + relativedelta(months=1) 
    #draw.text((x, BORDER + 175), str(i), fill=colors[max_color]) 
    current_date = current_date + timedelta(days=1) 

#draw start and end dates 
draw.text((BORDER, H + BORDER + 20), str(min_date.date()), fill="black") 
draw.text((BORDER + W, H + BORDER + 20), str(max_date.date()), fill="black") 

image.save("date.png") 
संबंधित मुद्दे