Shuffle the order of a 2D array in java - java

I'm creating my own memory game. Everything is going well so far. Just to let you know I'm using processing for Java. I have created a 2 dim PImage array. This is the code for filling the 2D array:
int g = 0;
for(int i = 0; i < 4; i++) {
for (int j = 0; j < 6; j++) {
if (j % 2 == 0) {
kaart[i][j] = loadImage( g + ".jpg" );
kaart[i][j].resize(vlakGrootte - 1, vlakGrootte - 1);
g++;
} else if (j % 2 == 1) {
kaart[i][j] = kaart[i][j-1];
}
}
}
I want the items in this array to be shuffled. It seems like java collections does not support to shuffle a 2D PImage array? Please correct me if im wrong.
Thanks to you all for helping me out.

1).Shuffle per-outter index :
YourType [][] kaart = new YourType [..][..];
List <YourType[]> list = (List<YourType[]> ) Arrays.asList(kaart);
Collections.shuffle(list);
kaart = (YourType[][]) list.toArray(new YourType[0][]);//convert back to a array
// just for checking
for(YourType[] k:kaart ){System.out.println(Arrays.toString(k));}
Replace YourType with the type of kaart.
2). Shuffle per-Outter+Inner index :
YourType[][] kaart = new YourType[..][..];
List<YourType[]> temp = new ArrayList<>();
for(YourType[] k:kaart ){
List <YourType> list = (List<YourType> ) Arrays.asList(k);
Collections.shuffle(list);//shuffle
YourType[] tempArray = (YourType[]) list.toArray();
temp.add(tempArray);
}
Collections.shuffle(temp);
kaart= (YourType[][]) temp.toArray(new YourType[0][]);//convert back to a array
// just for checking
for(YourType[] k:kaart ){System.out.println(Arrays.toString(k)); }
Replace YourType with the type of kaart.
3). Shuffle in The easiest way:
Just put all elements into a single List then call Collections.shuffle()

I would do this the same way you would deal those cards in real world. First you shuffle the deck:
ArrayList<Integer> pieces = new ArrayList<Integer>();
for (int i = 0; i < 4 * 6 / 2; i++) {
for (int j = 0; j < 2; j++) {
pieces.add(i);
}
}
Collections.shuffle(pieces);
Then you deal cards out of shuffled deck:
for(int i = 0; i < 4; i++) {
for (int j = 0; j < 6; j++) {
int g = pieces.remove(pieces.size()-1);
kaart[i][j] = loadImage( g + ".jpg" );
kaart[i][j].resize(vlakGrootte - 1, vlakGrootte - 1);
}
}

Related

How can i randomly select only one size in a two-dimensional array

String[] dizi_paragraf = dosya.split("\n");
for (int i = 0; i < dizi_paragraf.length; i++) {
String[] dizi_cumle = dizi_paragraf[i].split("\\.");
String[][] dizi_total = new String[dizi_paragraf.length][dizi_cumle.length];
int[][] dizi = new int[dizi_paragraf.length][dizi_cumle.length];
for (int j = 0; j < dizi_cumle.length; j++) {
dizi_total[i][j] = dizi_cumle[j];
dizi[i][j] = j;
System.out.println(dizi[i][j]);
}
}
Output:
0-0
0-1
1-0
1-1
1-2
2-0
3-0
3-1
4-0
4-1
5-0
5-1
5-2
5-3
I want this:
0-1
0-0
1-1
1-0
1-2
2-0
3-1
3-0
4-0
4-1
5-3
5-1
5-0
5-2
This is an example.
The value in j for each i changes randomly but until j length.
How can I do this? Have you any ideas?
For example, it should produce 0 or 1 for index 0. It should produce 0.1 or 2 for the 1st index. 2. You should take only 0 for indis. etc.
Just example. This can be change. I take this dynamically.
"i" must be constant. But j should be chosen randomly. for indice 0, j value: 0 and 1. This should be chosen randomly. for indice 1, j value: 0,1 and 2. This should be chosen randomly.
Try something as below:
String dosya = "Test cumle 1. CUmle 2.\nCumle 3 here. Next sentences. Last sentences.";
String[] dizi_paragraf = dosya.split("\n");
for (int i = 0; i < dizi_paragraf.length; i++) {
String[] dizi_cumle = dizi_paragraf[i].split("\\.");
String[][] dizi_total = new String[dizi_paragraf.length][dizi_cumle.length];
int[][] dizi = new int[dizi_paragraf.length][dizi_cumle.length];
List<Integer> jj = new ArrayList<>();
for (int j = 0; j < dizi_cumle.length; j++) {
jj.add(j);
}
Collections.shuffle(jj);
for (int j:jj) {
dizi_total[i][j] = dizi_cumle[j];
dizi[i][j] = j;
System.out.println("dizi[i][j] "+i+"-"+j);
}
}
The following solution does not use Collection.shuffle, just Random generator and arrays.
String[] dizi_paragraf = dosya.split("\n");
Random r = new Random();
for (int i = 0; i < dizi_paragraf.length; i++) {
String[] dizi_cumle = dizi_paragraf[i].split("\\.");
String[][] dizi_total = new String[dizi_paragraf.length][dizi_cumle.length];
int[][] dizi = new int[dizi_paragraf.length][dizi_cumle.length];
for (int j = 0; j < dizi_cumle.length; j++) {
int rNumber = 0;
boolean unique=false;
while (!unique){
unique=true;
rNumber = r.nextInt(dizi_cumle.length);
for (int jj = 0; jj < j; jj++) {
if (dizi[i][jj] == rNumber) {
unique = false;
break;
}
}
}
dizi_total[i][j] = dizi_cumle[j];
dizi[i][j] = rNumber;
System.out.println(i + "-" + dizi[i][j]);
}
}
For each j, the while loops starts with unique=false. It gets a random number r.nextInt(dizi_cumle.length) and sets the unique to true. Then it does a for loop on the dizi[][] array on the second dimension j, until it finds a previously set number. If the for loop ends without entering the if (dizi[i][jj] == rNumber) the unique is never set to false and the while exits. The number finally is set into the array.

Select element j in each column of an array in JAVA

I have the array
String[] test_=new String[] {"a b c d", "f g h i","j k l s gf"};
Now i want to create another array that has the elements
{"b d", "g i","k s"}
how can I do this?
I've managed to separate the array into rows using
String split_test[] = null;
for (int j = 0 ; j <= 2 ; j++) {
split_test=test_[j].split("\\s+");
System.out.println(Arrays.toString(split_test));
}
But now I want to separate each of those rows, I tried the solution of
How to Fill a 2d array with a 1d array? Combined with something like this split_test=test_[j].split("\s+"), but I haven't been able to solve it.
Also If I do what they say I have to make the array split_test have a number of specific columns, but what I want is the size of the columns of split_test depend of the array test_. For example in case I want to have an array with the elements {"b d", "g i", "k s gf"}
String[][] split_test = new String[3][2];
for(int row = 0; row < split_test.length; row++) {
for(int col = 0; col < split_test[row].length; col++) {
split_test[row][col] = test_[row];/*I still don't understand how to use the split within the for*/
System.out.println(split_test[row][col]);
}
}
Is there a simpler and more efficient way of doing this?
Thanks
Here is another one.
You can use the substring method of String class.
Or use indexes of the array returned by the split method.
String output[] = new String[test_.length];
String split_test[] = null;
for (int j = 0; j < test_.length(); j++) {
split_test = test_[j].split("\\s+");
// use direct index
// output2[j] = split_test[1] + " " + split_test[3];
// or based on length
output[j] = split_test[1] + " " + split_test[split_test.length - 2];
}
System.out.println(Arrays.toString(output));
Output:
b d
g i
k s
I have used a different approach that works as well. I noticed you only take the uneven indexes, hence my modulo approach:
String[] array = new String[] {"a b c d", "f g h i","j k l s gf"};
String[] result = new String[array.length];
for(int i = 0; i < array.length; i++) {
String subresult = "";
String[] array2 = array[i].split(" ");
for(int j = 0; j < array2.length; j++) {
if(j % 2 == 1)
subresult += array2[j] +" ";
}
result[i] = subresult.trim();
}
You should use a 2 dimentional array, you can create one by doing:
String[][] input=new String[][] {{"a","b","c","d"}, {"f","g","h","i"},{"j","k","l","s"}};
You can then do something like this to retrieve {{"b","d"}, {"g","i"},{"k","s"}}:
String[][] output = new String[input.length][2];
for(int i = 0; i<input.length; i++)
{
output[i] = new String[]{input[i][1],input[i][3]};
}
System.out.println(Arrays.deepToString(output));

JAVA Writing the diagonal of an 2-dimensional array into an 1-dimensional array

Want to write the diagonal of an 2-dimensional array (n*n Matrix) into an one-dimensional array.
1 2 3
4 5 6 => 1 5 9
7 8 9
public int[] getDiagonalFromArray(int[][] two_d_array){
int[] diagonal_array = new int[two_d_array[0].length];
int k=0;
for (int i = 0; i < two_d_array[0].length; i++) {
for (int j = 0; j < two_d_array[1].length; j++) {
for (int l = 0; l < two_d_array[0].length; l++) {
diagonal_array[k]=two_d_array[i][j];} //HERE SHOULD BE THE ERROR... HOW DO I CYCLE THROUGH THE 1dim "diagonal_array"?
}
}
return diagonal_array;
}
This method delivers wrong values.
This method of mine works, but just Prints the diagonale, instead of putting it into an 1dim array.
public void getDiagonal(int[][] two_d_array){
//int[] diagonal_array = new int[two_d_array[0].length];
for (int i = 0; i < two_d_array[0].length; i++) {
for (int j = 0; j < two_d_array[1].length; j++) {
if (i==j) System.out.print(two_d_array[i][j]+" ");
}
}
}
Where is the logical difference? I tried the if-clause on the first method, but it raises the "outofbound"-Exception.
Thanks in advance.
Why do you need more than one loop?
for (int i = 0; i < two_d_array[0].length; i++) {
diagonal_array[i]=two_d_array[i][i];
}
Seems to be enough to me.
If your matrix has the same width and height, this is a solution:
public int[] getDiagonal(int[][] two_d_array){
int[] diagonal_array = new int[two_d_array.length];
for (int i = 0; i < two_d_array.length; i++) {
diagonal_array[i] = two_d_array[i][i];
}
return diagonal_array;
Here, I consider principal diagonal elements to be the set of elements , where n & m are the number of rows and the number of columns (per row?) respectively.
Thus, the number of diagonal elements is never greater than min(numOfRows, numOfColumns).
And so, you can always try:
public int[] getDiagonalFromArray(int[][] 2DArray){
int[] diagonalArray = new int[Math.min(2DArray.length, 2DArray[0].length]);
int k=0;
for (int i = 0; i < 2DArray.length && k < diagonalArray.l length; ++i) {
for (int j = 0; j < 2DArray[i].length && k < diagonalArray.l length; ++j) {
if (i == j) {
diagonalArray[k++]=2DArray[i][j];
}
}
}
return diagonalArray;
}
Threw in some bounds checks for good measure.
Your input matrix must at be at least rectangular (square makes most sense), otherwise, the code will behave unreliably.
This is the same as #Andreas' answer, but I sacrifice performance and brevity here for the sake of understanding.

2D array and creating a mirror of an image

I'm supposed to create an image editor using 2D arrays. For this part I'm supposed to create code that creates a mirror of the image by flipping it left to right. Instead I'm flipping it upside down. What am I doing wrong?
public void mirror() {
// TODO Auto-generated method stub
int[] img;
int left = 0, right = data.length -1;
while (right >= left) {
img = data[left];
data[left++] = data[right];
data[right--] = img;
}
}
Multiple Problems:
1. You're using a 1D Array.
2. data.length on 1d array gives you number of rows.
3. Now when you use data.length for reversing, you end up revering rows instead of columns in 2d array.
Hence your logically incorrect output.
Use mirror method should be something like this -
public int[][] mirror(int[][] original) {
int[][] mirror = original;
for (int i=0; i<original.length; i++) {
original[i] = reverseArray(original[i]);
}
return mirror;
}
public int[] reverseArray(int[] array) {
for (i = 0; i < array.length / 2; i++) {
int temp = array[i];
array[i] = array[array.length - 1 - i];
array[array.length - 1 - i] = temp;
}
return array;
}
The problem is you were just mirroring the arrays that made up the matrix, rather than reversing the order of the arrays. Assuming data was in fact a 2D array to begin with, this should work for you.
public void mirror() {
for (int i = 0; i < data.length; i++){
for (int j = 0; j < data[i].length/2; j++){
int temp = data[i][j];
data[i][j] = data[i][data[i].length-j-1];
data[i][data[i].length-j-1] = temp;
}
}
}
A more simple way than the other answers in my opinion:
int[][] mirrored = new int[data.length][data[0].length];
for (int i = 0; i < data.length; i++) {
for (int j = 0; j < data[i].length; j++) {
mirrored[i][data[i].length - j - 1] = data[i][j];
}
}

How divide 2d array into 1d array by one statement?

If I have:
int[] a = {1,2,3,4,5};
int[] b = {5,7,8,9};
int[][] array2d ={a,b};
I can divide array2d into 2 1d array by:
int[] A = new int[array2d[0].length];
int[] B = new int[array2d[1].length];
for(int i = 0; i < array2d.lenght; i++){
A[i] = array2d[i][0];
B[i] = array2d[i][1];
}
but can it be done by one statement?
For example if I have:
int[][] array2dx = new int[2][1000];
I can do easy:
int[] Ax = array2dx[0];
int[] Bx = array2dy[1];
So I am look for something similar (dividing into 2 arrays) for array int[1000][2];
but can it be done by one statement?
Not with any built-in methods that I'm aware of. It sounds like you basically want to write a transpose method though:
static int[][] transpose(int[][] input) {
// TODO: Validation. Detect empty and non-rectangular arrays.
int[][] ret = new int[input[0].length][];
for (int i = 0; i < ret.length; i++) {
ret[i] = new int[input.length];
}
for (int i = 0; i < input.length; i++) {
for (int j = 0; i < ret.length; j++) {
ret[j][i] = input[i][j];
}
}
return ret;
}
Once you've transposed an int[1000][2] into an int[2][1000] you can get the two int[1000] arrays out simply, as you've already shown.

Categories