zoukankan      html  css  js  c++  java
  • codeforces #309 div1 B

    题目啰里啰嗦说了一大堆(耐心读完题目就可以秒题了)

    首先我们考虑当前置换的开头的循环节的开头

    1、如果是1 1->1形成循环节 问题变成i-1的子问题

    2、如果是2 1->2->1形成循环节 问题变成i-2的子问题

    3、如果>2 则存在1->x->1形成一个循环节,但在原置换中不连续,所以一定不可能不变

    故设长度为i的满足条件的置换个数为f(i)

    存在f(i)=f(i-1)+f(i-2)
    至于求第K小,逐位确定即可

    #include<cstdio>
    #include<cstring>
    #include<iostream>
    #include<cstdlib>
    #include<algorithm>
    using namespace std;
    
    const int maxn=52;
    typedef long long LL;
    int n;
    int a[maxn];
    LL f[maxn],k;
    
    int main(){
    	scanf("%d",&n);cin>>k;
    	f[0]=1;f[1]=1;
    	for(int i=2;i<=n;++i)f[i]=f[i-1]+f[i-2];
    	int pos=1,base=0;
    	while(pos<=n){
    		if(k>f[n-pos]){
    			k=k-f[n-pos];
    			a[pos]=base+2;
    			a[pos+1]=base+1;
    			pos+=2;base+=2;
    		}else{
    			a[pos]=base+1;
    			pos++;base++;
    		}
    	}
    	for(int i=1;i<=n;++i)printf("%d ",a[i]);
    	return 0;
    }
    

      

  • 相关阅读:
    eclipse中的项目如何打成war包
    【SVN】Please execute the 'Cleanup' command.
    2021.06.02模拟赛DP2
    2021.05.26模拟赛 DP1
    状压DP
    高斯消元
    矩阵快速幂
    2021.05.10讲题
    Luogu P2152[SDOI 2009]Super GCD
    Tarjan
  • 原文地址:https://www.cnblogs.com/joyouth/p/5361981.html
Copyright © 2011-2022 走看看