zoukankan      html  css  js  c++  java
  • AGC044C Strange Dance

    Description

    There are $3^N$ people dancing in circle. We denote with $0,1,cdots ,3^N-1$ the positions in the circle, starting from an arbitrary position and going around clockwise. Initially each position in the circle is occupied by one person.

    The people are going to dance on two kinds of songs: salsa and rumba.

    • When a salsa is played, the person in position $i$ goes to position $j$, where $j$ is the number obtained replacing all digits $1$ with $2$ and all digits $2$ with $1$ when reading $i$ in base $3$ (e.g., the person in position $46$ goes to position $65$).
    • When a rumba is played, the person in position $i$ moves to position $i+1$ (with the identification $3N=0$).

    You are given a string $T=T_1T_2 cdots T_{|T|}$ such that $T_i=S$ if the ii-th song is a salsa and $T_i=R$ if it is a rumba. After all the songs have been played, the person that initially was in position $i$ is in position $P_i$. Compute the array $P_0,P_1,dots, P_{3^N-1}$

    Solution

    维护一个Trie,每个点延伸三条边表示下一个数位上是0/1/2,表示时从低位到高位

    1/2翻转的操作可以打标记

    +1取模的操作可以交换Trie的三个子节点,并在0节点下递归进行(考虑进位)

    最后对于每个叶子的权值,到达的位置就是由根到它路径上的数组成的数

    #include<iostream>
    #include<utility>
    #include<vector>
    #include<cstdio>
    using namespace std;
    int n=1,N,base[20]={1},cnt=1,tr[2000005][3],val[2000005],tag[2000005],ans[600005];
    char str[200005];
    inline int read()
    {
        int f=1,w=0;
        char ch=0;
        while(ch<'0'||ch>'9'){if(ch=='-') f=-1;ch=getchar();}
        while(ch>='0'&&ch<='9') w=(w<<1)+(w<<3)+ch-'0',ch=getchar();
        return f*w;
    }
    void build(int now,int dep,int v)
    {
        if(dep==N+1)
        {
            val[now]=v;return;
        }
        for(int i=0;i<=2;i++) tr[now][i]=++cnt,build(cnt,dep+1,v+base[dep-1]*i);
    }
    void update(int now)
    {
        if(tag[now]) swap(tr[now][1],tr[now][2]),tag[tr[now][0]]^=1,tag[tr[now][1]]^=1,tag[tr[now][2]]^=1,tag[now]=0;
        int temp=tr[now][0];
        tr[now][0]=tr[now][2],tr[now][2]=tr[now][1],tr[now][1]=temp;
        if(tr[now][0]) update(tr[now][0]);
    }
    void dfs(int now,int ret,int dep)
    {
        if(!tr[now][0])
        {
            ans[val[now]]=ret;return;
        }
        if(tag[now]) swap(tr[now][1],tr[now][2]),tag[tr[now][0]]^=1,tag[tr[now][1]]^=1,tag[tr[now][2]]^=1,tag[now]=0;
        for(int i=0;i<=2;i++) dfs(tr[now][i],ret+base[dep]*i,dep+1);
    }
    int main()
    {
        N=read();
        for(int i=1;i<=N;i++) n*=3;
        for(int i=1;i<=N;i++) base[i]=base[i-1]*3;
        build(1,1,0);
        scanf("%s",str);
        for(int i=0;str[i];i++)
        {
            if(str[i]=='S') tag[1]^=1;
            else update(1);
        }
        dfs(1,0,0);
        for(int i=0;i<n;i++) printf("%d ",ans[i]);
        return 0;
    }
    Strange Dance
  • 相关阅读:
    EF Core 小技巧:迁移已经应用到数据库,如何进行迁移回退操作?
    ABP Framework 5.0 RC.1 新特性和变更说明
    OI迷惑行为大赏【目前较少,持续更新中】
    【比赛日志】APIO2020(2020.08.15)
    【好题】【IPSC2003】 Got Root? 无向图删边游戏
    [HNOI2019] 校园旅行 —— 一个边界数据
    【题解】JOISC 2020 Day 3 stray
    ExtJS学习:MVC模式案例(四) 林枫705
    ExtJS学习:MVC模式案例(三) 林枫705
    ExtJS学习:MVC模式案例(二) 林枫705
  • 原文地址:https://www.cnblogs.com/JDFZ-ZZ/p/14029496.html
Copyright © 2011-2022 走看看