zoukankan      html  css  js  c++  java
  • 【洛谷3516】[POI2011] PRZ-Shift(构造题)

    点此看题面

    • 给定一个长度为(n)的排列,可以进行两种操作:把最后一个数移到开头;把第三个数移到开头。
    • 一段连续的相同操作可以合并为一块操作,求一个操作序列把排列变为(1,2,...,n)
    • (nle2000),操作序列长度需(le n^2)

    构造思路

    我们枚举(i=2sim n),每次尝试让(i)紧贴到(i-1)后面。

    能改变相对顺序的只有第二种操作,且每次可以将一个数向前移动两位。

    因此我们就不断将(i)前移,直至它的前两个数中有(i-1)

    如果(i-1)就是它前面这个数就完事了,否则我们需要把夹在它们两个之间的数(t)给移出去。

    我们依然可以将(t)向前移两位,但注意(i-1)前面根据先前操作必然是连续的(1sim i-1),我们不能让(t)混在其中打乱已有的顺序。

    所以我们至少要将(t)前移(lceilfrac{i-1}2 ceil)次。

    然后这时候就要注意判断无解的情况了,如果(i=n-1),则(t)只可能是(n),那么(t)必须要恰好被移到(i)的后面。又因为我们只能两位两位一移,所以此时(n)为奇数则无解。

    具体实现中要维护好这个排列,只需维护每个位置上的数(a_i)以及每个数所在的位置(p_i)即可。

    代码:(O(n^2))

    #include<bits/stdc++.h>
    #define Tp template<typename Ty>
    #define Ts template<typename Ty,typename... Ar>
    #define Reg register
    #define RI Reg int
    #define Con const
    #define CI Con int&
    #define I inline
    #define W while
    #define N 2000
    #define pre(x) ((x)^1?(x)-1:n)//上一位坐标
    #define dis(x,y) ((x)-(y)+n)%n//两位间距离
    #define Print(op,x) (x)&&(tot+=sprintf(s+tot,op,x),++cnt)//存储操作,同时记录操作数
    using namespace std;
    int n,a[N+5],p[N+5],cnt,tot;char s[N*N*10];
    int x=1;I void Move(CI p3)//将位置p3上的数前移两位
    {
    	RI v3=a[p3],p2=pre(p3),v2=a[p2],p1=pre(p2),v1=a[p1];//记录当前位及前两位
    	Print("%da ",dis(x,p1)),x=p1,Print("%db ",1),p[a[p1]=v3]=p1,p[a[p2]=v1]=p2,p[a[p3]=v2]=p3;//光标移到p1,执行b操作,更新这三位信息
    }
    int main()
    {
    	RI i,j;for(scanf("%d",&n),i=1;i<=n;++i) scanf("%d",a+i),p[a[i]]=i;
    	RI t;for(i=2;i<=n;++i)//让i紧贴到i-1后面
    	{
    		W(a[pre(p[i])]^(i-1)&&a[pre(pre(p[i]))]^(i-1)) Move(p[i]);//如果前两位中没有i-1
    		if(a[pre(p[i])]==i-1) continue;if(i==n-1&&n&1) return puts("NIE"),0;//如果恰好紧贴完事,如果i=n-1且n为奇数无解
    		for(t=a[pre(p[i])],j=1;j<=(i>>1);++j) Move(p[t]);//将中间数前移ceil((i-1)/2)次
    	}return Print("%da ",dis(x,p[1])),printf("%d
    ",cnt),puts(s),0;//最后把光标移到1所在位置
    }
    
    败得义无反顾,弱得一无是处
  • 相关阅读:
    上学要迟到了【最短路转化】
    解方程【狄利克雷卷积+莫比乌斯反演+积性函数】
    FFT
    min25 筛
    Easy【生成函数】
    CF1406D-Three Sequences
    Alice和Bob赌糖果【赌徒破产模型】
    记MySQL自增主键修改无效的问题
    JVM学习笔记(十一、JDK分析工具)
    JVM学习笔记(十、GC3-垃圾回收机制)
  • 原文地址:https://www.cnblogs.com/chenxiaoran666/p/Luogu3516.html
Copyright © 2011-2022 走看看