CF1860C Game on Permutation

Question 问题 CF1860C Game on Permutation

有一个有 \(n\) 个元素的全排列,Alice 先放一个筹码在第 \(i\) 个元素上,在每次下一步中,当前玩家必须将筹码移动到同时向左且严格小于当前元素的任何元素。若当前玩家无法移动,则该玩家胜利

称其中第 \(i\) 个元素是幸运的仅当 Alice 把筹码放置在第 \(i\) 个元素的时候,无论 Bob 怎么移动 Alice 都可以获胜。

Analysis 分析

研究样例可发现若一旦放置在第 \(i\) 个元素的时候就无法动了,那么此时肯定是 Bob 获胜。那我们需要往后找到直到这个元素可以动。那么这就是第一个幸运元素。

后面的元素何时会是幸运的呢?观察到如果 Bob 可以从第 \(i\) 个元素移动到前面任意一个幸运元素,则 Bob 获胜。所以我们要满足第 \(i\) 个元素的大小要小于其前面所有幸运元素。

只需要记一个数组 \(mn_i\) 代表第 \(i\) 个元素前最小的幸运元素即可。

Code 代码

const int N=3e5+8;
int T,n,p[N],mn[N];
bool f[N];
int main(){
    read(T);
    while(T--){
        read(n);int Min=inf;mn[0]=inf;ll cnt=0;
        for(rint i=1;i<=n;i++) f[i]=0;
        for(rint i=1;i<=n;i++){
            read(p[i]);
            if(p[i]<Min) f[i]=1,Min=p[i];//f[i] 代表第 i 个点 0:可以移动 1:不可移动
        }
        for(rint i=1;i<=n;i++){
            if(!f[i]){
                if(p[i]<mn[i-1]) mn[i]=min(mn[i-1],p[i]),cnt++;
                else mn[i]=mn[i-1];
            } 
            else mn[i]=mn[i-1];
        }
        printf("%lld\n",cnt);
    }
    return 0;
}
posted @ 2024-05-29 21:56  Mr_Azz  阅读(1)  评论(0编辑  收藏  举报