Savitzky Golayフィルターを使用して、離散的にサンプリングされた1D信号の(サンプル間の)極大値を見つけるにはどうすればよいですか?


9

私は地震信号y(i)を持っています: ここに画像の説明を入力してください

ここで私は1つの最大値を見つけました:i = 152.54、y = 222.29手動で、それを赤でプロットしました。

すべての最大値を自動的に検索したい。

Savitzky Golay Filter(SGF)を使用して、信号とその導関数の両方の平滑化された推定値を見つけることができ、SGFの利点の1つは、他のフィルターよりも優れた最小値と最大値を維持できることです。これは私の使用に最適に聞こえます。

SGF係数を生成するMatlabスクリプトを見つけました。 これを使用して、導関数の4次のSGF係数を見つけました。小さなMatlabスクリプトをコーディングしました

  1. 微分係数の4次SGF係数で信号をたたみ込むことにより、信号の微分係数を求めます
  2. 導関数が符号を変更するサンプルのペア(i、i + 1)を見つける
  3. iとi + 1の間の線形補間によって導関数のゼロクロッシングを見つけます

脚本:

function [maxX,maxY] = findLocalMax(y)
% Kernel for 4th order Savitzky-Golay filter for finding derivative:
d4 = [0.0724 -0.1195 -0.1625 -0.1061 0 0.1061 0.1625 0.1195 -0.0724];

dy = conv(y,d4,'same'); % derivative

[m n] = size(dy);
maxX = [];
maxY = [];
for i = 1 : n - 1
  if dy(i) < 0 && dy(i+1) > 0 % max somewhere between i and i+1
    a = dy(i)/(dy(i) - dy(i+1)); % linear interpolation
    mx = i + a;
    maxX = [maxX mx];
    my = y(i)*(1-a) + y(i+1)*a; % linear interpolation
    maxY = [maxY my];
  end
end

私のスクリプトでは、関数が望ましい結果を出すために微分が負から正に変化するかどうかをテストする必要がありましたが、これは私を混乱させます。 最大の導関数は正から負に移行すべきではありませんか? 最大と最小を区別するより良い方法はありますか?

以下は、この関数を使用して信号の最大値を見つけた結果です。 ここに画像の説明を入力してください

結果は良さそうですが、いくつかの最大値が見つからないことに気づきました:i = 143.13、190.88、256.97。

これは、他の最大値に近づくためですか?

最も近い2つの最大値を制御するにはどうすればよいですか?

どんな答えも事前にありがとう!


フィルター出力をプロットできますか?
ジム・クレイ

回答:


5

この特定のタイプのフィルターについては詳しくありませんが、表示したプロットに基づいて、プロセスで検出されなかった最大値が、プロセスに固有の時間分解能に対抗していると思います。あらゆる種類の「スムージング」は、対象の信号の時間ローカルなスミアリングが存在することを意味します。そのため、近くに2つのピークがある場合、それらが1つに合体する可能性があります。より低い次数のフィルターでは、この動作が少なくなる可能性があります。おそらく、得られる平滑化の量が犠牲になります。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.