最终的序列一定是单调递减或者单调递增或者一个谷形
所以我们可以用单调栈从左到右一次单调栈维护每个元素作为谷底时左侧需要删除几个元素
然后从右往左进行单调栈,维护每个元素作为谷底的时候右侧需要删除几个元素
最终两侧的值相加就是这个元素作为谷底的代价
去最小值即可
代码如下:
cpp
#include <bits/stdc++.h>
using namespace std;
#define int long long
void solve() {
int n;
cin>>n;
vector<int>a(n+1,0);
for(int i=1;i<=n;i++){
cin>>a[i];
}
vector<int>stl,str,dl(n+1,0),dr(n+1,0);
stl.push_back(INT_MAX);
str.push_back(INT_MAX);
for(int i=1;i<=n;i++){
while(a[i]>stl.back()){
stl.pop_back();
}
stl.push_back(a[i]);
dl[i]=i+1-stl.size();
}
for(int i=n;i>=1;i--){
while(a[i]>str.back()){
str.pop_back();
}
str.push_back(a[i]);
dr[i]=n-i+2-str.size();
}
int ans=INT_MAX;
for(int i=1;i<=n;i++){
ans=min(ans,dl[i]+dr[i]);
}
cout<<ans<<'\n';
}
signed main() {
ios::sync_with_stdio(0);
cin.tie(0);
int t=1;
cin>>t;
while(t--)solve();
}