題目:輸入乙個字串,列印出該字串中字元的所有排列。例如輸入字串abc,則輸出由字元a、b、c所能排列出來的所有字串abc、acb、bac、bca、cab和cba。
分析:這是一道很好的考查對遞迴理解的程式設計題,因此在過去一年中頻繁出現在各大公司的面試、筆試題中。
我們以三個字元abc為例來分析一下求字串排列的過程。首先我們固定第乙個字元a,求後面兩個字元bc的排列。當兩個字元bc的排列求好之後,我們把第乙個字元a和後面的b交換,得到bac,接著我們固定第乙個字元b,求後面兩個字元ac的排列。現在是把c放到第一位置的時候了。記住前面我們已經把原先的第乙個字元a和後面的b做了交換,為了保證這次c仍然是和原先處在第一位置的a交換,我們在拿c和第乙個字元交換之前,先要把b和a交換回來。在交換b和a之後,再拿c和處在第一位置的a進行交換,得到cba。我們再次固定第乙個字元c,求後面兩個字元b、a的排列。
既然我們已經知道怎麼求三個字元的排列,那麼固定第乙個字元之後求後面兩個字元的排列,就是典型的遞迴思路了。
void permutation(char* pstr, char* pbegin);
/// get the permutation of a string,
// for example, input string abc, its permutation is
// abc acb bac bca cba cab
/void permutation(char* pstr)
/// print the permutation of a string,
// input: pstr - input string
// pbegin - points to the begin char of string
// which we want to permutate in this recursion
/void permutation(char* pstr, char* pbegin)
// otherwise, permute string
else}}
擴充套件1:如果不是求字元的所有排列,而是求字元的所有組合,應該怎麼辦呢?當輸入的字串中含有相同的字串時,相同的字元交換位置是不同的排列,但是同乙個組合。舉個例子,如果輸入aaa,那麼它的排列是6個aaa,但對應的組合只有乙個。
擴充套件2:輸入乙個含有8個數字的陣列,判斷有沒有可能把這8個數字分別放到正方體的8個頂點上,使得正方體上三組相對的面上的4個頂點的和相等。
思路:這是個遞迴求解的問題。遞迴演算法有四個特性:(1)必須有可達到的終止條件,否則程式將陷入死迴圈;(2)子問題在規模上比原問題小;(3)子問題可通過再次遞迴呼叫求解;(4)子問題的解應能組合成整個問題的解。
對於字串的排列問題。如果能生成n - 1個元素的全排列,就能生成n個元素的全排列。對於只有1個元素的集合,可以直接生成全排列。全排列的遞迴終止條件很明確,只有1個元素時。下面這個圖很清楚的給出了遞迴的過程。
#include
#include
#include
void f(char *str, int len, int n)
else
} free(p);
} int main(int argc, char **argv)
字串排列組合問題
一.全排列無重複字元 include include char buf 1024 void func int index void swap int index1,int index2 intmain void func int index else void swap int index1,int...
字串的排列組合問題
問題1 輸入乙個字串,列印出該字串中字元的所有排列。例如輸入字串abc,則輸出由字元a b c所能排列出來的所有字串abc acb bac bca cab和cba。思路 這是個遞迴求解的問題。遞迴演算法有四個特性 1 必須有可達到的終止條件,否則程式將陷入死迴圈 2 子問題在規模上比原問題小 3 子...
字串的排列組合問題
本文 問題1 輸入乙個字串,列印出該字串中字元的所有排列。例如輸入字串abc,則輸出由字元a b c所能排列出來的所有字串abc acb bac bca cab和cba。思路 這是個遞迴求解的問題。遞迴演算法有四個特性 1 必須有可達到的終止條件,否則程式將陷入死迴圈 2 子問題在規模上比原問題小 ...