Print all distinct permutations of a string having duplicates.
Examples:
Input : ABCA
Output : AABC AACB ABAC ABCA ACBA
ACAB BAAC BACA BCAA CABA
CAAB CBAA
An algorithm to print all distinct permutations has already been discussed here. Here we’ll discuss one more approach to do the same. Recall first how we print permutations without any duplicates in the input string. It is given here. Let’s now take the case of the string “ABAC”. While generating permutations, let’s say we are at index = 0, and swap it with all elements after it. When we reach i=2, we see that in the string s[index…i-1], there was an index that is equal to s[i]. Thus, swapping it will produce repeated permutations. Thus, we don’t swap it. The below explains it better.
Illustration: Let us understand with the below example.
i = 0 1 2 3
A B A C
index = 0, s[0] = A
Start swapping s[index] with s[i] following it:
i = index + 1 = 1
Since s[index] != s[i], swap and recur.
i = 2, s[index] == s[i], don't swap
i = 3, s[index] != s[i], swap and recur.
The Below code does the same.
C++
#include <bits/stdc++.h>
using namespace std;
bool shouldSwap( char str[], int start, int curr)
{
for ( int i = start; i < curr; i++)
if (str[i] == str[curr])
return 0;
return 1;
}
void findPermutations( char str[], int index, int n)
{
if (index >= n) {
cout << str << endl;
return ;
}
for ( int i = index; i < n; i++) {
bool check = shouldSwap(str, index, i);
if (check) {
swap(str[index], str[i]);
findPermutations(str, index + 1, n);
swap(str[index], str[i]);
}
}
}
int main()
{
char str[] = "ABCA" ;
int n = strlen (str);
findPermutations(str, 0, n);
return 0;
}
|
C
#include <stdbool.h>
#include <stdio.h>
#include <string.h>
bool shouldSwap( char str[], int start, int curr)
{
for ( int i = start; i < curr; i++)
if (str[i] == str[curr])
return 0;
return 1;
}
void findPermutations( char str[], int index, int n)
{
if (index >= n) {
printf ( "%s\n" , str);
return ;
}
for ( int i = index; i < n; i++) {
bool check = shouldSwap(str, index, i);
if (check) {
char temp = str[index];
str[index] = str[i];
str[i] = temp;
findPermutations(str, index + 1, n);
temp = str[index];
str[index] = str[i];
str[i] = temp;
}
}
}
int main()
{
char str[] = "ABCA" ;
int n = strlen (str);
findPermutations(str, 0, n);
return 0;
}
|
Java
public class GFG {
static boolean shouldSwap( char str[], int start, int curr) {
for ( int i = start; i < curr; i++) {
if (str[i] == str[curr]) {
return false ;
}
}
return true ;
}
static void findPermutations( char str[], int index, int n) {
if (index >= n) {
System.out.println(str);
return ;
}
for ( int i = index; i < n; i++) {
boolean check = shouldSwap(str, index, i);
if (check) {
swap(str, index, i);
findPermutations(str, index + 1 , n);
swap(str, index, i);
}
}
}
static void swap( char [] str, int i, int j) {
char c = str[i];
str[i] = str[j];
str[j] = c;
}
public static void main(String[] args) {
char str[] = { 'A' , 'B' , 'C' , 'A' };
int n = str.length;
findPermutations(str, 0 , n);
}
}
|
Python3
def shouldSwap(string, start, curr):
for i in range (start, curr):
if string[i] = = string[curr]:
return 0
return 1
def findPermutations(string, index, n):
if index > = n:
print (''.join(string))
return
for i in range (index, n):
check = shouldSwap(string, index, i)
if check:
string[index], string[i] = string[i], string[index]
findPermutations(string, index + 1 , n)
string[index], string[i] = string[i], string[index]
if __name__ = = "__main__" :
string = list ( "ABCA" )
n = len (string)
findPermutations(string, 0 , n)
|
C#
using System;
class GFG
{
static bool shouldSwap( char []str,
int start, int curr)
{
for ( int i = start; i < curr; i++)
{
if (str[i] == str[curr])
{
return false ;
}
}
return true ;
}
static void findPermutations( char []str,
int index, int n)
{
if (index >= n)
{
Console.WriteLine(str);
return ;
}
for ( int i = index; i < n; i++)
{
bool check = shouldSwap(str, index, i);
if (check)
{
swap(str, index, i);
findPermutations(str, index + 1, n);
swap(str, index, i);
}
}
}
static void swap( char [] str, int i, int j)
{
char c = str[i];
str[i] = str[j];
str[j] = c;
}
public static void Main()
{
char []str = { 'A' , 'B' , 'C' , 'A' };
int n = str.Length;
findPermutations(str, 0, n);
}
}
|
Javascript
<script>
function shouldSwap(str, start, curr) {
for (let i = start; i < curr; i++) {
if (str[i] == str[curr]) {
return false ;
}
}
return true ;
}
function findPermutations(str, index, n) {
if (index >= n) {
document.write(str);
document.write( "<br/>" )
return ;
}
for (let i = index; i < n; i++) {
let check = shouldSwap(str, index, i);
if (check) {
swap(str, index, i);
findPermutations(str, index + 1, n);
swap(str, index, i);
}
}
}
function swap(str, i, j) {
let c = str[i];
str[i] = str[j];
str[j] = c;
}
let str = ['A ', ' B ', ' C ', ' A'];
let n = str.length;
findPermutations(str, 0, n);
</script>
|
OutputABCA
ABAC
ACBA
ACAB
AACB
AABC
BACA
BAAC
BCAA
CBAA
CABA
CAAB
Better Approach:
Generate all distinct strings simply using some if conditions. The technique above uses an extra loop inside the recursion which causes a major time complexity cost. Instead, we can improve it by little pre-processing. We first sort the given string and then apply the below code.
Below is the implementation of the above idea:
C++
#include <algorithm>
#include <iostream>
#include <string>
using namespace std;
int total = 0;
void permute( int i, string &s)
{
if (i == (s.length() - 1)) {
cout << s << endl;
total++;
return ;
}
for ( int j = i; j < s.length(); j++) {
if (j>i && s[i] == s[j])
continue ;
if (j>i && s[j-1] == s[j]) {
continue ;
}
swap(s[i], s[j]);
permute(i + 1, s);
swap(s[i], s[j]);
}
}
int main()
{
string s = "abca" ;
sort(s.begin(), s.end());
permute(0, s);
cout << "Total distinct permutations = " << total
<< endl;
return 0;
}
|
Java
import java.util.*;
class GFG{
static int total = 0 ;
static void permute( int i, String s)
{
if (i == (s.length() - 1 ))
{
System.out.print(s + "\n" );
total++;
return ;
}
char prev = '*' ;
for ( int j = i; j < s.length(); j++)
{
char []temp = s.toCharArray();
if (j > i && temp[i] == temp[j])
continue ;
if (prev != '*' && prev == s.charAt(j))
{
continue ;
}
temp = swap(temp,i,j);
prev = s.charAt(j);
permute(i + 1 , String.valueOf(temp));
}
}
static char [] swap( char []arr, int i, int j)
{
char temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
return arr;
}
static String sortString(String inputString)
{
char tempArray[] = inputString.toCharArray();
Arrays.sort(tempArray);
return new String(tempArray);
}
public static void main(String[] args)
{
String s = "abca" ;
s = sortString(s);
permute( 0 , s);
System.out.print( "Total distinct permutations = " +
total + "\n" );
}
}
|
Python3
total = 0
def swap(arr, i, j):
temp = arr[i]
arr[i] = arr[j]
arr[j] = temp
return arr
def permute(i, s):
global total
if (i = = ( len (s) - 1 )):
print (s)
total + = 1
return
prev = '*'
for j in range (i, len (s)):
temp = list (s)
if (j > i and temp[i] = = temp[j]):
continue
if (prev ! = '*' and prev = = s[j]):
continue
temp = swap(temp,i,j)
prev = s[j]
permute(i + 1 , "".join(temp))
def sortString(inputString):
tempArray = list (inputString)
tempArray.sort()
return "".join(tempArray)
s = "abca"
s = sortString(s)
permute( 0 , s)
print (f "Total distinct permutations = {total}" )
|
C#
using System;
using System.Collections.Generic;
class GFG {
static int total = 0;
static void permute( int i, string s)
{
if (i == (s.Length - 1)) {
Console.Write(Convert.ToString(s) + "\n" );
total++;
return ;
}
char prev = '*' ;
for ( int j = i; j < s.Length; j++) {
char [] temp = s.ToCharArray();
if (j > i && temp[i] == temp[j])
continue ;
if (prev != '*' && prev == s[j]) {
continue ;
}
temp = swap(temp, i, j);
prev = s[j];
permute(i + 1, new string (temp));
}
}
static char [] swap( char [] arr, int i, int j)
{
char temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
return arr;
}
static string sortString( string inputString)
{
char [] tempArray = inputString.ToCharArray();
Array.Sort(tempArray);
return new string (tempArray);
}
public static void Main( string [] args)
{
string s = "abca" ;
s = sortString(s);
permute(0, s);
Console.Write( "Total distinct permutations = "
+ total + "\n" );
}
}
|
Javascript
<script>
let total = 0;
function permute(i,s)
{
if (i == (s.length - 1))
{
document.write(s + "<br>" );
total++;
return ;
}
let prev = '*' ;
for (let j = i; j < s.length; j++)
{
let temp = s.split( "" );
if (j > i && temp[i] == temp[j])
continue ;
if (prev != '*' && prev == s[j])
{
continue ;
}
temp = swap(temp,i,j);
prev = s[j];
permute(i + 1, (temp).join( "" ));
}
}
function swap(arr,i,j)
{
let temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
return arr;
}
function sortString(inputString)
{
let tempArray = inputString.split( "" );
(tempArray).sort();
return (tempArray).join( "" );
}
let s = "abca" ;
s = sortString(s);
permute(0, s);
document.write( "Total distinct permutations = " +
total + "<br>" );
</script>
|
Outputaabc
aacb
abac
abca
acba
acab
baac
baca
bcaa
caba
caab
cbaa
Total distinct permutations = 12
Time complexity: O(N*N!)