#問題点
現在、Pythonでmatファイルを読み込み、FFT解析を行いウォーターフォール線図の作成にトライしているのですが、FFTの処理時にメモリエラーになっているらしく、その対処法が知りたいです。
#コード
初めのコードがメインのコードになります。
下部が別のコードからインポートしたanarysissunction.py及びmakegraph.pyになります。
Python
1import numpy as np 2import scipy.io 3import matplotlib.pyplot as plt 4import makegraph as mg 5import analysisfunction as af 6from scipy import signal 7from scipy import fftpack 8Fs=8192 9N=1024 10overlap=50 11#flattop_window = signal.flattop(N) # フラットトップ窓 12hanning_window = np.hanning(N) # ハン窓 13#rec_window=signal.boxcar(N)#レクタンギュラ窓 14matdata = scipy.io.loadmat('SweepSignalFs8192.mat') 15wavedata=matdata['Data'] 16mg.one_graph('SweepSiganl',30,10,np.arange(0,77,1/8192),'Time[s]',wavedata[0:630784],'Real[m/s^2]',30,40,'SweepSignal_output') 17fmax,Line,dt,df,t,freq=af.FFTparameter(Fs,N) 18F_ave,N_ave=af.ov_FFT(wavedata,Fs,N,overlap,hanning_window)
Python
1#analysisfunction.py 2def FFTparameter(Fs,N): 3 fmax=int(Fs/2.56)#最大周波数 4 Line=int(N/2.56)#ライン数 5 dt=1/Fs#サンプリング間隔 6 df=fmax/Line 7 t=np.arange(0,N*dt,dt)#時間軸 8 freq=np.arange(0,Line*df,df)#周波数軸 9 return fmax,Line,dt,df,t,freq 10def ov_FFT(data,samplerate,Fs,overlap,window): 11 Ts = len(data) / samplerate 12 Fc = Fs / samplerate 13 x_ol = Fs * (1 - (overlap/100)) 14 N_ave = int((Ts - (Fc * (overlap/100))) / (Fc * (1-(overlap/100)))) 15 array = [] 16 for i in range(N_ave): 17 ps = int(x_ol * i) 18 array.append(data[ps:ps+Fs:1]) 19 array_window=array*window 20 F = fftpack.fft(array_window) 21 Famp=np.abs(F) 22 F_total=np.sum(Famp,axis=0) 23 F_average=F_total / Fs*2 24 F_average=F_average/N_ave 25 acf=1/(sum(window)/Fs) 26 F_average=acf*F_average 27 return F_average, N_ave
Python
1#makegraph.py 2def one_graph(title,width,height,x,xlabel,y,ylabel,labelfont,fz,savetitle): 3 fig = plt.figure(figsize=(width, height)) 4 fig.suptitle(title,fontsize=fz) 5 ax=fig.add_subplot(111) 6 plt.plot(x,y) 7 plt.xlabel(xlabel,fontsize=labelfont) 8 plt.xticks(fontsize=labelfont) 9 plt.ylabel(ylabel,fontsize=labelfont) 10 plt.yticks(np.arange(-0.4,0.6,0.2),fontsize=labelfont) 11 plt.savefig(savetitle) 12 return 0
#入力ファイルについて
今回用いたファイルはSweepSignalFs8192.matになります。このファイルには以下のデータが格納されています。
ここで、Dataは(630784,1)の配列なので、一旦wavedataに置き換えてから処理しています。
#matfile内のData(一部) 0.00668657 0.0122638 0.0117161 0.0131935 0.0134903 0.0143503 0.0146439 0.015117 0.015357 0.0156636 ...
#現状のエラーについて
以下のようなエラーが発生しています。
Python
1unfile('Documents/Python Scripts/waterfalll線図/SweepSignal_test.py') 2Reloaded modules: makegraph, analysisfunction 3Traceback (most recent call last): 4 5 File "Documents\Python Scripts\waterfalll線図\SweepSignal_test.py", line 24, in <module> 6 F_ave,N_ave=af.ov_FFT(wavedata,Fs,N,overlap,hanning_window) 7 8 File "Documents\Python Scripts\waterfalll線図\analysisfunction.py", line 82, in ov_FFT 9 F = fftpack.fft(array_window) 10 11 File "Documents\Anaconda3\lib\site-packages\scipy\fftpack\basic.py", line 87, in fft 12 return _pocketfft.fft(x, n, axis, None, overwrite_x) 13 14 File "Documents\Anaconda3\lib\site-packages\scipy\fft\_pocketfft\basic.py", line 31, in c2c 15 return pfft.c2c(tmp, (axis,), forward, norm, out, workers) 16 17MemoryError: Unable to allocate 2.38 GiB for an array with shape (38, 2048, 2048) and data type complex128
#試したこと
サンプリング数Nを様々な数に変更してみましたが、エラー分の2.38 GiBの所が変わるだけで改善できませんでした。デバッグやタスクマネージャーを使って確認すると、FFT演算で確かにメモリを大幅に消費していることが明白なので、この部分のメモリ消費を改善していきたいと考えています。
その他必要なデータがございましたら可能な限り提供しますので、誰かわかる方がいらっしゃいましたらご協力宜しくお願い致します。
