題意:
思路:
考慮dp,設定dp[i][j]表示到i為止,處於j(0:上升段,1:下降段)所需要的最小運算元,然後在分情況dp即可。
唯一的一點需要注意,下降段不可能由上升段轉移過來,因為我要得到的是上升段,把上升段轉為下降段顯然不優,這部分不需要轉移。
code:
#include <bits/stdc++.h>
#include<bits/extc++.h>
using namespace __gnu_pbds;
using namespace std;
using i64 = long long;
using u64 = unsigned long long;
using PII = pair<i64, i64>;
const int inf = 0x3f3f3f3f;
const i64 INF = 0x3f3f3f3f3f3f3f3f;
#define Z cout << "\n"
#define lb lower_bound
#define ub upper_bound
#define D(x) cerr << #x << ": " << (x) << "\n"
#define DV(v) cerr<<#v<<": ";for(int i=0;i<(v).size();i++)cerr<<((v)[i])<<",";cerr<<"\n"
#if 0
#define int i64
#endif
const int N = 2e5 + 5;
int dp[N][2];
signed main() {
ios::sync_with_stdio(false), cin.tie(nullptr), cout.tie(nullptr);
int t;
cin >> t;
while (t--) {
int n;
cin >> n;
vector<int>a(n + 5);
for (int i = 1; i <= n; i++)cin >> a[i];
for (int i = 1; i <= n; i++)dp[i][0] = dp[i][1] = inf;
dp[1][0] = dp[1][1] = 1;
for (int i = 2; i <= n; i++) {
if (a[i] < a[i - 1]) {
dp[i][0] = min(dp[i - 1][1], dp[i - 1][0]) + 1;
dp[i][1] = dp[i - 1][1];
// dp[i][1] = min(dp[i - 1][0] + 2, dp[i - 1][1]);
}
else if (a[i] == a[i - 1]) {
dp[i][0] = min(dp[i - 1][1], dp[i - 1][0]) + 1;
dp[i][1] = dp[i - 1][1] + 1;
// dp[i][1] = min(dp[i - 1][0] + 2, dp[i - 1][1] + 1);
}
else {
dp[i][0] = min(dp[i - 1][1] + 1, dp[i - 1][0]);
dp[i][1] = dp[i - 1][1] + 1;
//dp[i][1] = min(dp[i - 1][0] + 1, dp[i - 1][1] + 1);
}
}
cout << min(dp[n][0] - 1, dp[n][1]) << "\n";
}
return 0;
}