How to change the values of a multidimensional array in a range? - java

I want to change the values of a 2d array from a given starting position (rowPos and colPos) for a certain amount of rows and columns.
So far I have the code below:
int[][] block = new int[10][10];
int rowPos = 3, colPos = 3;
int rows = 4, columns = 4;
for (int i = rowPos; i < rows; i++)
for (int j = colPos; j < columns; j++)
block[i][j] = 1;
for (int[] x : block) {
for (int y : x)
System.out.print(y + " ");
System.out.println();
}
However this gives me the following output:
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 1 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
It is only setting the value at rowPos and colPos. This is my expected output:
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 1 1 1 1 0 0 0
0 0 0 1 1 1 1 0 0 0
0 0 0 1 1 1 1 0 0 0
0 0 0 1 1 1 1 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
I feel like I'm close but missing something small, please help me!

Change the loops to this:
for (int i = rowPos; i < rows + rowPos; i++)
for (int j = colPos; j < columns + colPos; j++)
block[i][j] = 1;
In your code, you let i and j start at the row and column you want to begin changing the values. That's fine, but it also means your condition doesn't work anymore. Let me show you what happens:
You declare i and set it's value to 3.
You check if i (3) is less than rows (4). Success!
You declare j and set it's value to 3.
You check if j (3) is less than columns (4). Success!
You set block[3][3] to 1.
j is incremented by 1 and is now 4.
You check if j (4) is less than columns (4). Fail!
i is incremented by 1 and is now 4.
You check if i (4) is less than rows (4). Fail!
You print the array's contents.
The problem is that because you start i and j at values greater than 0, you need to keep that in mind when performing the check.

Related

Am I using Scanner and File class correctly?

I am creating a Game of Life program that accepts user input patterns, using java.util.Scanner and java.io.File
The main issue is that I cannot seem to get the program to read the pattern.txt file...
I do not see any issue, the pattern.txt is in the same folder as the .java and .class files when I compile them.
Am I using File and Scanner correctly?
I've tried reordering the import statements, changing try & catch structure, and creating a new File(//..Path/../pattern.txt) to directly call the file via the relative path
1.txt is the pattern file:
20 20
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 1 1 1 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 1 0 1 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 1 1 1 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 1 1 1 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 1 1 1 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 1 1 1 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 1 0 1 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 1 1 1 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
`
import java.util.Scanner;
import java.io.File;
import java.io.FileNotFoundException;
public static void main(String [] args) throws FileNotFoundException{
String inputFileName = "1.txt"; // Directly setting relative path
int [][] initStates = getInitialStates(inputFileName);
Grid gd = new Grid(initStates);
gd.display();
gd.getStats();
gd.run();
}
public static int [][] getInitialStates(String fileName) {
try {
File file = new File(fileName);
// checks to see if file was created
// if (file.exists())
// System.out.println("FILE EXISTS");
// else
// System.out.println("FILENOTFOUDN");
Scanner input = new Scanner(file); // Create scanner to read file
int[][] states = null;
int rows = input.nextInt(); // get rows and cols values from first values of text file
int cols = input.nextInt();
// states = new int[rows][cols]; // Create 2d array w/ rows and cols
states = new int[rows][cols];
// for (int i = 0; i < rows; i++) {
// states[i] = new int[cols];
// }
// Read initial states from the input file
for (int i = 0; i < states.length; i++) {
for (int j = 0; j < states[0].length; j++) {
states[i][j] = input.nextInt();
}
}
return states;
} catch (FileNotFoundException e) {
e.printStackTrace();
return null;
}
// return states;
}
`
Error output is FileNotFoundException printing the stack trace:
java.io.FileNotFoundException: 1.txt (No such file or directory)
at java.base/java.io.FileInputStream.open0(Native Method)
at java.base/java.io.FileInputStream.open(FileInputStream.java:219)
at java.base/java.io.FileInputStream.<init>(FileInputStream.java:157)
at java.base/java.util.Scanner.<init>(Scanner.java:639)
at client.getInitialStates(client.java:67)
at client.main(client.java:24)
Exception in thread "main" java.lang.NullPointerException
at Grid.<init>(Grid.java:14)
at client.main(client.java:26)
I get the NullPointerException because the getInitialStates() method isn't returning the 2d array because it cannot read the file.
If as per comment a FileNotFoundException is thrown, it means that the working directory of your program (i.e. directory where java YourMainClassName is invoked) is different from location of the file you're trying to open by its name.
You can check the working directory:
System.out.println("Working Directory = " + System.getProperty("user.dir"));
As described in this answer: https://stackoverflow.com/a/7603444/1083697

Creating matrices Java

I have trouble creating a matrice for a game map design.
void prepareMatrix(int width, int height)
{
room = new int[height][width];
for(int i = 0; i < height; i++)
{
for(int j = 0; j < width; j++)
{
if(i < height/4)
{
room[i][j] = 2;
}
else if(j == 0 || j == --width)
{
room[i][j] = 1;
}
else if(i == --height)
{
room[i][j] = 1;
}
else
{
room[i][j] = 0;
}
}
}
}
I want to create something like this: (1- Wall1, 2- wall2, 0-floor)
2 2 2 2 2 2
2 2 2 2 2 2
1 0 0 0 0 1
1 0 0 0 0 1
1 0 0 0 0 1
1 1 1 1 1 1
And I get this:
2 2 2 2 2 2 2 2 2 2
2 2 2 2 2 2 2 2 2 2
1 0 0 0 0 1 0 0 0 0
1 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0
The matrice would be a blueprint for the map.
You are using --width and --height. It appears from the expected result that you want the 1's to go in the first and last columns and in the last row. As a commenter implied, --width does not just return the width minus one, it also reduces width by 1. You may want width - 1 and height - 1 instead.
Like M. Aroosi said, try to change the --width to width-1 and --height to height-1. You don't want to modify the value of a parameter. I think what is happening is that every time it goes through the loop, the values change for width and height.

Problems adding to two dimensional list in java

I don't understand why this cannot work, if anyone could help that would be great;
for(int i = 0; i < 10 ; i++){
lines = fileL[i];
for(int j = 0; j < lines.length(); j++){
enemySpawningL[i][j] = fileL[i].substring(j*2, 1);
}
}
where enemySpawning[][] has been set as a string and fileL is set as this;
private String[] fileL = {
"1 0 0 0 0 1 0 0 0 0 1 0 0 0 0 1 0 0 0 0 1",
"1 0 0 0 0 1 0 0 0 0 1 0 0 2 0 1 0 0 0 0 1 0 0 0 0 1 0 0 0 0 1 0 2 0 0 1 0 0 0 0 1 0 0 0 0 1",
"1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1 0 0 0 1",
"1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1 0 0 1",
"1 0 0 0 0 1 0 0 2 0 1 0 0 0 0 1 0 2 0 0 1 0 0 0 0 1 0 0 2 0 1 0 0 0 0 1 0 2 0 0 1 0 0 0 0 1 0 2",
"1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 0 0 1",
"1 0 3 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 3 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 3 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 3 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 3 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 3 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 3 0 1 0 2 0 1 0 0 0 1 0 2 0 1 0 3 0 1",
"1 0 0 0 2 0 0 0 1 0 0 0 3 0 0 0 1 0 0 0 2 0 0 0 1 0 0 0 0 0 0 0 1 0 0 0 3 0 0 0 1 0 0 0 0 0 0 0 1 0 0 0 2 0 0 0 1 0 0 0 0 0 0 0 1 0 0 0 3 0 0 0 1 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 1 0 0 0 2 0 0 0 1",
"2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3 0 2 0 0 3",
"2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 2",
};
(I tried using a textfile for it, but I didn't think there was a point cause it's not too important)
EDIT: I'm just trying to make the enemySpawning list be [line number][number in line]
EDIT2: Also the error I'm getting is java.lang.NullPointerException
The error is probably because you didn't initialize enemySpawningL.
String[][] enemySpawningL = new String[rowsNum][columnsNum];
And if I understand correctly what you are trying to do change your code to
for(int i = 0 ; i < 10 ; ++i) {
String[] digits = fileL[i].split(" ");
for(int j = 0 ; j < digits.length ; ++j) {
enemySpawningL[i][j] = digits[j];
}
}
That will give you one digit in every cell. Currently your substring() is wrong as the start point is bigger than the end point for j > 0 and if you change the order you insert string with several digits every time.
"1"
"1 0"
"1 0 0"
....
The problem is, as #guy mentioned, not initializing the array, but there is also another error in here:
enemySpawningL[i][j] = fileL[i].substring(j*2, 1);
Because 'j' can have maximal value of fileL[i] length, if you request index j*2, in half of the loop it will be out of bound. You are also using the substring method in incorrect way. How you want you loop to look like is:
for(int j = 0; j < lines.length(); j += 2){
enemySpawningL[i][j] = fileL[i].substring(j, j+1);
}
The j variable is now incremented by two every iteration (to skip spaces) and substring will return one character from position j of the string file[L]. Which is what you wanted.

Java JPG DCT coefficients alter by themselfs after I modify them

I have a program that changes the DCT coefficients of a JPG image.
This is the code that gives me the DCT coefficients
public int[] quantizeBlock(double inputData[][], int code) {
int outputData[] = new int[blockSize * blockSize];
int i, j;
int index;
index = 0;
for (i = 0; i < 8; i++) {
for (j = 0; j < 8; j++) {
// The second line results in significantly better compression.
outputData[index] = (int) (Math.round(inputData[i][j]
* (((double[]) (Divisors[code]))[index])));
// outputData[index] = (int)(((inputData[i][j] * (((double[])
// (Divisors[code]))[index])) + 16384.5) -16384);
index++;
}
}
return outputData;
}
This is a DCT matrix before modifications
-43 7 0 0 0 0 0 0
-8 1 2 -1 0 0 0 0
-1 -1 -1 1 0 0 0 0
-2 1 0 -1 0 0 0 0
6 0 0 0 0 0 0 0
-2 0 1 0 0 0 0 0
-1 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0
This is after the modifications
-42 8 0 0 0 0 0 0
-7 1 3 0 0 0 0 0
0 0 0 1 0 0 0 0
-1 1 0 0 0 0 0 0
7 0 0 0 0 0 0 0
-1 0 1 0 0 0 0 0
0 0 0 0 0 0 0 0
After I save the image using image Buffer,I use the created image to get back the modified DCT from it but all I get is:
-41 9 0 0 0 0 0 0
-6 1 4 0 0 0 0 0
0 0 0 1 0 0 0 0
0 1 0 0 0 0 0 0
8 0 0 0 0 0 0 0
0 0 1 0 0 0 0 0
0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0
I've seen a question where the user using a library in IOS did the same thing and had the same problem.Apparently the library recopressed the image and the hidden message was destroyed.
I don't know if this is the case for me.I use Image Buffer to create the image.
A couple things off the top that could be happening. The first is rounding errors. The JPEG process introduces small errors. All your values are one off. This could come from rounding.
The second is quantization. Your values may be quantized (divided). Your example does not indicate the compression stages that may be taking place in between your examples.

Cloning/Copying an Object

I am creating a connect 4 game in Java and i'm trying to make a deep copy of a custom object (The game Board), then modify that copy and add it to a list as part of the mini max algorithm.
This is the code i'm using for copying:
public void getPossibleBoards(Board board) {
for(int i = 0; i < 7; i++) {
if(!board.columns.get(i).isFull()) {
Board tmpBoard = board.copy(board);
tmpBoard.columns.get(i).addCounter(turn);
boardList.add(tmpBoard);
}
}
}
public Board copy(Board other) {
Board b = new Board(other);
b.columns = other.columns;
return b;
}
This takes the main board (passed as a parameter), loops through the columns on the board and if the column isn't full it creates a new board object and puts a counter in a empty column, then adds this new board object to a list for later use.
The problem is that when I copy the board, it keeps referencing the main board and modifying that, then each loop it adds a counter to a column without wiping the board clear first.
Expected output is: (Player 1 is human, player 2 is the computer)
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
2 0 0 0 0 0 1
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 2 0 0 0 0 1
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 2 0 0 0 1
And so on until the 7 loops are over.
Actual output:
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 2
2 2 2 2 2 2 1
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 0
0 0 0 0 0 0 2
2 2 2 2 2 2 1
and so on until the 7 loops are over.
EDIT:
I had problems with the solution below so I decided to try another way, but got the same result and I don't understand why.
I'm basically creating a new Board object, within the constructor i'm assigning new blank columns to it, then looping through the main_board to get the colours of the counters at each slot (Stored as integers in the Slot class), and altering the new Board respectively.
if(!board.columns.get(i).isFull()) {
Board tmpBoard = new Board();
for(int j = 0; j < 7; j++) {
for(int k = 0; k < 7; k++) {
tmpBoard.columns.get(j).slots.get(k).setColour(board.columns.get(j).slots.get(k).getColour());
}
}
}
Board constructor
public Board() {
for(int i = 0; i < 7; i++) {
columns.add(new Column());
}
}
EDIT: Nevermind, above solution worked, just me forgetting to add a new counter after the copy.
The line b.columns = other.columns; causes the problem since you are doing a reference assignment (i.e. its not doing a deep copy as you are expecting). You can copy that array by using System.arraycopy method.
I think in your case you are using an ArrayList to represent columns/rows if so, you can use:
Collections.copy(arrayList2,arrayList1);
or simply
new ArrayList<Integer>(oldList)
in order to create a copy.
Why does Board take another Board as a constructor parameter?
Your problem is that you don't copy the columns, you only do b.columns = other.columns in your copy method. If one of the two boards is changed both boards are affected. Create a new column instances when copying and also deep copy all elements in an column until you reach immutable objects or primitives.

Categories

Resources