グラフにプロットされるいくつかの9000ポイントがあります。
[ フル解像度 ]
実際、プロットは思ったほど滑らかではありません。 グラフを必要な程度に滑らかにする方法はありますか?
または、あまりにもでこぼこしている部分を選択的に平滑化できるように、何らかのしきい値を設定しますか?
確かではありませんが、 fast-fourier-transform 助けてもいいですか?
簡単な(アドホックな)方法は、隣接する各ポイントで加重平均(alpha
で調整可能)を取るだけです。
data(2:n-1) = alpha*data(2:n-1) + (1-alpha)*0.5*(data(1:n-2)+data(3:n))
またはそのバリエーション。はい。より洗練するには、まずデータをフーリエ変換してから、高周波をカットします。何かのようなもの:
f = fft(data)
f(n/2+1-20:n/2+20) = zeros(40,1)
smoothed = real(ifft(f))
これにより、最も高い20の周波数がカットされます。それらを対称的に切り取るように注意してください。そうしないと、逆変換はもはや実在しません。適切なレベルの平滑化のために、カットオフ周波数を慎重に選択する必要があります。これは非常に単純な種類のフィルタリング(周波数領域でのボックスフィルタリング)であるため、歪みが許容できない場合は、高次の周波数を緩やかに減衰してみてください。
Curve Fitting Toolboxがある場合は、 smooth
関数を使用できます。デフォルトの方法は、サイズ5の移動平均です(方法は変更できます)。例:
% some noisy signal
Fs = 200; f = 5;
t = 0:1/Fs:1-1/Fs;
y = sin(2*pi*f*t) + 0.6*randn(size(t));
subplot(411)
plot(y), title('Noisy signal')
% smoothed signal
subplot(412)
plot( smooth(y, 5, 'moving') ), title('smooth')
ylim([-2 2])
そうでない場合は、コアMATLABの filter
関数を使用して独自のウィンドウ関数を使用できます。
% equivalent to a moving average window
wndwSize = 5;
h = ones(1,wndwSize)/wndwSize;
subplot(413)
plot( filter(h, 1, y) ), title('filter + square window')
% Guassian
h = pdf('Normal',-floor(wndwSize/2):floor(wndwSize/2),0,1);
subplot(414)
plot( filter(h, 1, y) ), title('filter + Guassian window')
FFTは悪い考えではありませんが、おそらくここではやり過ぎです。移動平均または移動平均の結果は一般に悪いため、宿題の遅れ(およびホワイトノイズ)以外は避けてください。
Savitzky-Golayフィルタリングを使用します(Matlab sgolayfilt(...)で)。これにより、探しているものに最適な結果が得られます-曲線の形状を維持しながら、局所的なスムージングを行います。
-ポール
外れ値に対してロバストではないため、モバイル平均の使用を避ける必要がある場合があります。これらの場合、モバイル中央値が望ましいです。
最初に、5または10などの複数のポイントで移動平均を表示しようとします。この方法では、値の単一の不一致はグラフにほとんど影響を与えません。もちろん、グラフの正確性に依存します。