1. 程式人生 > >leetCode 47.Permutations II (排列組合II) 解題思路和方法

leetCode 47.Permutations II (排列組合II) 解題思路和方法

nts 看到了 possible ash following for oss article sort

Permutations II

Given a collection of numbers that might contain duplicates, return all possible unique permutations.

For example,
[1,1,2] have the following unique permutations:

[1,1,2], [1,2,1], and [2,1,1].


思路:這題相比於上一題,是去除了反復項。

代碼上與上題略有區別。詳細代碼例如以下:

public class Solution {
    boolean[] b;
    List<List<Integer>> list;
    Set<String> al;
    public List<List<Integer>> permuteUnique(int[] nums) {
        b = new boolean[nums.length];
        Arrays.fill(b,true);
        Arrays.sort(nums);
        list = new ArrayList<List<Integer>>();
        al = new HashSet<String>();
        count(nums, "", nums.length);
        //對al數據進行處理
        Iterator<String> iterator = al.iterator();
        //叠代器
        while(iterator.hasNext()){
        	String s = iterator.next();
        	List<Integer> newal = new ArrayList<Integer>();
        	for(int i = 0; i < s.length();i++){
        		if(s.charAt(i) == '-'){//有負號
        			newal.add('0' - s.charAt(++i) );
        		}else{//無負號
        			newal.add(s.charAt(i) - '0');
        		}
        	}
        	list.add(newal);
        }
        return list;
    }
    /**
     * @param nums 要排列的數組
     * @param str 已經排列好的字符串
     * @param nn 剩下須要排列的個數,假設須要全排列,則nn為數組長度
     */
     void count(int[] nums,String str,int nn){
        if(nn == 0){
            al.add(str);//先加入到al中,再對al數據進行處理
            return;
        }
        for(int i = 0; i < nums.length; i++){
        	if(nn == nums.length && i > 0 && nums[i] == nums[i-1]){
        		continue;//去除反復項
        	}
            if(b[i]){//假設還沒有組合,則組合上
                b[i] = false;//標記為已組合
                count(nums,str + nums[i],nn-1);
                b[i] = true;//為下一組合準備
            }
        }
    }
}


可是上述代碼在數據量比較大的時候效率非常低,如數據有10個數據時大概耗時200ms。在論壇上看到了一個大神的代碼。10個數據的耗時約25ms,效率非常高。

詳細代碼例如以下:

public class Solution {
    public List<List<Integer>> permuteUnique(int[] num) {
		List<List<Integer>> returnList = new ArrayList<List<Integer>>();
		returnList.add(new ArrayList<Integer>());
	 
		for (int i = 0; i < num.length; i++) {
			Set<List<Integer>> currentSet = new HashSet<List<Integer>>();
			for (List<Integer> l : returnList) {
				for (int j = 0; j < l.size() + 1; j++) {
					l.add(j, num[i]);
					List<Integer> T = new ArrayList<Integer>(l);
					l.remove(j);
					currentSet.add(T);
				}
			}
			returnList = new ArrayList<List<Integer>>(currentSet);
		}
	 
		return returnList;
	}
}



leetCode 47.Permutations II (排列組合II) 解題思路和方法