ArrayList<int[]> displaying last array only - java

I'm trying to write a "Mastermind" AI program and at the moment I'm trying to implement a naive AI which searches all possible 1296 combination of 4 pegs with 6 colours.
I have written up the following for loop to print out all combinations:
int compguess[] = new int[4];
int a, b, c, d;
ArrayList<int[]> combination = new ArrayList<int[]>();
for (int z = 0; z < 6; z++) {
for (int x = 0; x < 6; x++) {
for (int i = 0; i < 6; i++) {
for (int k = 0; k < 6; k++) {
a = z;
b = x;
c = i;
d = k;
compguess[0] = a;
compguess[1] = b;
compguess[2] = c;
compguess[3] = d;
combination.add(compguess);
When I run this code with System.out.println("combination" + Arrays.toString(combination.get(k))); at the end. This displays the combinations properly, however when I try to do the following:
for(int i=0; i< height; i++){
int[] temp = combination.get(i);
for(int j = 0; j < 4 ; j++){
state[i][j] = temp[j];
}
guess.addActionListener(this);
}
It only displays the last element (4,4,4,4) 40 times, instead I want it to be (0,0,0,0), (0,0,0,1), (0,0,0,2), (0,0,0,3), (0,0,0,4), (0,0,0,5), (0,0,1,0), (0,0,1,1), (0,0,1,2), (0,0,1,3) only 10 which is the size of the height

The problem is that you are using the same array every time, causing a change to one of them to change all, as they are, in fact, the same. Just reinitialize the array in the innermost for loop:
for (int z = 0; z < 6; z++) {
for (int x = 0; x < 6; x++) {
for (int i = 0; i < 6; i++) {
for (int k = 0; k < 6; k++) {
compguess = new int[4];
// rest of your code

Related

Java - Create a list of an array of fixed 40 elements

Sorry if there is a similar question in here, but I have a bit of trouble creating a list (unfixed dimension) of another list or array of fixed dimension (40 elements in this case).
So far I have created a class with a method to add values(string) at a specific position.
public class t_Info_Loan_Class {
private String[] t_Info_Loan;
t_Info_Loan_Class() {
t_Info_Loan = new String[40];
}
private void add(String s, int j) {
t_Info_Loan[j] = s;
}
};
Then I tried a simple addition:
t_Info_Loan_Class[] t_Info_Loan_Tab = new t_Info_Loan_Class[40];
for (int i = 0; i < 2; i++)
t_Info_Loan_Tab[i] = new t_Info_Loan_Class();
for(int j = 0; j < 40; j++)
t_Info_Loan_Tab[0].add("S", j);
for(int j = 0; j < 40; j++)
t_Info_Loan_Tab[1].add("D", j);
for(int i = 0; i < 2; i++) {
for(int j = 0; j < 40; j++)
System.out.print(t_Info_Loan_Tab[i].t_Info_Loan[j] + " ");
System.out.println();
}
From this, I get a NullPointerException.
My intention is to generate:
S S S ... S (40 times)
D D D ... D (40 times)
Thanks!
You are initializing the array of t_Info_Loan_Class, but you are not initializing the objects themselves.
Before calling any member method, you should create your instances
for (int i = 0; i < 40; i++)
t_Info_Loan_Tab[i] = new t_Info_Loan_Tab("string");

optimization for ikj algorithm (matrix multiplication)

Creating a custom matrix class I implemented multiplication with ikj algorithm and now I'm trying to optimize it. The problem is that the version that should work better is about 5 times slower and I can't understand why.
This is the Matrix class with the "basic" algorithm:
class Matrix {
private double[][] m; // matrix
private int rows;
private int cols;
// other stuff...
// does some checks and returns requested matrix value
// I know this will slow down computation, but it's not the relevant part
public double get(int row, int col) {
if (row >= rows || col >= cols)
throw new IndexOutOfBoundsException(); // to catch block
else
return m[startRow + row][startCol + col];
}
public Matrix multiply(Matrix other) {
int n = rows;
int m = cols;
int p = other.cols;
double[][] prod = new double[n][p];
for (int i = 0; i < n; i++)
for (int k = 0; k < m; k++)
for (int j = 0; j < p; j++)
prod[i][j] += get(i,k) * other.get(k,j);
return new Matrix(prod);
}
}
And this is the modified algorithm:
public Matrix multiplyOpt(Matrix other) {
int n = rows;
int m = cols;
int p = other.cols;
double[][] prod = new double[n][p];
for (int i = 0; i < n; i++) {
for (int k = 0; k < m; k++) {
double aik = get(i,k);
for (int j = 0; j < p; j++) {
prod[i][j] += aik * other.get(k,j);
}
}
}
return new Matrix(prod);
}
My though was that moving that get call outside the loop it will be called n x m times instead of n x m x p.
These are the results of a random matrix multiplication (exception is never thrown):
multiply time = 0.599s
multiplyOpt time = 3.041s
Why this change makes it slower and not faster?
EDIT
Timings are obtained with:
double[][] m1 = new double[1000][750];
double[][] m2 = new double[750][1250];
for (int i = 0; i < m1.length; i++)
for (int j = 0; j < m1[0].length; j++)
m1[i][j] = new Double(Math.random());
for (int i = 0; i < m2.length; i++)
for (int j = 0; j < m2[0].length; j++)
m2[i][j] = new Double(Math.random());
Matrix a = new Matrix(m1);
Matrix b = new Matrix(m2);
long start = System.currentTimeMillis();
Matrix c = a.multiply(b);
long stop = System.currentTimeMillis();
double time = (stop - start) / 1000.0;
System.out.println("multiply time = "+time);
start = System.currentTimeMillis();
c = a.multiplyOpt(b);
stop = System.currentTimeMillis();
time = (stop - start) / 1000.0;
System.out.println("multiplyOpt time = "+time);

Complexity of LSD string sort (cfr. Algorithms by Sedgewick & Wayne)

In Algorithms by Sedgewick & Wayne (4th edition), they state that LSD string sort uses 7WN + 3R array accesses and extra space proportional to N+R to sort N items whose keys are W-character strings taken from an R-character alphabet.
They prove this by saying: "The method is W passes of key-indexed counting, except that the aux[] arrays is initialized just once.The total is immediate from the code and PROPOSITION A."
However, 2 pages back, they state that key-indexed counting uses 11N + 4R + 1 array accesses to stably sort N items between 0 and R-1.
How is this possible? Shouldn't LSD be N+W(4R + 10N) ?
Just to be clear, I'm not looking for the big-O notation.
Thanks in advance!
Code for key-indexed counting sort (according to Algorithms):
int N = a.length;
int[] count = new int[R+1];
for (int i = 0; i < N; i++)
count[a[i]+1]++;
for (int r = 0; r < R; r++)
count[r+1] += count[r];
for (int i = 0; i < N; i++)
aux[count[a[i]]++] = a[i];
for (int i = 0; i < N; i++)
a[i] = aux[i];
Code for LSD string sort
int N = a.length;
int R = 256;
String[] aux = new String[N];
for (int d = W-1; d >= 0; d--)
{
int[] count = new int[R+1];
for (int i = 0; i < N; i++)
count[a[i].charAt(d) + 1]++;
for (int r = 0; r < R; r++)
count[r+1] += count[r];
for (int i = 0; i < N; i++)
aux[count[a[i].charAt(d)]++] = a[i];
for (int i = 0; i < N; i++)
a[i] = aux[i];
}
}
}

ArrayIndexOutOfBoundsException Java Issue

So I have been working on this problem for a while now. I keep getting an ArrayIndexOutOfBoundsException but I am unable to locate where the issue lies. If someone could point me in the right direction, I would really appreciate it! Thanks!
public class Answer {
public static void main(String[] args){
double[] y = {23, 11.1, 50.4};
double[] x = {22.2, 46, 100.0};
Answer answer = new Answer();
answer.answer(y, x);
}
public static int answer(double[] y, double[] x) {
int result = 0;
double percent_1, percent_2;
double[] compareList_1 = new double[x.length];
double[] compareList_2 = new double[y.length];
// Calculate percent of first 2 x value array items with y
// all y values. Store the results in a seperate list.
for(int i = 0; i < x.length; i++){
percent_1 = compare(y[i], x[0]);
percent_2 = compare(y[i], x[1]);
compareList_1[i] = percent_1;
compareList_2[i] = percent_2;
}
// Compare those lists to find common number
// There you have your answer.
result = (int)compareLists(compareList_1, compareList_2);
return result;
}
// Calculates percentage from x and y values
public static double compare(double y, double x){
double result = 1 - (y/x);
return result;
}
// Finds common value in lists
public static double compareLists(double[] list_1, double[] list_2){
for(int i = 0; i < list_1.length + 1; i++){
for(int j = 0; j < list_2.length + 1; j++){
if(list_1[i] == list_2[j]){
return list_1[i];
}
}
}
// Just cus this shouldn't ever return.
return 100;
}
}
In your iteration (compareLists), you should use 'length' (not length + 1)
for(int i = 0; i < list_1.length; i++)
for(int j = 0; j < list_2.length; i++)
I think the problerm is in
for(int i = 0; i < list_1.length + 1; i++){
for(int j = 0; j < list_2.length + 1; j++){
i < list_1.length + 1 or j < list_2.length + 1 change it to
for(int i = 0; i < list_1.length; i++){
for(int j = 0; j < list_2.length ; j++){
remove +1 from each condition.For j < list_2.length + 1 the list_2.length will give you length of array ie lastIndex +1 and you are adding another +1 in it causing loop condition to be j<lastIndex +1 giving you index error on the last iteration of loop in the line if(list_1[i] == list_2[j]){ for list_2[j]
Also in answer method you declare array by
double[] compareList_1 = new double[x.length];
double[] compareList_2 = new double[y.length];
and in the loop you are iterating upto x.length if x.length is greater than y.length the you can get the Index error in compareList_2[i] = percent_2;(inside the loop) because its length is y.length.

Multiplying Muti-Dimensional Arrays

Been having a bit of trouble finishing this program involving two 2D arrays and multiplying them together. Now I was able to construct these arrays with set lengths and then using a number generator to create each array. As for a third array I was able to establish the length of the array, but when placing the three arrays into a method I am still having out of bounds issues.
public class arrayTest1{
public static void main ( String [] args){
int matrix1[][] = new int [5][2];
for (int i = 0; i < matrix1.length; i++)
for (int j = 0; j < matrix1[i].length; j++)
matrix1[i][j] = (int)(Math.random() * 1000);
System.out.println("The array 1 is: ");
for (int i = 0; i < matrix1.length; i++){
for (int j = 0; j < matrix1[i].length; j++){
System.out.print(matrix1[i][j]+" ");
}
System.out.println();
}
int matrix2[][] = new int [2][5];
for (int i = 0; i < matrix2.length; i++)
for (int j = 0; j < matrix2[i].length; j++)
matrix2[i][j] = (int)(Math.random() * 1000);
System.out.println("The array 2 is: ");
for (int i = 0; i < matrix2.length; i++){
for (int j = 0; j < matrix2[i].length; j++){
System.out.print(matrix2[i][j]+" ");
}
System.out.println();
}
int matrixSum[][] = new int [matrix1.length][matrix2[0].length];
matrixMulti(matrix1,matrix2,matrixSum);
System.out.println("The array mutliplied is: ");
for (int i = 0; i < matrixSum.length; i++){
for (int j = 0; j < matrixSum[i].length; j++){
System.out.print(matrixSum[i][j]+" ");
}
System.out.println();
}
}
public static void matrixMutli(int [][] m1, int [][] m2,int [][] totalMatrix){
for(int i = 0; i < m1.length; i++)
for(int j = 0; j < m2[0].length; j++)
for(int k = 0; k < totalMatrix.length; k++)
totalMatrix [i][j] += m1[i][k] * m2[k][j];
}
}
The ArrayIndexOutOfBounds is caused by the fact that your k variable goes from 0 to 5. It needs to go from 0 to 2. The problem is because of the line :
for(int k = 0; k < totalMatrix.length; k++)
The matrix totalMatrix is initialized with int matrixSum[][] = new int [matrix1.length][matrix2[0].length]; and matrix1.length is 5. So totalMatrix.length is 5.
To correct this you need to make sure that k is bounded by either matrix1[i].length or by matrix2.length. These two values need to be the same and you can choose either to be the bound for k.
So this is the code:
for(int i = 0; i < m1.length; i++)
for(int j = 0; j < m2[0].length; j++)
for(int k = 0; k < m2.length; k++)
totalMatrix [i][j] += m1[i][k] * m2[k][j];
Also consider adding code that checks whether m1[i].length == m2.length and throws an IllegalArgumentException if not. If you are still in trouble have a look at matrix multiplication.

Categories