I have the following code:
public void add (int value)
{
if (numElements == list.length)
System.out.println("Can't add, list is full");
else
{
int hold=0;
for (int j = 0; j < numElements; j++)
{
int temp = list[j];
if (temp <= value)
{
hold = j;
}
}
System.arraycopy(list,hold, list, hold+1 ,numElements-hold);
list[hold] = value;
for (int i = 0; i< list.length; i++)
System.out.print(list[i] + ", ");
System.out.println();
numElements++;
}
}
The purpose is to put an integer in an array at the correct spot smallest to largest(insertion sort).
When I run the following test code:
myList.add(100);
myList.add(50);
myList.add(200);
myList.add(25);
The resulting array is: [25,50,200,100]
When I debug it after each time the method is invoked the arrays are:
[100, 0, 0, 0, 0, 0, 0, 0, 0, 0]
[50, 100, 0, 0, 0, 0, 0, 0, 0, 0]
[50, 200, 100, 0, 0, 0, 0, 0, 0, 0]
[25, 50, 200, 100, 0, 0, 0, 0, 0, 0]
As you can see the error is happening when the 200 is trying to be put in.
I need some help fixing this...thanks!
The arraycopy() call is fine. The problem is that if the correct insertion point is after all elements in the list, your loop will not determine this.
You might try something like:
for(hold = 0; hold < numElements; ++hold) {
if(list[hold] > value) break;
}
Related
i am writing a program that will read the element in a convolute and the program will then multiple each element in the convolute with the kernel given. I will need to take the convolute array from other class as well as kernel.
But i am getting this Error message: Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: 6
The error will be specified in the comment section with capitalised sentence, which is in my second for loop
The classes (kernel and the convolute) will be provided down after my code.
Thank You!
public static void main(String[] args)
{
Kernel kernel = new Kernel();
Convolute convolute = new Convolute();
int[][] matrixA = convolute.MATRIX_A;
int[][] kernelVertical = kernel.VERTICAL;
int[][] resultArray = new int[4][4];
int tempMatrix = 0, sumMatrix = 0; // declare temporary matrix and sumMatrix to take all the sum of each product array
int matrixRowA = 0, matrixColumnA = 0; // declare variable for matrix row and column
int convoluteRowControl = 2, convoluteColumnControl = 2; // this variable is to control moving of the kernel through the convolute
while(convoluteRowControl < matrixA.length) // while loop stops when convoluteRowControl points to 6
{
for(int kernelRow = 0; kernelRow < kernelVertical.length; kernelRow++) // this loop will stop when kernelRow is 3
{
for(int kernelColumn = 0; kernelColumn < kernelVertical[kernelRow].length; kernelColumn++) // this loop will stop when kernelColumn is 3
{
tempMatrix = matrixA[matrixRowA][matrixColumnA] * kernelVertical[kernelRow][kernelColumn]; // ERROR IS HERE!!
sumMatrix += tempMatrix; // sum all of the matrix calculated
matrixColumnA++; // re-initialize matrixColumnA to move to the next column element in matrixA
}
matrixRowA++; // re-initialize matrixRowA to move to the next row element in matrixA
matrixColumnA = convoluteColumnControl - 2; // re-initialize matrixColumnA back to the original specified range
}
for(int row = 0; row < resultArray.length; row++) // this loop is used to store sumMatrix calculated in the above loop to each element of the array
{ // loop stops at 5
for(int column = 0; column < resultArray[row].length; column++)
{
resultArray[row][column] = sumMatrix; // store sumMatrix into each element of the array
}
}
++convoluteColumnControl; // re-initialize convoluteColumnControl so that the kernel can move to the next column
if(matrixColumnA < 5) // if kernel get to the last column of its size, reset the row and move to the next column again
{ // this will stop when kernel get to the final column of the convolute
matrixRowA = convoluteRowControl - 2; // reset row back to the the top kernel
matrixColumnA = convoluteColumnControl - 2; // set new starting limit for the column in the kernel
}
if(matrixColumnA == 5) // when matrixColumnA is 5 (which means the final column of the convolute) this IF is executed
{ // to set the new row for the kernel
++convoluteRowControl; // convolteRowControl increase by 1 to set a new row limit for the kernel in convolution
matrixRowA = convoluteRowControl - 2; // reset matrixRowA equivalent to the starting of the new kernel
}
}
}
public class Convolute
{
/*
* ARRAY_A contains a 6x6 matrix
*/
public static final int[][] MATRIX_A =
{
{10, 10, 10, 0, 0, 0},
{10, 10, 10, 0, 0, 0},
{10, 10, 10, 0, 0, 0},
{10, 10, 10, 0, 0, 0},
{10, 10, 10, 0, 0, 0},
{10, 10, 10, 0, 0, 0}
};
}
public class Kernel
{
/*
* HORIZONTAL - A kernel that detects horizontal lines.
*/
public static final int[][] HORIZONTAL =
{
{ 1, 1, 1},
{ 0, 0, 0},
{-1, -1, -1}
};
/*
* VERTICAL - A kernel that detects vertical lines.
*/
public static final int[][] VERTICAL =
{
{ 1, 0, -1},
{ 1, 0, -1},
{ 1, 0, -1}
};
}
Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 2 years ago.
Improve this question
I tried to put java list into a 2D array and Retrieve it from the JSP. But It wasn't success.I really need this done.. Support me if you can..I have put my codes below if you able to solve this I'm really appreciate that.
Update:
1st List is getting inserted to first row(I want it insert to first column). likewise other three lists inserted to other 3 rows instead of three columns.
Screenshot
Requirement :
Ex:-
Servlet Code.
Scanner scanner = new Scanner(Result);
List<String> cdLine = new ArrayList<String>();
List<Integer> wtc = new ArrayList<Integer>();
List<Integer> ncc = new ArrayList<Integer>();
List<Integer> ccpps = new ArrayList<Integer>();
ControlData controlData = new ControlData();
while(scanner.hasNextLine())
{
token1 = scanner.nextLine();
Wtcs = controlData.CtrlWeight(token1);
NC = controlData.NofConditions(token1);
Ccspps = controlData.previousComplex(token1);
cdLine.add(token1);
wtc.add(Ccspps);
ncc.add(NC);
ccpps.add(Wtcs);
#SuppressWarnings("rawtypes")
List arr[][]={{cdLine},{wtc},{ncc},{ccpps}};
}
#SuppressWarnings("rawtypes")
List arr[][]={{cdLine},{wtc},{ncc},{ccpps}};
scanner.close(); //close the scanner
RequestDispatcher dispatcher = getServletContext().getRequestDispatcher("/views/Control_structures.jsp");
request.setAttribute("Code_string", arr);
dispatcher.forward(request, response);
JSP code(using JSTL)
<c:forEach items="${Code_string}" var="post" varStatus="theCount">
<tbody>
<c:forEach items="${post}" var="value" varStatus="cell">
<tr>
<td scope="row">${theCount.count}</td>
<td>${value[0]}</td>
<td>${value[1]}</td>
<td>${value[2]}</td>
<td>${value[3]}</td>
<td>-</td>
</tr>
</c:forEach>
</tbody>
</c:forEach>
Update 2:
The 2D array that parsing to the JSP is like this. Hope this also need to be changed.
[[[public class Prime {, if, public static void main(String[]
args) {, , int low = 20, high = 50;, , while (low <
high) {, if(checkPrimeNumber(low)),
System.out.print(low + " ");, , ++low;, }, },
, public static boolean checkPrimeNumber(int num) {,
boolean flag = true;, , for(int i = 2; i <= num/2; ++i) {, ,
if(num % i == 0) {, flag = false;,
break;, }, }, , return flag;, }, }]],
[[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, 1, 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, 1, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0]]]
Output that I'm getting:
Thank you for your contribution.
There are two problems in your code:
A. With the following statement, you have created a 3-D structure which is an array of arrays of lists (Note that the List is an implementation of a dynamic 1-D array).
List arr[][]={{cdLine},{wtc},{ncc},{ccpps}};
You need an array of lists as given below:
List arr[]={cdLine,wtc,ncc,ccpps};
B. Do not place the above line inside the while loop. Do it just once after the while loop.
Apart from the points mentioned above, I would recommend you create a custom type instead of using raw type for the List array. Your custom type should be something like:
class MyType {
private List<String> cdLine = new ArrayList<String>();
private List<Integer> wtc = new ArrayList<Integer>();
private List<Integer> ncc = new ArrayList<Integer>();
private List<Integer> ccpps = new ArrayList<Integer>();
// ..constructors and getters and setters
}
Feel free to comment in case of any doubt/issue.
Note: the code below now reflects a working solution to the problem, I figured out the error.
I am trying to solve the simple problem of seeing if two nodes are connected. There are many solutions available that use a stack, and I can find much DFS code that is recursive, but non that use recursion and actually search for something and return true/ false. Any help would be appreciated. Thanks!
public static boolean routeBetween(int[][] graph, int startNode, int targetNode){
//where we can keep track of the visited vertices
int numberOfVertices = graph[0].length;
boolean[] visited = new boolean[numberOfVerticies];
//set all verticies to not visited
for(int i=0; i<visited.length; i++){
visited[i] = false;
}
return dfs(graph, visited, startNode, targetNode);
}
//where the actual dfs / recursion will happen, need this to keep track of
//visited
public static boolean dfs(int[][] graph, boolean[] visited, int startNode, int targetNode){
if(startNode == targetNode){
return true;
}
boolean foundNode = false;
if(!visited[startNode]){
visited[startNode] = true;
for(int i=0; i<graph[startNode].length;i++){
if(graph[startNode][i] ==1){
boolean currentChild = dfs(graph, visited, i, targetNode);
foundNode = currentChild || foundNode;
}
}
}
return foundNode;
}
Here is some code that I was using to test the above code:
int [][] matrix = {
{0, 1, 0, 0, 1, 1, 0, 0},
{1, 0, 0, 0, 0, 1, 1, 0},
{0, 0, 0, 1, 0, 0, 1, 0},
{0, 0, 1, 0, 0, 0, 0, 1},
{1, 0, 0, 0, 0, 1, 0, 0},
{1, 1, 0, 0, 1, 0, 0, 0},
{0, 1, 1, 0, 0, 0, 0, 1},
{0, 0, 0, 1, 0, 0, 1, 0}
};
System.out.println(GraphTools.routeBetween(matrix,0,1));
System.out.println(GraphTools.routeBetween(matrix,0,2));
I know that you have already figured out your issue, but sometimes it's worthwhile to see things worked out differently.
Since you are already keeping track of all the nodes that you visit in a boolean array, much of the work you do in your dfs method turns out to be redundant.
Another way to do it is as follows:
public static boolean dfs2(int[][] graph, boolean[] visited, int startNode, int targetNode) {
// if you have not visited the current node or the target node
// then visit this node and recursively explore its unvisited
//neighbors
if (!visited[startNode] && !visited[targetNode]) {
// visit the start node
visited[startNode] = true;
for (int i = 0; i < graph[startNode].length; i++) {
if (graph[startNode][i] == 1) {
return dfs(graph, visited, i, targetNode);
}
}
}
// otherwise we just return whether or not we have visited the
// target node and continue... If we have visited the target node
//we never go into the if-statement and we always return true
return visited[targetNode];
}
Your way is perfectly fine, I just wanted to offer an alternative solution. Hope this is helpful.
Quick question about Java 2D arrays; For my tile-based, top-down, 2D game (using swing) I use
a 2D array to create a map, like this
public int[][] createMap(){
return new int[][]{
{0, 0, 1, 3, 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, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
{0, 1, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0}};
}
I then use this in my gameComponents class where I draw the individual tiles unto the map, like this
protected void paintComponent(Graphics g){
super.paintComponent(g);
for (int row = 0; row < game.getMap().getWidth(); row++) {
for (int col = 0; col < game.getMap().getHeight(); col++) {
g.drawImage(tile.getTileImage().get(values()[game.getMap().getMapArray()[col][row]]), row * SIZE,
col * SIZE, this);
}
} }
(where size is the size of a tile)
This works, and it correctly draws each tile to the map as expected, however
this also causes a problem for collision detection. As you may have noted, while I do define the size between the tiles in draw method, it is not defined in the array at all. Which, as you'd imagine, raises issues when checking for collision as the drawn tile is not where the tile is in the 2D array (due to size offset).
This is the code I use for checking collision (of course, not working due to ArrayIndexOutofbounds).
public boolean collisionDetected(int xDirection, int yDirection, Game game, Player player){
for (int row = 0; row < game.getMap().getHeight() * 16; row ++){
for (int col = 0; col < game.getMap().getWidth() * 16; col++) {
System.out.println(col + xDirection + player.getPositionX());
if(game.getMap().getTile(col + xDirection + player.getPositionX() ,
row + yDirection + player.getPositionY()) == Tiles.GRASS ){
System.out.println("COLLISION DETECTED");
return true;
}
}
}
return false;
}
This method uses a method within the map class that returns the tile on that
specific coordinate, like this
public Tiles getTile(int col,int row){
return Tiles.values()[mapArray[col][row]];
}
And, of course, as the 2D array doesn't know of the size offset, it just throws
an arrayindexoutofbound.
My question is, is it possible to define a 2D map array with the size of a tile in-mind? I appreciate any help & input I can get, after-all I am here to learn!
Extra clarification: All the tiles are in an enum class (i.e AIR, GRASS, STONE...). Also worth noting that the player position is not bound by an array, I merely move it the amount of pixels I want it to move.
Thanks in advance!
This method uses a method within the map class that returns the tile on that specific coordinate, like this
public Tiles getTile(int col,int row){
return Tiles.values()[mapArray[col][row]];
}
So if you have a "coordinate", why do you call the parameters col/row?
If you have a 10x10 grid and each tile is 20 pixels then the grid size is 200x200 so you could have x/y values in the range 0-199
So if you have a coordinate of 25x35 you would simply calculate the row/col values as:
int row = 35 / 20;
int column = 25 / 20;
So your method would be something like :
public Tiles getTile(int x, int y)
{
int row = y / 20;
int column = x / 20;
return Tiles.values()[mapArray[row][column]];
}
I'm trying to concatenate many byte[] arrays into one, big array. I've found a solution utilizing ByteArrayOutputStream but I find results weird.
Code
List<SampleChunk> chunkList = new ArrayList<SampleChunk>();
public static byte[] getRaw(List<SampleChunk> list) throws FileNotFoundException {
ByteArrayOutputStream os = new ByteArrayOutputStream();
for (int i = 0; i < list.size(); i++) {
try {
os.write(list.get(i).getSamples());
} catch (IOException e) {
e.printStackTrace();
}
}
PrintWriter pr = new PrintWriter(new File("all.txt"));
pr.write(Arrays.toString(os.toByteArray()));
pr.close();
return os.toByteArray();
}
public void init(){
XuggleAudio xa = new XuggleAudio(new File("in.flv"));
PrintWriter pr = new PrintWriter(new File("chunks.txt"));
int count = 0;
SampleChunk sc = null;
while ((sc = xa.nextSampleChunk()) != null) {
pr.write(count++ + " " + Arrays.toString(sc.getSamples()) + "\n");
chunkList.add(sc);
}
getRaw(chunkList);
}
Problem is, that theese two output doesn't match. PrintWriter in init() method prints something like this
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,
2 [45, -1, -78, -4, 48, -1, -63, -4, 86,
3 [-38, -1, -55, -1, -62, -1, 85
4 ...
but output form getRaw() method contains only values from {-1,1,0,2}. Both output have the same size (os.toByteArray().length == list.size * (...)getSamples.lenght). What did I wrong? How to merge theese arrays right?