Permutation of int[] array-adding to list - java

I have an algorithm to count each permutation of an int array. In this case - when I want to print these permutations - everything worked fine. But if I want to save the arrays to the arraylist, it saved the correct number of them, but it saved only the one same option. I know that the problem will be trivial, but I can't solve it. Thanks for your help.
I add to the method printArray, that it saved the printed Array to Arraylist afterwards.
Output of printArray is correct, but output of printList is like this:
1 2 3 4 5 6
(and this input is printed n!, which is correct but its only one permutation)
Here is my code:
public class Permute {
ArrayList<int[]> list;
public Permute() {
list=new ArrayList<>();
}
void printArray(int[] a) {
for (int i = 0; i < a.length; i++) {
System.out.print(a[i] + " ");
}
System.out.println("");
list.add(a);
}
void printList(){
for(int[] arr:list){
for(int item:arr){
System.out.print(item+" ");
}
System.out.println("");
}
}
void permute(int[] a, int k) {
if (k == a.length)
printArray(a);
else {
for (int i = k; i < a.length; i++) {
int temp = a[k];
a[k] = a[i];
a[i] = temp;
permute(a, k + 1);
temp = a[k];
a[k] = a[i];
a[i] = temp;
}
}
}
public static void main(String[] args) {
Permute p = new Permute();
int a[] = {1, 2, 3, 4, 5, 6};
p.permute(a, 0);
p.printList();
}
}

You are using the same array over and over again. You rearrange the items inside it.
It's fine when you print it. But when you come to save it in a list, what gets saved is the array reference, not the array contents.
So you enter a reference to the same object n! times into the the list. At the end of the operation, all those references still refer to the same object - and printing the list will print that same array again and again, with the most recent contents it has.
If you want to save the different contents each time, you'll need to make a copy of the array, and save that copy.
So, for example, you can use
list.add( Arrays.copyOf(a, a.length) );

Related

Java- How to find the permutation of all values in a 1 dimensional array and store them in a 2 dimensional array

I want to create a method in which, when given a 1 dimensional array, it'll find all permutations of the values in that array and make it into a 2 dimensional array. I found some algorithms online which finds all the permutations but only prints the values out in the form of a 2d array(example), but I couldn't quite modify the code to store the output into a single 2d array. Any help would be appreciated, thank you.
Here's how I would do it - adapted from the link in your question:
import java.util.List;
import java.util.LinkedList;
import java.util.Iterator;
// Java program to calculate all permutations using
// Heap's algorithm
class HeapAlgo
{
List<int[]> heapPermutation(int a[]) {
LinkedList<int[]> list = new LinkedList<int[]>();
heapPermutation(a, a.length, a.length, list);
return list;
}
//Generating permutation using Heap Algorithm
void heapPermutation(int a[], int size, int n, List<int[]> list)
{
// if size becomes 1 then adds the obtained
// permutation to the list
if (size == 1)
list.add(a.clone());
for (int i=0; i<size; i++)
{
heapPermutation(a, size-1, n, list);
// if size is odd, swap first and last
// element
if (size % 2 == 1)
{
int temp = a[0];
a[0] = a[size-1];
a[size-1] = temp;
}
// If size is even, swap ith and last
// element
else
{
int temp = a[i];
a[i] = a[size-1];
a[size-1] = temp;
}
}
}
// Driver code
public static void main(String args[])
{
HeapAlgo obj = new HeapAlgo();
int a[] = {1,2,3};
List<int[]> list = obj.heapPermutation(a);
for(Iterator<int[]> i = list.iterator(); i.hasNext();) {
int[] array = i.next();
for(int j = 0; j < array.length; j++) {
System.out.print(array[j] + " ");
}
System.out.println();
}
}
}
// Based on code contributed by Amit Khandelwal.
Another approach would be to create an array of int[] arrays. The length would be the factorial of the length of a. You could create a stack class that tracks the lowest empty index to add the next permutation to.

Changing 2D ArrayList code to 2D array code

I found this code online and it works well to permute through the given array and return all possible combinations of the numbers given. Does anyone know how to change this code to incorporate a 2D array instead?
public static ArrayList<ArrayList<Integer>> permute(int[] numbers) {
ArrayList<ArrayList<Integer>> permutations = new ArrayList<ArrayList<Integer>>();
permutations.add(new ArrayList<Integer>());
for ( int i = 0; i < numbers.length; i++ ) {
ArrayList<ArrayList<Integer>> current = new ArrayList<ArrayList<Integer>>();
for ( ArrayList<Integer> p : permutations ) {
for ( int j = 0, n = p.size() + 1; j < n; j++ ) {
ArrayList<Integer> temp = new ArrayList<Integer>(p);
temp.add(j, numbers[i]);
current.add(temp);
}
}
permutations = new ArrayList<ArrayList<Integer>>(current);
}
return permutations;
}
This is what I have attempted:
public static int[][] permute(int[] numbers){
int[][] permutations = new int[24][4];
permutations[0] = new int[4];
for ( int i = 0; i < numbers.length; i++ ) {
int[][] current = new int[24][4];
for ( int[] permutation : permutations ) {
for ( int j = 0; j < permutation.length; j++ ) {
permutation[j] = numbers[i];
int[] temp = new int[4];
current[i] = temp;
}
}
permutations = current;
}
return permutations;
}
However this returns all zeroes. I chose 24 and 4 because that is the size of the 2D array that I need.
Thanks
It’s not really that easy. The original code exploits the more dynamic behaviour of ArrayList, so a bit of hand coding will be necessary. There are many correct thoughts in your code. I tried to write an explanation of the issues I saw, but it became too long, so I decided to modify your code instead.
The original temp.add(j, numbers[i]); is the hardest part to do with arrays since it invloves pushing the elements to the right of position j one position to the right. In my version I create a temp array just once in the middle loop and shuffle one element at a time in the innermost loop.
public static int[][] permute(int[] numbers) {
// Follow the original here and create an array of just 1 array of length 0
int[][] permutations = new int[1][0];
for (int i = 0; i < numbers.length; i++) {
// insert numbers[i] into each possible position in each array already in permutations.
// create array with enough room: when before we had permutations.length arrays, we will now need:
int[][] current = new int[(permutations[0].length + 1) * permutations.length][];
int count = 0; // number of new permutations in current
for (int[] permutation : permutations) {
// insert numbers[i] into each of the permutation.length + 1 possible positions of permutation.
// to avoid too much shuffling, create a temp array
// and use it for all new permutations made from permutation.
int[] temp = Arrays.copyOf(permutation, permutation.length + 1);
for (int j = permutation.length; j > 0; j--) {
temp[j] = numbers[i];
// remember to make a copy of the temp array
current[count] = temp.clone();
count++;
// move element to make room for numbers[i] at next position to the left
temp[j] = temp[j - 1];
}
temp[0] = numbers[i];
current[count] = temp.clone();
count++;
}
assert count == current.length : "" + count + " != " + current.length;
permutations = current;
}
return permutations;
}
My trick with the temp array means I don’t get the permutations in the same order as in the origianl code. If this is a requirement, you may copy permutation into temp starting at index 1 and shuffle the opposite way in the loop. System.arraycopy() may do the initial copying.
The problem here is that you really need to implement properly the array version of the ArrayList.add(int,value) command. Which is to say you do an System.arraycopy() and push all the values after j, down one and then insert the value at j. You currently set the value. But, that overwrites the value of permutation[j], which should actually have been moved to permutations[j+1] already.
So where you do:
permutation[j] = numbers[i];
It should be:
System.arraycopy(permutation,j, permutations, j+1, permutations.length -j);
permutation[j] = numbers[i];
As the ArrayList.add(int,value) does that. You basically wrongly implemented it as .set().
Though personally I would scrap the code and go with something to dynamically make those values on the fly. A few more values and you're talking something prohibitive with regard to memory. It isn't hard to find the nth index of a permutation. Even without allocating any memory at all. (though you need a copy of the array if you're going to fiddle with such things without incurring oddities).
public static int[] permute(int[] values, long index) {
int[] returnvalues = Arrays.copyOf(values,values.length);
if (permutation(returnvalues, index)) return returnvalues;
else return null;
}
public static boolean permutation(int[] values, long index) {
return permutation(values, values.length, index);
}
private static boolean permutation(int[] values, int n, long index) {
if ((index == 0) || (n == 0)) return (index == 0);
int v = n-(int)(index % n);
int temp = values[n];
values[n] = values[v];
values[v] = temp;
return permutation(values,n-1,index/n);
}

Not all Array Elements Display When Using A Sort Method Logic

I have this code;
They both use system.out.println statements to print out the array elements. Originally I used a return statement with Arrays.toString(array) to show the array in the main method that worked fine. Now I could like to use print statements just to keep the level of complexity down. As you can see the output form sort is missing the last element in the array, this is because I am using array.length -1. however if I don't use array.length -1 I will get an .ArrayIndexOutOfBoundsException so anyone have a practical solution for this?
import java.util.Arrays;
public class SortMethod
{
static int[] array = {2,1,5,3,5};
public void sort(int[] arrays)
{
for(int i = 0;i < arrays.length - 1;i++ )
{
int store = 0;
if (arrays[i + 1 ] < arrays[i])
{
store = arrays[i];
arrays[i] = arrays[i + 1];
arrays[i + 1] = store;
}
System.out.print(arrays[i]);
}
System.out.println();
}
public void reverse (int[] arrays)
{
for (int i=arrays.length-1; i >=0; i--)
{
System.out.print(arrays[i]);
}
}
/**
* #param args
*/
public static void main(String[] args)
{
// TODO Auto-generated method stub
SortMethod sort = new SortMethod();
sort.sort(array);
sort.reverse(array);
}
}
Output;
From Sort:1235
From Reverse:55321
First of all your sorting method doesn't actually sort properly. You check values with the value immediately to its left, but what happens if you have a 4 at the end of the list?
{2,1,5,3,5,4}
would return the result:
123545
which is hardly sorted... You'll want to take every value you switch, and check it backwards as well making sure its not also smaller than the previous value. Right now you sort values to the right but never back to the left.
Also you can just do the sorting algorithm, and then iterate through the array afterwards and print the values then, rather than trying to print them in the middle of the sorting method:
public class TestCode
{
static int[] array = {2,1,5,3,5,4,9,1,99,7};
public void sort(int[] arrays)
{
for(int i = 0; i < arrays.length - 1 ;i++ )
{
int store = 0;
// Move larger values to the right
if (arrays[i] > arrays[i + 1])
{
store = arrays[i];
arrays[i] = arrays[i + 1];
arrays[i + 1] = store;
// Sort swapped smaller values to the left
for(int j = i; j > 1; j--)
{
if (arrays[j] < arrays[j - 1])
{
store = arrays[j];
arrays[j] = arrays[j - 1];
arrays[j - 1] = store;
}
}
}
}
for(int i = 0; i < array.length; i ++)
{
System.out.print(arrays[i] + " ");
}
System.out.println();
}
public void reverse (int[] arrays)
{
for (int i=arrays.length-1; i >=0; i--)
{
System.out.print(arrays[i] + " ");
}
}
/**
* #param args
*/
public static void main(String[] args)
{
// TODO Auto-generated method stub
TestCode sort = new TestCode();
sort.sort(array);
sort.reverse(array);
}
}
Gives the output:
1 1 2 3 4 5 5 7 9 99
99 9 7 5 5 4 3 2 1 1
SUMMARY:
When sorting arrays you'll need to iterate though the array array.length - 1 times to compare the values (you don't need to compare the last value with the value to its right because there isn't one).
When printing an array you need to iterate through it array.length times and print out each and every value. Your main problem is coming from trying to print out the array in your sorting algorithm which is only iterating through the array array.length - 1 times when you should probably just print the array outside of the sorting algorithm.
The last line of the public void sort(int[] arrays) function:
System.out.println();
should be
System.out.println(arrays[arrays.length - 1]);
as you want to print the hole array.
And for the record, the public void sort(int[] arrays) function does not actually sort an array. It is not what the sort should do just by one pass of checking and swapping of the neighboring elements.
For example, if the array is initialized as:
static int[] array = {2,1,5,3,5};
The resulting array of sort is: 53215, and the reversed array is 51235. Both are not the intended result.
In sort() you're iterating from 0 to arrays.length-1 (exclusive), so for arrays.length==5 variable i will take values: 0, 1, 2, 3
In reverse() you iterate from arrays.length-1 (inclusive) to 0 - i will take values: 4, 3, 2, 1, 0.
When you remove -1 part from arrays.length-1 in sort() you're getting ArrayOutOfBoundsException because you reference arrays[i + 1] which will be out of arrays range for i==4.
Change your sort method as follows :
public void sort(int[] arrays) {
// int i = 0;
for (int i = 0; i < arrays.length - 1; i++) {
int store = 0;
if (arrays[i + 1] < arrays[i]) {
store = arrays[i];
arrays[i] = arrays[i + 1];
arrays[i + 1] = store;
}
System.out.print(arrays[i]);
if (i + 1 == arrays.length - 1) {
System.out.print(arrays[i + 1]);
}
}
System.out.println();
}
Just added a new print statement
if (i + 1 == arrays.length - 1) {
System.out.print(arrays[i + 1]);
}
to print the last array element.
First of all I would like to point out that the code is incomplete. This is just half the sorting code, I can see you are trying to use bubble sort, but unfortunately the inner loop is missing.
Apart from this there is no problem in this code.
Could you just replace your sort method with the one given below? This will fix all the issues.
public void sort(int[] a){
int temp = 0;
for(int i = 0 ; i < a.length ; i++){
for(int j = 0 ; j< a.length - 1 ; j++){
if(a[j] > a[j+1]){
temp = a[j];
a[j] = a[j+1];
a[j+1]=temp;
}
}
}
printArray(a);
System.out.println();
}
public void printArray(int[] a){
for(int i = 0 ; i < a.length ; i++){
System.out.print(a[i]);
}
}
Also, I would recommend you to read about sorting techniques. You can always visit Sorting articles

I keep receiving a .class expected error [duplicate]

This question already has an answer here:
What does "error: '.class' expected" mean and how do I fix it
(1 answer)
Closed 2 years ago.
Here is what I'm supposed to do:
Write a program to read a 2-D array of 4x4. Then read the first element of the array and compare it with the third element of each column. Replace the smaller value with the larger values of the two. Create a method called swap to swap the values.
I'm not sure what I'm doing wrong and I'm just starting to learn arrays. My teacher is very conceptual and isn't very concrete on his definition so I'm having trouble with it. I keep receiving a .class expected error.
public class Array {
public static void main(String[] args) {
int num [][] = {{4, 6, 7, 2},
{5, 12, 9, 8},
{1, 0, 3, 10},
{5, 3, 14, 11}};
System.out.println("the array elements are:");
for(int i = 0; i < num.length; i++){
System.out.println();
for(int j = 0; j < num[i].length; j++)
System.out.print(num[i][j] + " ");
}
System.out.println("swaped elements are:");
for(int i = 0; i < num.length; i++){
System.out.println();
for(int j = 0; j < num[i].length; j++)
System.out.print(swap(num[][]) + " ");
}
}
public static void swap (int x[][]){
for(int i = 0; i < x.length; i++){
int temp = x[0][i];
if (x[0][i] > x[2][i] ){
x[2][i] = temp;
x[0][i] = x[2][i];
}
}
}
}
swap() doesn't return anything. Even if you did resolve the other issue (num[][] is a syntax error), you'd need to specify something to return from swap. Hint: probably the array you modified.
Write a program to read a 2-D array of 4x4.
I don't see you reading something. Just initializing it. Maybe you should read from stdin or from a file?
Then read the first element of the array and compare it with the third element of each column.
Replace the smaller value with the larger values of the two.
Create a method called swap to swap the values
As a swap method I would expect a method with 4 indexes for the 2 positions in the 2D-Array, where the values to swap are located.
public static void swap (int x[][], int i1, int i2, int j1, int j2) {
int temp = x[i1][j1];
x[i1][j1] = x[i2][j2];
x[i2][j2] = temp;
}
Have you heard about the simplified for-loop?
public static void show (int x[][]) {
for (int [] inner : x)
for (int i : inner)
System.out.print (i + " ");
}

Reversing elements of an array

Given an array a and two other int variables, k and temp, write a loop that reverses the elements of the array.
for (k = 0; k < a.length-1; k++) {
temp = a[k];
a[k] = a[a.length-1-k];
a[a.length-1-k] = temp;
}
This is not working. Any idea why?
E.g., for a = [0, 1, 2, 3, 4, 5] you'll switch 0 and 5 twice: when i == 0 and when i == 5. This double-switching will put both elements into their original positions: (0, 5) -> (5, 0) -> (0, 5).
Try to make your loop to go through half of array only: so each pair is switched once.
You need to stop your loop at a.length/2 (in the middle).
for(k=0;k<a.length/2;k++)
This should work for odd and even length arrays if this is integer division.
check this at my blog hope this going to help http://codeheaven.wordpress.com/
Here is the code from above link:
public class ArrayReversing {
public static void main(String a[]){
int arr[]={ 1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 };
int temp;
int as = arr.length;
int k = as – 1;
System.out.println(“Array Before Reversing”);
printArray(arr);//method used to print array on screen
ArrayReverse://using loops with title
for(int i = 0; i < arr.length/2 ; i++){
temp = arr[k];// swaping
arr[k] = arr[i];
arr[i] = temp;
k–;
}
System.out.println(“Array After Reversing”);
printArray(arr); // calling the method printArray to print the elements of array
}
static void printArray(int ar[]){
PrintArray:
for(int l:ar)
System.out.println(l);
}
}
Output:
Array Before Reversing
1
2
3
4
5
6
7
8
Array After Reversing
8
7
6
5
4
3
2
1
Use a Stack. A stack reverses the elements that are added to it. A stack can be described as First In, Last Out (FILO). "Push" adds the elements to the stack and "Pop" removes them.
public static int[] num1 = {1,2,3,4,5,6};
public static Stack<Integer> stack = new Stack<Integer>();
public static void main(String[] args) {
for(int i = 0; i < num1.length; i++){
stack.push(num1[i]);
}
for(int i = 0; i < num1.length; i++){
System.out.print(stack.pop());
}
}
Output:
654321
You are swapping elements from each end of the array... and iterating to the items you've already swapped... is that enough of a hint?
You might also want to look at the ArrayUtils.reverse method.
Here is an example using that method.
I know you cannot use it in this assignment. But you should be aware of this and use it whenever possible, say in your assignments, projects.
This will work
int a[] = {1,2,3,4,5};
for (int k = 0; k < a.length/2; k++) {
int temp = a[k];
a[k] = a[a.length-(1+k)];
a[a.length-(1+k)] = temp;
}
Try this will simply work:
public class ReverseArray{
public static void main(String[] args){
int[] a ={1,2,3,4,5};
for(int i=a.length-1;i>=0;i--){
System.out.print(a[i]);
}
}
}

Categories

Resources