码迷,mamicode.com
首页 > 其他好文 > 详细

康托展开和逆展开

时间:2015-02-01 23:14:38      阅读:272      评论:0      收藏:0      [点我收藏+]

标签:

康托展开:

给定一个排列(由n个数排列而成),我们可以计算出该排列在由n个数组成的所有排列中排名第几(按字典序),这就是康托展开。

比如由4个数1,2,3,4组成排列

那么2413在所有的排列中排第几呢?

首先计算第一位数字比2小的排列有多少种,即 1 * fac[3],怎么得来的呢?首先比2小的数字只有1个,那么第一位数字只有一种选择,剩下的三位数字有fac[3]种选择,所以是1 * fac[3]

现在当第一位固定是2,那么来计算第二位数字比4小的排列有多少种呢?首先比4小的数字有1个,那么第一位数字只有一种选择,剩下的两位数字有fac[2]中选择,所以是1*fac[2]

依次类推,当前两位固定为24,第三位比1小的排列有0 * fac[1]

以此类推,当前两三位固定为241时,第4位比3小的排列有0*fac[0];

即fac[3] + fac[2] = 8;特别记住,我们算出来的是比2413小的排列有多少种,所以2413在所有由1,2,3,4组成的排列中排名第9。

技术分享
 1 int KT(int *a, int n)//算出数组中存储的数字在全排列中排第几
 2 {
 3     int i,j,cnt,pos = 0;
 4     for(i=0; i<n; ++i)
 5     {
 6         cnt = 0;
 7         for(j=i+1; j<n; ++j)
 8             if(a[j] < a[i])
 9                 cnt++;
10         pos += cnt * fac[n-i-1];
11     }    
12     return pos + 1;
13 }
View Code

康托逆展开:

给定5个数1,2,3,4,5,  找出排第48的排列是什么,设这个排列为x1x2x3x4x5,

设比x1小的数字有k1个,那么有k1*4!种排列比x1x2x3x4x5小

设比x2小的数字有k2个,那么有k2*3!种排列比x1x2x3x4x5小。

以此类推,共有k1*4!+k2*3!+k3*2!+k4*1!种阶乘比x1x2x3x4x5小

即k1*4!+k2*3!+k3*2!+k4*1!==48-1

而且,k1<=4, k2<=3,k3<=2,k4<=1.那么即使k2,k3,k3取最大值,即k2=3,k3=2,k4=1

那么k2*3!+k3*2!+k4*1! 依旧<4!   所以可以用47/4!得到k1

然后 (47-k1*4!) / 3!  得到k2,

以此类推得到k3,k4

 1 /*
 2 算出由数组中存的n个不同的数组成的排第pos位的排列是什么
 3 */
 4 void KT_decode(int *a, int *b,int pos, int n)
 5 {
 6     sort(a,a+n);
 7     int i=0,j,cnt1,cnt2;
 8     pos -= 1;
 9     while(pos)
10     {
11         cnt2 = 0;
12         cnt1 = pos / fac[n-i-1];
13         pos -= cnt1 * fac[n-i-1];
14         for(j=0; j<n; ++j)
15         {
16             if(!vis[a[j]])
17                 cnt2++;
18             if(cnt2==cnt1+1)
19             {
20                 vis[a[j]] = true;
21                 b[i++] = a[j];
22                 break;
23             }                
24         }    
25     }
26     for(j=0; j<n; ++j)
27         if(!vis[a[j]])
28             b[i++] = a[j];
29     
30 }

 

康托展开和逆展开

标签:

原文地址:http://www.cnblogs.com/justPassBy/p/4266501.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!