[AGC013C] Ants on a Circle 解题报告

洛谷题面
AT题面
CF625F

先考虑弱化版,若是不考虑编号怎么办。
这个问题有一个很经典的结论,碰撞等同穿过,所以直接算出每个点按照指定方向走,在 \(t\) 秒后的位置即可。

现在多了一个编号,因为是碰撞,所以两个点的相对位置是相同的,即 \(x\) 号点原来是 \(y\) 号点顺时针方向的第几个点,它最终还是 \(x\) 顺时针方向的第几个点。那么我们只要找到一个点的位置,就可以找到其它所有点的位置。假定我们确定的是第一个点的位置,感性理解一下,每有一个点逆时针穿过 \(0\),它的排名会减 \(1\),反之会加 \(1\)。直接算就好了。

tips:算的时候注意精度问题。

点击查看代码
#include<bits/stdc++.h>
#define ull unsigned long long
#define ll long long
#define int __int128
#define pdi pair<double,int>
#define pii pair<int,int>
#define pb push_back
#define mp make_pair
#define eps 1e-9
using namespace std;
namespace IO{
    template<typename T>
    inline void read(T &x){
        x=0;
        int f=1;
        char ch=getchar();
        while(ch>'9'||ch<'0'){
            if(ch=='-'){
                f=-1;
            }
            ch=getchar();
        }
        while(ch>='0'&&ch<='9'){
            x=x*10+(ch-'0');
            ch=getchar();
        }
        x=(f==1?x:-x);
    }
    template<typename T>
    inline void write(T x){
        if(x<0){
            putchar('-');
            x=-x;
        }
        if(x>=10){
            write(x/10);
        }
        putchar(x%10+'0');
    }
    template<typename T>
    inline void write_endl(T x){
        write(x);
        putchar('\n');
    }
    template<typename T>
    inline void write_space(T x){
        write(x);
        putchar(' ');
    }
}
using namespace IO;
const int N=3e5+10;
int n,ed[N],l,t,pos,id[N],p[N],st[N],ans[N];
bool cmp(int x,int y){
    return st[x]<st[y];
}
signed main(){
    #ifndef ONLINE_JUDGE
        freopen("1.in","r",stdin);
        freopen("1.out","w",stdout);
    #endif
    read(n),read(l),read(t);
    for(int i=0;i<n;i++){
        id[i]=i;
        char opt;
        read(st[i]);
        opt=getchar();
        while(opt!='1'&&opt!='2'){
            opt=getchar();
        }
        if(opt=='2'){
            ed[i]=st[i]-t;
        }
        else{
            ed[i]=st[i]+t;
        }
        int x=floor((long double)ed[i]/l);
        pos=(x%n+n+pos)%n;
        ed[i]=(ed[i]%l+l)%l;
    }
    sort(id,id+n,cmp);
    for(int i=0;i<n;i++){
        p[id[i]]=i;
    }
    sort(ed,ed+n);
    for(int i=0;i<n;i++){
        ans[i]=ed[(i+pos)%n];
    }
    for(int i=0;i<n;i++){
        write_endl(ans[p[i]]);
    }
    return 0;
}
posted @ 2023-05-15 20:38  luo_shen  阅读(46)  评论(0)    收藏  举报