0

これは、山と谷の位置を特定することについて私が持っていた前の質問に対する更新です。前の質問はこれでした:

MATLABの山と谷(ただし、対応する山と谷の定義があります)

今回は提案された答えを出しましたが、最終的なアルゴリズムにはまだ何か問題があると思います。コードで何が間違っていたのか教えていただけますか?ありがとう。

function [vectpeak, vecttrough]=peaktroughmodified(x,cutoff)

% This function is a modified version of the algorithm used to identify
% peaks and troughs in a series of prices. This will be used to identify
% the head and shoulders algorithm. The function gives you two vectors:
% PEAKS - an indicator vector that identifies the peaks in the function,
% and TROUGHS - an indicator vector that identifies the troughs of the
% function. The input is the vector of exchange rate series, and the cutoff
% used for refining possible peaks and troughs.

% Finding all possible peaks and troughs of our vector.
[posspeak,possploc]=findpeaks(x);
[posstrough,posstloc]=findpeaks(-x);
posspeak=posspeak';
posstrough=posstrough';

% Initialize vector of peaks and troughs.
numobs=length(x);
prelimpeaks=zeros(numobs,1); 
prelimtroughs=zeros(numobs,1);
numpeaks=numel(possploc);
numtroughs=numel(posstloc);

% Indicator for possible peaks and troughs.
for i=1:numobs
    for j=1:numpeaks
        if i==possploc(j);
            prelimpeaks(i)=1;
        end
    end
end

for i=1:numobs
    for j=1:numtroughs
       if i==posstloc(j);
            prelimtroughs(i)=1;
       end
    end
end

% Vector that gives location.
location=1:1:numobs;
location=location';

% From the list of possible peaks and troughs, find the peaks and troughs
% that fit Chang and Osler [1999] definition.
% "A peak is a local minimum at least x percent higher than the preceding
% trough, and a trough is a local minimum at least x percent lower than the
% preceding peak." [Chang and Osler, p.640]

% cutoffs
peakcutoff=1.0+cutoff; % cutoff for peaks
troughcutoff=1.0-cutoff; % cutoff for troughs


% First peak and first trough are initialized as previous peaks/troughs.

prevpeakloc=possploc(1);
prevtroughloc=posstloc(1);

% Initialize vectors of final peaks and troughs.
vectpeak=zeros(numobs,1);
vecttrough=zeros(numobs,1);

% We first check whether we start looking for peaks and troughs.
for i=1:numobs
    if prelimpeaks(i)==1;
       if i>prevtroughloc;
           ratio=x(i)/x(prevtroughloc);
           if ratio>peakcutoff;
               vectpeak(i)=1;
               prevpeakloc=location(i);
           else vectpeak(i)=0;
           end
       end
    elseif prelimtroughs(i)==1;
        if i>prevpeakloc;
            ratio=x(i)/x(prevpeakloc);
            if ratio<troughcutoff;
                vecttrough(i)=1;
                prevtroughloc=location(i);
            else vecttrough(i)=0;
            end
        end
    else
        vectpeak(i)=0;
        vecttrough(i)=0;
    end
end        
end
4

2 に答える 2

0

私はそれを実行しました、そしてあなたがこの変更をするならばそれはうまくいくようです:

peakcutoff= 1/cutoff; % cutoff for peaks
troughcutoff= cutoff; % cutoff for troughs

カットオフ0.1(ピークはトラフの10倍でなければなりません)で次のコードを使用してテストしましたが、妥当なように見えます

x = randn(1,100).^2;
[vectpeak,vecttrough] = peaktroughmodified(x,0.1);
peaks = find(vectpeak);
troughs = find(vecttrough);
plot(1:100,x,peaks,x(peaks),'o',troughs,x(troughs),'o')

matlabでのベクトル化についてよく読んでおくことを強くお勧めします。プログラムには多くの無駄な行があり、読みにくくなり、大きなデータセットでは非常に遅くなります。たとえば、prelimpeaksとprelimtroughsは、ループなしで、それぞれ1行で完全に定義できます。

prelimpeaks(possploc) = 1;
prelimtroughs(posstloc) = 1;
于 2012-09-19T19:23:50.263 に答える
0

上記のパーセンテージしきい値手法よりも、山と谷を見つけるための優れた手法があると思います。最小二乗適合放物線をデータセットに適合させます。これを行うための手法は、1946年のFrankPetersの論文「ParabolicCorrelation、NewDescrptiveStatistic」にあります。Petersが定義しているように、フィットした放物線には曲率の指標がある可能性があります。放物線の曲率指数の絶対値を最小化するポイントをテストして、山と谷を見つけます。これらのポイントが見つかったら、ポイントを除外したときに曲率のインデックスがどのように変化するかを考慮して、どのポイントがピークでどれがトラフであるかをテストします。これは、元の放物線の曲率が正か負かによって異なります。除去によって絶対値の最小曲率が達成される連続するポイントが気になる場合は、識別されたポイントが互いに離れている必要がある最小距離を設定して制約します。もう1つの制約は、識別されたポイントの数である必要があります。この制約がないと、このアルゴリズムは2つのポイントを除くすべてのポイント、つまり曲率のない直線を削除します。隣接するポイント間に急激な変化があり、両方を極端なポイントに含める必要がある場合があります。おそらく、最小距離の制約をオーバーライドする連続するポイントのパーセンテージしきい値テストが役立つでしょう。別の解決策は、級数の高速フーリエ変換を計算し、より低いスペクトルを最小化する点を削除することです。FFT関数は、最小二乗適合放物線を見つけるコードよりも簡単に利用できます。Peterのアプローチよりも管理が容易な、最小二乗適合放物線を決定するための行列操作手法があります。私はそれがどこかでウェブ上で文書化されているのを見ましたが、リンクを失いました。行列ベクトル表記を使用して最小二乗適合放物線に到達できる人からのアドバイスをいただければ幸いです。

于 2013-06-08T09:00:32.300 に答える