做專案遇到資料採集系統中adc拼合問題,如果順序不對,波形就是錯誤的(題外話),為了找到正確的順序,涉及到排列問題。
一般地,從n個不同元素中取出m(m≤n)個元素,按照一定的順序排成一列,叫做從n個元素中取出m個元素的乙個排列(arrangement)。特別地,當m=n時,這個排列被稱作全排列(permutation)。
ex:考慮三個數字1,2,3,這個序列有6個可能的排列組合
123
132
213
231
312
321
這些排列組合根據less-than操作符做字典順序的排序。
字典順序顧名思義是就是將1-n的乙個排列看成乙個數,然後按照字典的順序從小到達的輸出
所謂的全排列,就是說將數字進行不重複的排列,所有得到的序列,就是全排列
給定數字1 , 2 , 3 , 4,其全排列是:
, , , , ,
, , , , ,
, , , , ,
, , , , ,
全排列如上所示,那麼什麼是全排列的序號?這裡我們通常將全排列按照字典序進行編排,就如上面從左到右看,就是按照字典序排列的。
我們說,對於1,2,3,4的全排列,第20號序列是,因為其在這個按照字典序排列的全排列中處在第20的位置。
在stl中,有next_permutation的演算法實現。
next_permutation()會取得[first,last) 所標之序列的下乙個排列組合。如果沒有下乙個排列組合,便返回false,否則返回true。
演算法:
首先,從最尾端開始往前尋找兩個相鄰元素,令第乙個元素為*i,第二個元素為*ii,且滿足*i < *ii。找到這樣一組相鄰元素後,再從最尾端開始往前檢驗,找出第乙個大於*i 的元素,令為*j ,將i,j元素對調,再將ii之後的所有元素顛倒排序。
如下圖:方框為i和ii
};首先,從最尾端開始往前尋找兩個相鄰元素,令第乙個元素為*i,第二個元素為*ii,且滿足*i > *ii。找到這樣一組相鄰元素後,再從最尾端開始往前檢驗,找出第乙個小於*i 的元素,令為*j ,將i,j元素對調,再將ii之後的所有元素顛倒排序。
**和next_permutation類似
康托展開式實現了由1到n組成的全排列序列到其編號之間的一種對映
公式:
x=an*(n-1)!+an-1*(n-2)!+…+ai*(i-1)!+…+a2*1!+a1*0!
由1到n這n個數組成的全排列,共n!個,按每個全排列組成的數從小到大進行排列,並對每個序列進行編號(從0開始),並記為x;比如說1到4組成的全排列中,1234對應編號0,1243對應編號1。
對於ai(係數)的解釋需要用例子來說明:
對1到4的全排列中,我們來考察3214,則
a4==2
a3==1
a2==0
a1=0(最後只剩下一項)
也就是說康托公式中的每一項依次對應全排列序列中的每個元素,並按上述規則對映;
則x=2*3!+1*2!+0*1!+0*0!=14,即3214對應的編號為14。
code:
//已知排列求序號
long
long getindex(short dim, short *rankbuf)
康托公式可以根據排列的序號來求出該排列,即通過x的值求出ai(i大於等於1小於等於n)的值,運用輾轉相除的方法即可實現,現在已知乙個編號14(注意該編號是從0開始的,如果是從1開始,此處要減1),求其對應的全排列序列:
14 / (3!) = 2 餘 2
2 / (2!) = 1 餘 0
0 / (1!) = 0 餘 0
0 / (0!) = 0 餘 0
故得到:a4=2,a3=1,a2=0,a1=0,由ai的定義即可確定14對應的全排列為2103.
code:
//已知序號求排列
void getpermutation(int dim, short *rankbuf, long
long
index)
for (i = dim - 1; i; i--)
for (j = i - 1; j >= 0; j--)
if (rankbuf[j] <= rankbuf[i])
rankbuf[i]++; //根據逆序數陣列進行調整
}
全排列演算法及實現
全排列在很多程式都有應用,是乙個很常見的演算法,常規的演算法是一種遞迴的演算法,這種演算法的得到基於以下的分析思路。給定乙個具有n個元素的集合 n 1 要求輸出這個集合中元素的所有可能的排列。一 遞迴實現 例如,如果集合是,那麼這個集合中元素的所有排列是,顯然,給定n個元素共有n 種不同的排列,如果...
全排列演算法及實現
全排列在很多程式都有應用,是乙個很常見的演算法,常規的演算法是一種遞迴的演算法,這種演算法的得到基於以下的分析思路。給定乙個具有n個元素的集合 n 1 要求輸出這個集合中元素的所有可能的排列。一 遞迴實現 例如,如果集合是,那麼這個集合中元素的所有排列是,顯然,給定n個元素共有n 種不同的排列,如果...
全排列演算法及實現
全排列在很多程式都有應用,是乙個很常見的演算法,常規的演算法是一種遞迴的演算法,這種演算法的得到基於以下的分析思路。給定乙個具有n個元素的集合 n 1 要求輸出這個集合中元素的所有可能的排列。一 遞迴實現 例如,如果集合是,那麼這個集合中元素的所有排列是,顯然,給定n個元素共有n 種不同的排列,如果...