1. 程式人生 > >java 實現全排列組合

java 實現全排列組合

import java.util.*;

public class AllSort{ 
 static int count = 0;
 static char[] buf = {'1', '2', '3', '4'}; 
    static ArrayList<String> list = new ArrayList<String>();
   
    public static void main(String[] args) { 
        select(buf, list, 3);
       
        for(String str : list){
         char[] temp = str.toCharArray();
         //perm(temp,0,temp.length-1);
         System.out.println(str);
        }
       
        System.out.println("In total: "+ count);
    } 
   
    public static void select(char[] source, ArrayList<String> arrayList, int num){
     int l = source.length;
     
     char[] temp = new char[num];
     
     System.arraycopy(source, 0, temp, 0, num);
     
     arrayList.add(new String(temp));
     
     for(int i=num; i<l; i++){
      for (int j=0; j<num; j++){
       char tempChar = temp[j];
       temp[j] = source[i];
        
       arrayList.add(new String(temp));
       
       temp[j] = tempChar;
      }
     }
    }
    public static void perm(char[] buf, int start, int end){ 
        if(start==end){//當只要求對陣列中一個字母進行全排列時,只要就按該陣列輸出即可 
            for(int i=0;i<=end;i++){ 
                System.out.print(buf[i]);        
            } 
            count ++;
            System.out.println();
        } 
        else{//多個字母全排列 
            for(int i=start;i<=end;i++){ 
                char temp=buf[start];//交換陣列第一個元素與後續的元素 
                buf[start]=buf[i]; 
                buf[i]=temp; 
                 
                perm(buf,start+1,end);//後續元素遞迴全排列 
                 
                temp=buf[start];//將交換後的陣列還原 
                buf[start]=buf[i]; 
                buf[i]=temp; 
            } 
        } 
    } 
}

    全排列的演算法是一個基礎,排列演算法在它的基礎上增加了選數過程(select),即先選後排。這裡面主要是用到了一個遞迴的思想, 利用遞迴法來做這題關鍵下幾點:
1.普通情況-取出序列中的一個數並且將剩下的序列全排列
2.特殊情況-序列中只剩一個數,則全排列就是其自身。將增個獲得的序列輸出。
3.在不止一個數的情況下,該位要分別交換剩下的數(例如:兩個數A,B 則有兩種情況,一個是AB 一個是BA)

參考文章

http://www.cnblogs.com/nokiaguy/archive/2008/05/11/1191914.html

主要思想:

設R={r1,r2,…,rn}是要進行排列的n個元素,Ri=R-{ri}
(ri)Perm(X)表示在全排列Perm(X)的每一個排列前加上字首ri得到的排列

    (1)當n=1時,Perm(R)=(r),其中r是集合R中唯一的元素;
    (2)當n>1時,Perm(R)可由(r1)Perm(R1),(r2)Perm(R2),…,(rn)Perm(Rn)構成

m 取n

package test;

import java.util.ArrayList;
import java.util.List;

public class Test {
    private static char[] is = new char[] { '1', '2', '4', '5', '6', '7', '8', '9'};
    private static int total;
    private static int m = 6;

    public static void main(String[] args) {
        List<Integer> iL = new ArrayList<Integer>();
        new Test().plzh("", iL,  m);
        System.out.println("total : " + total);
    }

    private void plzh(String s, List<Integer> iL, int m) {
        if(m == 0) {

            System.out.println(s);
            total++;
            return;
        }
        List<Integer> iL2;
        for(int i = 0; i < is.length; i++) {
            iL2 = new ArrayList<Integer>();
            iL2.addAll(iL);
            if(!iL.contains(i)) {
                String str = s + is[i];
                iL2.add(i);
                plzh(str, iL2, m-1);
            }
        }
    }
}