题解 CF1760D Challenging Valleys

大家好,我是 CQ-C2024 蒟蒻 CJH。

题意

给定数组 $a_0,\dots,a_{n-1}$,请你找出一段 $l \sim r$ 的序列满足以下条件:

  1. $0 \le l \le r \le n-1$。

  2. $a_l=a_{l+1}=a_{l+2}=\dots=a_{r}$。

  3. $l=0$ 或 $a_{l-1} > a_{l}$。

  4. $r=n-1$ 或 $a_r<a_{r+1}$。

如果恰好只有一段符合以上条件的序列则输出 YES,否则输出 NO

分析思路

这里我们枚举在 $0 \sim n-1$ 中枚举左端点 $l$,再从 $l \sim n-1$ 中找到最大的右端点 $r$ 满足 $a_r=a_l$。

再判断是否满足条件 3 和条件 4 即可。

代码

//the code is from chenjh
#include<bits/stdc++.h>
using namespace std;
int a[200002];
void solve(){
    int n;scanf("%d",&n);
    for(int i=0;i<n;i++) scanf("%d",&a[i]);
    //注意数组是从第 0 个开始输入。
    bool fl=0;//判断是否有解。
    for(int i=0;i<n;){//枚举左端点。
        int j;
        for(j=i;j<n && a[j]==a[i];j++);//右端点不断向右扩展。
        int l=i,r=j-1;//因为此时 j>=n 或 a[j]!=a[i],所以右端点为 j-1。
        if((l==0||a[l-1]>a[l]) && (r==n-1||a[r]<a[r+1])){//判断是否满足条件。
            if(fl){puts("NO");return;}//已经有一个解,不满足恰好只有一个解。
            else fl=1;//标记为有解
        }
        i=j;
    }
    puts(fl?"YES":"NO");//有解输出 "YES",无解输出 "NO"。
}
int main(){
    int t;scanf("%d",&t);
    while(t--) solve();
    return 0;
}

谢谢大家!

posted @ 2022-11-23 14:55  Chen_Jinhui  阅读(19)  评论(0)    收藏  举报  来源