シーケンスの変位を最大要素と最小要素の差と定義します。与えられた整数のシーケンスについて、長さ の連続するすべてのサブシーケンスの最大変位を見つけますm
。
たとえば、シーケンスが [1, 5, 7, 0, 2, -4] で m = 3 の場合、
- [1, 5, 7] の変位は 6 です。
- [5, 7, 0] の変位は 7 です。
- [7, 0, 2] の変位は 7 です。
- [0, 2, -4] の変位は 6 です。
- したがって、最大変位は 7 です。
入力シーケンスの長さを n とすると、以下の私のソリューションは O(nlog(m)) 時間で実行されます。より良い方法はありますか?私が見逃している線形時間アルゴリズムがあるに違いないと感じています。この質問の目的のために、私が気にするのは漸近的な時間の複雑さだけです。
#include <vector>
#include <set>
#include <iostream>
int find_max_displacement(std::vector<int> seq, int m){
std::multiset<int> subseq;
// insert the m items of first subsequence into tree
for (int i = 0; i < m; i++){
subseq.insert( seq[i] );
}
int max_disp = *subseq.rbegin() - *subseq.begin(); // max minus min
for (int i = 0; i < seq.size() - m; i++){
subseq.erase(subseq.find(seq[i])); // kick oldest element out of subsequence
subseq.insert( seq[i+m] ); // insert new element into subsequence
int new_disp = *subseq.rbegin() - *subseq.begin();
if (new_disp > max_disp){
max_disp = new_disp;
}
}
return max_disp;
}
int main(){
std::vector<int> arr {1, 5, 7, 0, 2, -4};
int max_disp = find_max_displacement(arr, 3);
std::cout << max_disp << std::endl;
return 0;
}