Skip to content
Related Articles

Related Articles

Improve Article
Save Article
Like Article

Print all possible permutations of an array with duplicates using Backtracking

  • Difficulty Level : Medium
  • Last Updated : 20 Aug, 2021

Given an array nums[] of size N, the task is to print all possible distinct permutations of the array nums[] (including duplicates).

Input: nums[] = { 1, 2, 2 }
Output: 
1 2 1
2 1 2
2 2 1

Attention reader! Don’t stop learning now. Get hold of all the important DSA concepts with the DSA Self Paced Course at a student-friendly price and become industry ready.  To complete your preparation from learning a language to DS Algo and many more,  please refer Complete Interview Preparation Course.

In case you wish to attend live classes with experts, please refer DSA Live Classes for Working Professionals and Competitive Programming Live for Students.

Input: nums[] = { 1, 1 }
Output: 1 1



Approach : Follow the steps below to solve the problem

  1. Traverse the array.
  2. Generate permutations of an array.
  3. Set an order of selection among duplicate elements.
  4. If i > 0 && nums[i] == nums[i – 1]: Add nums[i] in the current permutation only if nums[i – 1] has been added in the permutation, i.e visited[i – 1] is true.
  5. Otherwise, continue.
  6. Using this approach, print the distinct permutations generated.

Check this Recursion Tree to understand the implementation details of the code.

Below is the implementation of the above approach:

C++14




// C++ Program to implement
// the above approach
 
#include <bits/stdc++.h>
using namespace std;
 
// Function to fill the vector curr
// while maintaining the indices visited
// in the array num
void backtrack(vector<int>& nums,
               vector<int>& curr,
               vector<vector<int> >& ans,
               vector<bool>& visited)
{
 
    // If current permutation is complete
    if ((int)curr.size() == (int)nums.size()) {
        ans.push_back(curr);
    }
 
    // Traverse the input vector
    for (int i = 0; i < (int)nums.size();
         i++) {
 
        // If index is already visited
        if (visited[i])
            continue;
 
        // If the number is duplicate
        if (i > 0 and nums[i] == nums[i - 1]
            and !visited[i - 1])
            continue;
 
        // Set visited[i] flag as true
        visited[i] = true;
 
        // Push nums[i] to current vector
        curr.push_back(nums[i]);
 
        // Recursive function call
        backtrack(nums, curr,
                  ans, visited);
 
        // Backtrack to the previous
        // state by unsetting visited[i]
        visited[i] = false;
 
        // Pop nums[i] and place at
        // the back of the vector
        curr.pop_back();
    }
}
 
// Function to pre-process the vector num
vector<vector<int> > permuteDuplicates(
    vector<int>& nums)
{
    // Sort the array
    sort(nums.begin(), nums.end());
 
    // Stores distinct permutations
    vector<vector<int> > ans;
 
    vector<bool> visited(
        (int)nums.size(), false);
 
    // Store the current permutation
    vector<int> curr;
 
    // Find the distinct permutations of num
    backtrack(nums, curr, ans, visited);
 
    return ans;
}
 
// Function call to print all distinct
// permutations of the vector nums
void getDistinctPermutations(vector<int> nums)
{
    // Find the distinct permutations
    vector<vector<int> > ans
        = permuteDuplicates(nums);
 
    // Traverse every row
    for (int i = 0; i < (int)ans.size();
         i++) {
 
        // Traverse every column
        for (int j = 0; j < (int)ans[i].size();
             j++) {
 
            cout << ans[i][j] << " ";
        }
 
        cout << '\n';
    }
}
 
// Driver Code
int main()
{
    // Input
    vector<int> nums = { 1, 2, 2 };
 
    // Function call to print
    // all distinct permutations
    getDistinctPermutations(nums);
 
    return 0;
}

Java




// Java Program to implement
// the above approach
import java.io.*;
import java.util.*;
class GFG {
 
  static ArrayList<Integer> nums = new ArrayList<Integer>();
  static ArrayList<Integer> curr = new ArrayList<Integer>();
  static ArrayList<ArrayList<Integer>> ans = new ArrayList<ArrayList<Integer>>();
  static ArrayList<Boolean> visited = new ArrayList<Boolean>();
 
  // Function to fill the vector curr
  // while maintaining the indices visited
  // in the array num
  static void backtrack()
  {
 
    // If current permutation is complete
    if (curr.size() == nums.size())
    {
      ans.add(curr);
      for(int i = 0; i < curr.size(); i++)
      {
        System.out.print(curr.get(i) +" ");
      }
      System.out.println();
    }
 
    // Traverse the input vector
    for (int i = 0; i < (int)nums.size();
         i++)
    {
 
      // If index is already visited
      if (visited.get(i))
        continue;
 
      // If the number is duplicate
      if (i > 0 && (nums.get(i) == nums.get(i - 1)) && !visited.get(i - 1))
        continue;
 
      // Set visited[i] flag as true
      visited.set(i, true);
 
      // Push nums[i] to current vector
      curr.add(nums.get(i));
 
      // Recursive function call
      backtrack();
 
      // Backtrack to the previous
      // state by unsetting visited[i]
      visited.set(i, false);
 
      // Pop nums[i] and place at
      // the back of the vector
      curr.remove(curr.size() - 1);
    }
  }
  // Function to pre-process the vector num
  static ArrayList<ArrayList<Integer>> permuteDuplicates()
  {
    // Sort the array
    Collections.sort(nums);
 
    for(int i = 0; i < nums.size(); i++)
    {
      visited.add(false);
    }
 
    // Find the distinct permutations of num
    backtrack();
 
    return ans;
 
  }
 
  // Function call to print all distinct
  // permutations of the vector nums
 
  static void getDistinctPermutations()
  {
    ans = permuteDuplicates();
 
 
  }
 
  // Driver code
  public static void main (String[] args)
  {
 
    // Input
    nums.add(1);
    nums.add(2);
    nums.add(2);
 
    // Function call to print
    // all distinct permutations
    getDistinctPermutations();
  }
}
 
// This code is contributed by avanitrachhadiya2155

Python3




# Python3 Program to implement
# the above approach
 
# Function to fill the vector curr
# while maintaining the indices visited
# in the array num
def backtrack():
    global ans, curr, visited, nums
     
    # If current permutation is complete
    # print(ans)
    if (len(curr) == len(nums)):
        print(*curr)
 
    # Traverse the input vector
    for i in range(len(nums)):
 
        # If index is already visited
        if (visited[i]):
            continue
 
        # If the number is duplicate
        if (i > 0 and nums[i] == nums[i - 1] and visited[i - 1]==False):
            continue
 
        # Set visited[i] flag as true
        visited[i] = True
 
        # Push nums[i] to current vector
        curr.append(nums[i])
 
        # Recursive function call
        backtrack()
 
        # Backtrack to the previous
        # state by unsetting visited[i]
        visited[i] = False
 
        # Pop nums[i] and place at
        # the back of the vector
        del curr[-1]
 
# Function to pre-process the vector num
def permuteDuplicates(nums):
    global ans, visited, curr
    nums = sorted(nums)
 
    # Find the distinct permutations of num
    backtrack()
    return ans
 
# Function call to print all distinct
# permutations of the vector nums
def getDistinctPermutations(nums):
    global ans, curr, visited
     
    # Find the distinct permutations
    ans = permuteDuplicates(nums)
 
# Driver Code
if __name__ == '__main__':
    visited = [False]*(5)
    ans,curr = [], []
    nums = [1, 2, 2]
 
    # Function call to print
    # all distinct permutations
    getDistinctPermutations(nums)
 
    # This code is contributed by mohit kumar 29.

C#




// C# Program to implement
// the above approach
using System;
using System.Collections.Generic;
 
public class GFG{
 
  static List<int> nums = new List<int>();
  static List<int> curr = new List<int>();
  static List<List<int>> ans = new List<List<int>>();
  static List<bool> visited = new List<bool>();
 
  // Function to fill the vector curr
  // while maintaining the indices visited
  // in the array num
  static void backtrack()
  {
 
    // If current permutation is complete
    if (curr.Count == nums.Count)
    {
      ans.Add(curr);
      for(int i = 0; i < curr.Count; i++)
      {
        Console.Write(curr[i] +" ");
      }
      Console.WriteLine();
    }
 
    // Traverse the input vector
    for (int i = 0; i < (int)nums.Count;
         i++)
    {
 
      // If index is already visited
      if (visited[i])
        continue;
 
      // If the number is duplicate
      if (i > 0 && (nums[i] == nums[i-1]) && !visited[i-1])
        continue;
 
      // Set visited[i] flag as true
      visited[i] = true;
 
      // Push nums[i] to current vector
      curr.Add(nums[i]);
 
      // Recursive function call
      backtrack();
 
      // Backtrack to the previous
      // state by unsetting visited[i]
      visited[i] = false;
 
      // Pop nums[i] and place at
      // the back of the vector
      curr.RemoveAt(curr.Count - 1);
    }
  }
 
  // Function to pre-process the vector num
  static List<List<int>> permuteDuplicates()
  {
    // Sort the array
    nums.Sort();
 
    for(int i = 0; i < nums.Count; i++)
    {
      visited.Add(false);
    }
 
    // Find the distinct permutations of num
    backtrack();
 
    return ans;
 
  }
 
  // Function call to print all distinct
  // permutations of the vector nums
 
  static void getDistinctPermutations()
  {
    ans = permuteDuplicates();
 
 
  }
 
  // Driver code
  static public void Main (){
 
    // Input
    nums.Add(1);
    nums.Add(2);
    nums.Add(2);
 
    // Function call to print
    // all distinct permutations
    getDistinctPermutations();
 
  }
}
 
// This code is contributed by rag2127

Javascript




<script>
 
// JavaScript Program to implement
// the above approach
 
let nums = [];
let curr = [];
let ans = [];
let visited = [];
 
// Function to fill the vector curr
  // while maintaining the indices visited
  // in the array num
function backtrack()
{
    // If current permutation is complete
    if (curr.length == nums.length)
    {
      ans.push(curr);
      for(let i = 0; i < curr.length; i++)
      {
        document.write(curr[i] +" ");
      }
      document.write("<br>");
    }
  
    // Traverse the input vector
    for (let i = 0; i < nums.length;
         i++)
    {
  
      // If index is already visited
      if (visited[i])
        continue;
  
      // If the number is duplicate
      if (i > 0 && (nums[i] == nums[i - 1]) && !visited[i - 1])
        continue;
  
      // Set visited[i] flag as true
      visited[i] = true;
  
      // Push nums[i] to current vector
      curr.push(nums[i]);
  
      // Recursive function call
      backtrack();
  
      // Backtrack to the previous
      // state by unsetting visited[i]
      visited[i] = false;
  
      // Pop nums[i] and place at
      // the back of the vector
      curr.pop();
    }
}
 
 // Function to pre-process the vector num
function permuteDuplicates()
{
    // Sort the array
    (nums).sort(function(a,b){return a-b});
  
    for(let i = 0; i < nums.length; i++)
    {
      visited.push(false);
    }
  
    // Find the distinct permutations of num
    backtrack();
  
    return ans;
}
 
// Function call to print all distinct
  // permutations of the vector nums
function getDistinctPermutations()
{
    ans = permuteDuplicates();
}
 
 // Driver code
// Input
nums.push(1);
nums.push(2);
nums.push(2);
 
// Function call to print
// all distinct permutations
getDistinctPermutations();
 
 
// This code is contributed by unknown2108
 
</script>
Output: 
1 2 2 
2 1 2 
2 2 1

 

Time Complexity: O(N! * N)
Auxiliary Space : O(N! * N)

 




My Personal Notes arrow_drop_up
Recommended Articles
Page :

Start Your Coding Journey Now!