47. 全排列 II

2022-08-04  本文已影响0人  水中的蓝天

47. 全排列 II

给定一个可包含重复数字的序列 nums ,按任意顺序 返回所有不重复的全排列。

思路:
考虑使用 DFS( Depth-first search 深度优先搜索) 来解决此类问题,很多排列组合相关的问题,都可以通过DFS来解决 ;但要注意去重的问题; 去重需要判断层数对应的索引到将要交换的元素值是否相同,不相同才交换


class Solution {

    public List<List<Integer>> permuteUnique(int[] nums) {

        //0. 边界条件处理
        if(nums==null) return null;
        //1.1 定义结果数组
        List<List<Integer>> list = new ArrayList();
        //1.2 数组中没有元素就返回
        if(nums.length==0) return list;
        //2.DFS
        dfs(list,nums,0);
        //3.返回结果
        return list;
    }
    
    //深度优先搜索
    private void dfs(List<List<Integer>> list, int[] nums,int idx) {
      
      //1.一轮遍历结束了
      if(idx==nums.length) {
          List<Integer> result = new ArrayList();
          for(int val : nums) {
              result.add(val);
          }
          list.add(result);
          return;
      }

      //2.枚举每一层的各种可能,求出满足条件的排列
      for(int i = idx;i < nums.length;i++) {

            //保证一个数字在idx位置只能出现一次
            if(isRepeat(nums,i,idx)) continue;
            //某一层可以交换的索引
            swap(nums,i,idx);
            //下一层 自动回溯
            dfs(list,nums,idx+1);
            //还原现场
            swap(nums,i,idx);

      }

    }

    //交换
    private void swap(int[] nums,int i,int j){
      int tmp  = nums[i];
      nums[i] = nums[j];
      nums[j] = tmp;
    }

    //是否重复
    private boolean isRepeat(int[] nums,int i,int idx){
         //检查[idx,i)之间的值是否有相同的
         for(int j = idx; j < i;j++) {
             if(nums[j]==nums[i]) return true;
         }
         return false;
    }

}

上一篇 下一篇

猜你喜欢

热点阅读