[bzoj] 1025: [SCOI2009]游戏 发表于 Mar 18 2015 | 分类于 bzoj | 题意对于一些长度为n的排列,将其作为一个置换,那么可能有一个自置换的次数使其回到1,2,3,…,n的情况。求对于所有能够回到1,2,3..,n的排列,不同的次数共有多少种。 传送门 分析移步守望、御神木的题解 代码12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364#include <cstdio>int CH , NEG ;inline void read(int& ret) { ret = NEG = 0 ; while (CH=getchar() , CH<'!') ; if (CH == '-') NEG = true , CH = getchar() ; while (ret = ret*10+CH-'0' , CH=getchar() , CH>'!') ; if (NEG) ret = -ret ;}inline void reads(int& ret) {truewhile (ret=getchar() , ret<'!') ;truewhile (CH=getchar() , CH>'!') ;}typedef long long ll ;#define maxn 1010LLint n , p , pri[maxn] = {0} ;bool cps[maxn] = {0} ;ll f[maxn][maxn] = {0} ;int i , j ;inline void GetPri() {truepri[0] = 0 ;truefor (i = 2 ; i <= n ; i ++ )truetrueif (!cps[i]) {truetruetruepri[++pri[0]] = i ;truetruetruefor (j = i<<1 ; j <= n ; j += i )truetruetruetruecps[j] = true ;truetrue}}inline void dp() {truefor (i = 0 ; i <= n ; i ++ )truetruef[i][0] = 1 , f[0][i] = 1 ;truefor (i = 1 ; i <= n ; i ++ )truetruefor (j = 1 ; j <= pri[0] ; j ++ ) {truetruetruef[i][j] = f[i][j-1] ;truetruetruep = pri[j] ;truetruetruewhile (i-p >= 0)truetruetruetruef[i][j] += f[i-p][j-1] , p *= pri[j] ;truetrue}trueprintf("%lld\n", f[n][pri[0]]) ;}int main() {// #define READtrue#ifdef READtruetruefreopen(".in" ,"r",stdin ) ;truetruefreopen(".out","w",stdout) ;true#endiftrueread(n) ;trueGetPri() ;truedp() ;true#ifdef READtruetruefclose(stdin) ; fclose(stdout) ;true#elsetruetruegetchar() ; getchar() ;true#endiftruereturn 0 ;}