有关康拓展开的介绍,请看百度百科:http://baike.baidu.com/view/437641.htm
下面是康拓展开的逆运算的函数,acm中常常用到:
#include<iostream> using namespace std; int fac[] = {1,1,2,6,24,120,720,5040,40320}; //i的阶乘为fac[i] /*{1...n}的全排列,中的第k个数为s[] */ void invKT(int n, int k, int s[]) { int i, j, t, vst[8]={0}; k--; for (i=0; i<n; i++) //0 到 n-1 分别对应了要求的数组s[]的下标序号 { t = k/fac[n-i-1]; //从 (n-1)!开始 t为比第[i]小的个数 for (j=1; j<=n; j++) //判断数字从1 到 n 哪些数字没有用 if (!vst[j]) //如果这个数字没有使用,并且比她小的数有0个,那么这个数i就是要找的数 { if (t == 0) break; t--; //找到比她小的有0个的数 } s[i] = j; vst[j] = 1; k %= fac[n-i-1]; } } int main() { int s[4]; invKT(4,3,s);//找1,2,3,4的第3个 for(int i=0;i < 4; ++i) cout<<s[i] <<endl; return 0; }