Java: Another way of generating permutations? [duplicate] - java

This question already has answers here:
Generating all permutations of a given string
(57 answers)
Closed 6 years ago.
I have the following code that will generate the permutations of an entered string, but is it possible for it to be changed so that there is no use of the for loop, just recursion?
public static void findPermutations (String beginningString, String endingString) {
if (endingString.length() <= 1)
System.out.println(beginningString + endingString);
else
for (int i = 0; i < endingString.length(); i++) {
try {
String newString = endingString.substring(0, i) + endingString.substring(i + 1);
permuteString(beginningString + endingString.charAt(i), newString);
} catch (StringIndexOutOfBoundsException exception) {
exception.printStackTrace();
}
}
}

Here is an answer that i found somewhere else so no credit to me. Can't find question again though
public class Permutations {
// print N! permutation of the characters of the string s (in order)
public static void perm1(String s) { perm1("", s); }
private static void perm1(String prefix, String s)
{
int N = s.length();
if (N == 0)
{
System.out.println(prefix);
}
else {
for (int i = 0; i < N; i++)
perm1(prefix + s.charAt(i), s.substring(0, i) + s.substring(i+1, N));
}
}
// print N! permutation of the elements of array a (not in order)
public static void perm2(String s) {
int N = s.length();
char[] a = new char[N];
for (int i = 0; i < N; i++)
a[i] = s.charAt(i);
perm2(a, N);
}
private static void perm2(char[] a, int n) {
if (n == 1) {
if(new String(a).contains("ncl-"))
System.out.println(a);
return;
}
for (int i = 0; i < n; i++) {
swap(a, i, n-1);
perm2(a, n-1);
swap(a, i, n-1);
}
}
// swap the characters at indices i and j
private static void swap(char[] a, int i, int j) {
char c = a[i];
a[i] = a[j];
a[j] = c;
}
public static void main(String[] args) throws IOException {
//String word = "nst n-eitoira cp2vmamoocnla1e k nfto-k7re id6";
String word = "doggy";
perm1(word);
System.out.println();
perm2(word);
}
}

Related

Quicksort by length of String in Array

I have strings scanned from the user. Next step is to sort array by the length of text, I don't know what I'm doing wrong, sometimes it's working.
public static void quickSort(String[] subtitles, int start, int end) {
int i = start;
int j = end;
if (j - i >= 1) {
String pivot = subtitles[i];
while (j > 1) {
while (subtitles[i].compareTo(pivot) <= 0 && i < end && j > i)
i++;
while (subtitles[j].compareTo(pivot) >= 0 && j > start && j >= i)
j--;
if (j > i)
swap(subtitles, i, j);
}
swap(subtitles, start, j);
quickSort(subtitles, start, j - 1);
quickSort(subtitles, j + 1, end);
} else
return;
}
public static void swap(String[] a, int i, int j) {
String tmp = a[i];
a[i] = a[j];
a[j] = tmp;
}
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
int amountStrings = 3;
String[] subtitles = new String[amountStrings];
System.out.println("insert ");
for (int i = 0; i < amountStrings; i++) {
subtitles[i] = scan.next();
}
System.out.println("--------");
quickSort(subtitles, 0, subtitles.length - 1);
for (int i = 0; i < subtitles.length; i++) {
System.out.print(subtitles[i] + " ");
}
Incorrect:
In:
asdzxc asd zxc
Out:
asd asdzxc zxc
Correct:
In:
sdf sdfsfwer s
Out:
s sdf sdfsfwer
Ok, I reviewed your code and made two new methods. One sorts the array alphabetically and one sorts by counting the number of letters in each word of the array. It is up to you what methods fits you well.
Tested and working.
import java.util.Arrays;
import java.util.Comparator;
import java.util.Scanner;
public class Subtitles {
public static void sortAlfabetical(String x[]) {
int j;
boolean found = true; // will determine when the sort is finished
String temp;
while (found) {
found = false;
for (j = 0; j < x.length - 1; j++) {
if (x[j].compareToIgnoreCase(x[j + 1]) > 0) { // ascending sort
temp = x[j];
x[j] = x[j + 1]; // swap
x[j + 1] = temp;
found = true;
}
}
}
for (int i = 0; i < x.length; i++) {
System.out.print(x[i] + " ");
}
}
public static void compare(String[] arrayOne) {
Arrays.sort(arrayOne, new Comparator<String>() {
#Override
public int compare(String o1, String o2) {
return o1.length() - o2.length();
}
});
for (String s : arrayOne) {
System.out.print(s + " ");
}
}
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
int amountStrings = 3;
String[] subtitles = new String[amountStrings];
System.out.println("insert ");
for (int i = 0; i < amountStrings; i++) {
subtitles[i] = scan.next();
}
System.out.println("--------");
System.out.print("Sorting alphabetical: ");
sortAlfabetical(subtitles);
System.out.println();
System.out.println("===========================");
System.out.print("Sorting by word length: ");
compare(subtitles);
}
}

generating different distinct permutation of fixed length(L)

I am writing a program to generate different permutation of an array with fixed length of 3.
The main problem I am facing is that it always generate dublicate permutation, How can i fix it without using Java set<>.
public class generatingCombination {
public static void main(String[] args) {
String s="ABCDEF";
printArray(s,0,new char[3], new boolean[s.length()]);
}
static void printArray(String s,int x,char []arr, boolean [] used){
if(x==3){
System.out.println(Arrays.toString(arr));
return;
}
else
{
for( int i=0;i<s.length();i++){
if(used[i]) continue;
arr[x]=s.charAt(i);
used[i]=true;
printArray(s, x+1, arr,used);
used[i]=false;
printArray(s, x+1, arr,used);
}
}
}
}
If you're only interested in permutations of length 3, then why not just:
public static void main(String[] args) {
String s = "ABCDEF";
for (int i = 0; i < s.length(); i++) {
for (int j = 0; j < s.length(); j++) {
if (j == i) {
continue;
}
for (int k = 0; k < s.length(); k++) {
if (k == i || k == j) {
continue;
}
System.out.println(Arrays.toString(new char[] { s.charAt(i), s.charAt(j), s.charAt(k)}));
}
}
}
}

How do I simplify these For-loops to save lines of code? [closed]

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 8 years ago.
Improve this question
The output of the code displays the following:
The code below seems pretty funky to me, even as a newbie. I imagine the code can be done more efficiently or at least lines of code can be saved without having to whip out so many loops.
If anyone can provide a cleaner solution, thanks in advance.
public class diamond {
public static void main(String[] args) {
for (int c=1; c<=10; c++) {
for (int d=1; d<=11-c; d++) {
System.out.print("*");
}
for (int e=2; e<c*2; e++) {
System.out.print(" ");
}
for (int i=1; i<=11-c; i++) {
System.out.print("*");
}
System.out.println();
}
for (int f=2; f<=10; f++) {
for (int g=1; g<=f; g++) {
System.out.print("*");
}
for (int h=2; h<22-f*2; h++) {
System.out.print(" ");
}
for (int j=1; j<=f; j++) {
System.out.print("*");
}
System.out.println();
}
}
}
The key is to notice repetitive patterns in your code and factor it out.
You could use a helper method to print a series of N characters:
public static void printNTimes(char value, int n) {
for (int i = 0; i < n; i++) {
System.out.print(value);
}
}
You can generalize the approach by using constants for the characters involved and the size of the diamond.
private static final char OuterChar = '*';
private static final char InnerChar = ' ';
private static final int Size = 10;
And add another helper method to print a row with N instances of one character on the outside, and 2 * (Size - N) characters on the inside:
private static void printRow(int n) {
printNTimes(OuterChar, n);
printNTimes(InnerChar, (Size - n) * 2);
printNTimes(OuterChar, n);
System.out.println();
}
Your code then becomes:
public class diamond
{
private static final char OuterChar = '*';
private static final char InnerChar = ' ';
private static final int Size = 10;
public static void printNTimes(char value, int n) {
for (int i = 0; i < n; i++) {
System.out.print(value);
}
}
private static void printRow(int n) {
printNTimes(OuterChar, n);
printNTimes(InnerChar, (Size - n) * 2);
printNTimes(OuterChar, n);
System.out.println();
}
public static void main(String[] args) {
for (int c = Size; c >= 1; c--) {
printRow(c);
}
for (int c = 2; c <= Size; c++) {
printRow(c);
}
}
}
int max=9,min=10;
for(int i=0;i<19;i++){
for(int j=0;j<20;j++){
if(j<min || j>max){
System.out.print("*");
}
else{
System.out.print(" ");
}
}
if(i<9){
min--;
max++;
}
else {
min++;
max--;
}
System.out.println();
}
I find this rather clear but YMMV.
for( int i = 10; i >= 1; i-- ){
String s = "**********".substring(0, i);
System.out.printf( "%-10s%10s\n", s, s );
}
for( int i = 1; i <= 10; i++ ){
String s = "**********".substring(0, i);
System.out.printf( "%-10s%10s\n", s, s );
}
Since this is repeated within the loop:
for (int d=1; d<=11-c; d++)
{
System.out.print("*");
}
you could write it to a variable and print it out twice. That would eliminate two loops. (one subloop in each outer loop)
I like to wrap logic in code that is easy to read and maintain so instead of doing loads of nested for-loops I wrote a class with descriptive methods.
package se.wederbrand.stackoverflow.diamond;
import java.util.ArrayList;
import java.util.List;
public class Diamond {
final List<String> rows;
public static void main(String[] args) {
System.out.println(new Diamond(10));
}
public Diamond(int width) {
this.rows = new ArrayList<>();
for (int stars = 1; stars <= width; stars++) {
// add all rows, start from the middle and build around it
addRows(stars, width);
}
}
private void addRows(int stars, int width) {
String row = generateRow(stars, width);
// add on top
this.rows.add(0, row);
if (stars > 1) {
// add to bottom
this.rows.add(row);
}
}
private String generateRow(int stars, int width) {
String row = "";
int spaces = width - stars;
for (int j = 0; j < stars; j++) {
row += "*";
}
for (int j = 0; j < spaces; j++) {
row += " ";
}
for (int j = 0; j < stars; j++) {
row += "*";
}
return row;
}
#Override
public String toString() {
String diamond = "";
for (String row : rows) {
diamond += row + System.lineSeparator();
}
return diamond;
}
}
This is an fun question as you get to see how everybody takes a different approach to solving it. This way just gives you a string that is "padded" with another character on the other side.
public static void main(String[] args) {
for (int c = 1; c <= 10; c++) {
System.out.println(printPadded(11 - c, '*', (c - 1) * 2, ' '));
}
for (int f = 10; f >= 2; f--) {
System.out.println(printPadded(11 - f, '*', (f - 1) * 2, ' '));
}
}
public static String printPadded(int padCount, char padCharacter,
int middleCount, char middleCharacter) {
StringBuilder s = new StringBuilder(padCount * 2 + middleCount);
for (int i = 0; i < padCount; i++) {
s.append(padCharacter);
}
for (int i = 0; i < middleCount; i++) {
s.append(middleCharacter);
}
for (int i = 0; i < padCount; i++) {
s.append(padCharacter);
}
return s.toString();
}

quicksort doesn't sort string with many letters

I've been trying to do a program that sorts characters from a string in alphabetical order.
It works with short words, but when I tried to input word such as : abcdefghijklmnopqrstuvwxyzabcdefghijklmnopqrstuvwxyz. It doesn't sort it at all.
Can somebody help me to improve my code?
Here is my code:
public class quicky{
public static void partition(char[] a,int low, int high){
int i = low;
int j = high;
char tmp;
int pivot = i+(j-i)/2;
while (i <= j) {
while(a[i] < a[pivot]){
i++;
}
while(a[j] > a[pivot]){
j--;
}
if(i <= j) {
tmp = a[i];
a[i] = a[j];
a[j] = tmp;
i++;
j--;
}
}
if(low < j){
partition(a, low, j);
}
if(i < high){
partition(a, i,high);
}
}
public Character[] toCharArray( String s )
{
int len = s.length();
Character[] array = new Character[len];
for (int i = 0; i < len ; i++) {
array[i] = new Character(s.charAt(i));
}
return array;
}
public static void main(String[] args)
{
String input = "abcdefghijklmnopqrstuvwxyzabcdefghijklmnopqrstuvwxyz";
String output = quicksort(input);
System.out.print(output);
}
public static String quicksort(String y)
{
int length = y.length();
int i = 0;
int j = length-1;
char[] a = y.toCharArray();
partition(a,i,j);
String x=new String(a);
return x;
}
}

Generating permutations of an int array using java -- error

I am writing a JAVA code to generate all permutations of a integer array.
Though I am getting the number of permutations right, the permutations themselves are not correct.
On running I obtain:
Input array Length
3
1
2
3
0Permutation is
1, 2, 3,
##########################
1Permutation is
1, 3, 2,
##########################
2Permutation is
3, 1, 2,
##########################
3Permutation is
3, 2, 1,
##########################
4Permutation is
1, 2, 3,
##########################
5Permutation is
1, 3, 2,
##########################
6 number of permutations obtained
BUILD SUCCESSFUL (total time: 3 seconds)
public class PermulteArray {
public static int counter = 0;
public static void Permute(int[] input, int startindex) {
int size = input.length;
if (size == startindex + 1) {
System.out.println(counter + "Permutation is");
for (int i = 0; i < size; i++) {
System.out.print(input[i] + ", ");
}
System.out.println();
System.out.println("##########################");
counter++;
} else {
for (int i = startindex; i < size; i++) {
int temp = input[i];
input[i] = input[startindex];
input[startindex] = temp;
Permute(input, startindex + 1);
}
}
}
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
System.out.println("Input array Length");
int arraylength = in.nextInt();
int[] input = new int[arraylength];
for (int i = 0; i < arraylength; i++) {
input[i] = in.nextInt();
}
counter = 0;
Permute(input, 0);
System.out.println(counter + " number of permutations obtained");
}
}
int temp=input[i];
input[i]=input[startindex];
input[startindex]=temp;
Permute(input, startindex+1);
You've swapped an element before calling Permute but you need to swap it back again afterwards to keep consistent positions of elements across iterations of the for-loop.
This is the best solution I have seen so far :
public static void main(String[] args) {
int[] a = { 1, 2, 3, 4, 5, 6 };
permute(0, a);
}
public static void permute(int start, int[] input) {
if (start == input.length) {
//System.out.println(input);
for (int x : input) {
System.out.print(x);
}
System.out.println("");
return;
}
for (int i = start; i < input.length; i++) {
// swapping
int temp = input[i];
input[i] = input[start];
input[start] = temp;
// swap(input[i], input[start]);
permute(start + 1, input);
// swap(input[i],input[start]);
int temp2 = input[i];
input[i] = input[start];
input[start] = temp2;
}
}
check this out
for (int i = startindex; i < input2.length; i++) {
char[] input = input2.clone();
char temp = input[i];
input[i] = input[startindex];
input[startindex] = temp;
permute(input, startindex + 1);
}
//This will give correct output
import java.util.Scanner;
public class PermulteArray {
public static int counter = 0;
public static void Permute(int[] input, int startindex) {
int size = input.length;
if (size == startindex + 1) {
System.out.println(counter + "Permutation is");
for (int i = 0; i < size; i++) {
System.out.print(input[i] + ", ");
}
System.out.println();
System.out.println("##########################");
counter++;
} else {
for (int i = startindex; i < size; i++) {
int temp = input[i];
input[i] = input[startindex];
input[startindex] = temp;
Permute(input, startindex + 1);
temp = input[i];
input[i] = input[startindex];
input[startindex] = temp;
}
}
}
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
System.out.println("Input array Length");
int arraylength = in.nextInt();
int[] input = new int[arraylength];
for (int i = 0; i < arraylength; i++) {
input[i] = in.nextInt();
}
counter = 0;
Permute(input, 0);
System.out.println(counter + " number of permutations obtained");
}
}
You can solve this using recursive calls.
https://github.com/Pratiyush/Master/blob/master/Algorithm%20Tutorial/src/arrays/Permutations.java
public void swap(int[] arr, int i, int j)
{
int tmp = arr[i];
arr[i] = arr[j];
arr[j] = tmp;
}
public void permute(int[] arr, int i)
{
if (i == arr.length)
{
System.out.println(Arrays.toString(arr));
return;
}
for (int j = i; j < arr.length; j++)
{
swap(arr, i, j);
permute(arr, i + 1); // recurse call
swap(arr, i, j); // backtracking
}
}
public static void main(String[] args) {
Permutations permutations = new Permutations();
int[] arr = {1, 2, 3,4};
permutations.permute(arr, 0);
}
Also, other approaches are available in
http://www.programcreek.com/2013/02/leetcode-permutations-java/
http://www.programcreek.com/2013/02/leetcode-permutations-ii-java/
public class PermuteArray {
public static void permute(char[] input2, int startindex) {
if (input2.length == startindex) {
displayArray(input2);
} else {
for (int i = startindex; i < input2.length; i++) {
char[] input = input2.clone();
char temp = input[i];
input[i] = input[startindex];
input[startindex] = temp;
permute(input, startindex + 1);
}
}
}
private static void displayArray(char[] input) {
for (int i = 0; i < input.length; i++) {
System.out.print(input[i] + "; ");
}
System.out.println();
}
public static void main(String[] args) {
char[] input = { 'a', 'b', 'c', 'd'};
permute(input, 0);
}
}
import java.util.ArrayList;
public class RecursivePermGen {
void permGen(int n, int m, ArrayList<Integer> cur) {
if(m == 0) {
System.out.println(cur);
return;
}
for(int i = 1; i <= n; i++) {
cur.add(0, i);
permGen(n, m-1, cur);
cur.remove(0);
}
}
public static void main(String[] args) {
RecursivePermGen pg = new RecursivePermGen();
ArrayList<Integer> cur = new ArrayList<Integer>();
pg.permGen(2, 2, cur);
}
}
I have simple answer for this question, you can try with this.
public class PermutationOfString {
public static void main(String[] args) {
permutation("123");
}
private static void permutation(String string) {
printPermutation(string, "");
}
private static void printPermutation(String string, String permutation) {
if (string.length() == 0) {
System.out.println(permutation);
return;
}
for (int i = 0; i < string.length(); i++) {
char toAppendToPermutation = string.charAt(i);
String remaining = string.substring(0, i) + string.substring(i + 1);
printPermutation(remaining, permutation + toAppendToPermutation);
}
}
}
A solution i have used several times (mostly for testing purposes) is in the following gist. It is based on the well-known algorithm to generate permutations in lexicographic order (no recursion):
/**
* Compute next (in lexicographic order) permutation and advance to it.
*
* Find greater index i for which a j exists, such that:
* j > i and a[i] < a[j] (i.e. the 1st non-inversion).
* For those j satisfying the above, we pick the greatest.
* The next permutation is provided by swapping
* items at i,j and reversing the range a[i+1..n]
*/
void advanceToNext() {
// The array `current` is the permutation we start from
// Find i when 1st non-inversion happens
int i = n - 2;
while (i >= 0 && current[i] >= current[i + 1])
--i;
if (i < 0) {
// No next permutation exists (current is fully reversed)
current = null;
return;
}
// Find greater j for given i for 1st non-inversion
int j = n - 1;
while (current[j] <= current[i])
--j;
// Note: The range a[i+1..n] (after swap) is reverse sorted
swap(current, i, j); // swap current[i] <-> current[j]
reverse(current, i + 1, n); // reverse range [i+1..n]
}
A complete solution (in the form of a class) lies here:
https://gist.github.com/drmalex07/345339117fef6ca47ca97add4175011f

Categories