2014-03-04 148 views
2

我發現了幾個類似於我的問題,但答案在我的情況下不起作用... 我認爲,在我的情況下,它是不同的,我需要一些幫助弄清楚它是什麼。用matplotlib繪圖函數繪製圖表需要時間分鐘

我的腳本爲x和y讀取兩個50000值的文件,並用matplotlib繪圖函數繪製這些值。

我插入了一些打印語句來弄清楚爲什麼它需要更多的一分鐘或有時更長的時間...所以最後的「完成!」 (之前的plt.show())之後讓我們說2秒,但然後所有東西... ...斯普利特

有時我得到一分鐘的圖片,然後有時候,同樣的事情,需要5分鐘,或者我殺了處理。

任何人都可以幫忙嗎?我從2012年開始在Mac上工作...

colors = cm.rainbow(np.linspace(0, 1, len(data_dict.keys()))) 

fig, ax = plt.subplots(dpi=150) 
for key,c in zip(data_dict.keys(),colors): 
    ax.plot(x, 
      data_dict[key], 
      label=key, 
      color=c, 
      alpha=.5) 
    print("%s DONE!" % (key)) 

ax.axhline(1,color='red',linestyle='--') 
ax.grid(True) 
ax.set_xlabel("Zeit in ns") 
ax.set_ylabel("Distanz in nm") 
legend = ax.legend() 
print("DONE!") 
plt.show() 
+0

什麼' data_dict'看起來像? (你在你的問題中提到過'y',但是你的代碼中沒有'y')這個'for-loop'調用'ax.plot'的次數是多少?在一臺典型的機器上,如果你調用'ax.plot'幾千次,你將無法獲得良好的性能...... – unutbu

+0

在這種情況下,它被稱爲2倍... x = [2.0,4.0,6.0 ,. ..]; data_dict = {'filename':[2305.0,3456.0,...], 'filename':[2305.0,3456.0,...]} – drmariod

+0

由於您在plt.show()之前看到最後的'完成'並延遲似乎發生在那裏,請嘗試fig.savefig('output.jpg')看看需要多長時間來實際創建圖像,看看它是否可以在不同的顯示方法,如subprocess.Popen( 'firefox','-new-tab','output.jpg')我不得不這樣做,因爲我需要用非阻塞方法調出圖像,以便繼續進一步處理。 – sabbahillel

回答

1

典型的顯示器顯示大約100dpis。你正在繪製50K點。如果每個點並排並列,那麼您仍然需要50000/100.0 = 500英寸來單獨顯示所有點。通常一個圖形在點之間會有一點空間,這會使所需英寸的數量更大。

要在屏幕上顯示圖像,matplotlib正在將圖像壓縮到可能爲800 x 600像素的窗口。因此50K x值僅以800像素顯示。

換句話說,你正在使matplotlib努力繪製很多點,在最終的形象中得到短暫的sh points。

顯然,圖像應該以人類可以理解的方式總結數據。由於我們可能無法將自己的想法包裝在50K以內的可區分點上,因此您可能應該縮減採樣數據。一種粗暴的方式是採取每第100個點:

x = x[::100] 

或者,你可能需要每100點的平均值:

x = x.reshape(-1, 100).mean(axis=1) 

import matplotlib.pyplot as plt 
import numpy as np 
np.random.seed(1) 
N = 49999 

def chunks(seq, n): 
    # http://stackoverflow.com/a/312464/190597 (Ned Batchelder) 
    """ Yield successive n-sized chunks from seq.""" 
    for i in xrange(0, len(seq), n): 
     yield seq[i:i + n] 

def downsample(seq, n): 
    return [sum(chunk)/len(chunk) for chunk in chunks(seq, n)] 

x = range(N) 
x = downsample(x, 100) 
data_dict = {'A' : np.random.random(N), 'B' : np.random.random(N)} 
colors = plt.cm.rainbow(np.linspace(0, 1, len(data_dict.keys()))) 

fig, ax = plt.subplots(dpi=150) 
for key,c in zip(data_dict.keys(),colors): 
    y = downsample(data_dict[key], 100) 
    ax.plot(x, 
      y, 
      label=key, 
      color=c, 
      alpha=.5) 
    print("%s DONE!" % (key)) 

ax.axhline(1,color='red',linestyle='--') 
ax.grid(True) 
ax.set_xlabel("Zeit in ns") 
ax.set_ylabel("Distanz in nm") 
legend = ax.legend() 
print("DONE!") 
# plt.show() 
plt.savefig('/tmp/test.png') 

enter image description here

+0

'x = x [:: 100]'做了詭計,謝謝!我嘗試按照您的建議進行平均,但可以將我的列表保存到此np對象中,您有建議嗎?我的x和ys只是帶有花車的列表......提前感謝! – drmariod

+0

順便說一下,你是對的,事實並非如此,我的顯示器可以解決這個問題,但這條線在變化很大的區域變得更大膽......我想我需要所有的觀點......沒有想過,也許5000就足夠了,但它看起來還是很棒的...... – drmariod

+0

如果'x'是一個列表,你可以用'x = np.array(x)'將它轉換爲一個NumPy數組。然後你可以使用'x = x.reshape(-1,100).mean(axis = 1)'來取每100點的平均值。 – unutbu