Hy!
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException?
package studing;
public class Array {
public static void main(String[] args) {
int i;
int[] ar1 = new int[50];
for(i = 0; i < ar1.length; i++)
{
ar1[i] = i * 2 + 1;
System.out.print(ar1[i] + " ");
};
System.out.println();
for(i = ar1.length; i > -1; i--)
{
ar1[i] = i * 2 - 1;
System.out.print(ar1[i]);
};
}
}
After compiling the console displays:
1 3 5 7 9 11 13 15 17 19 21 23 25 27 29 31 33 35 37 39 41 43 45 47 49
51 53 55 57 59 61 63 65 67 69 71 73 75 77 79 81 83 85 87 89 91 93 95
97 99
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException:
50 at studing.Array.main(Array.java:18)
I want the output console in the second row 99 97 95 93 ...
Thanks in advance!
You start at ar1.length in your second loop, which is out of bounds.
To get it to work, you need to start at ar1.length-1, which is the maximum index for your array.
This is because arrays are 0-based in Java, as noted in the comments by #Maroun Maroun.
The first time the second for loop runs, i = 50 (the initial value), which is beyond the end of the array. This value is used before the index update of i--, so ar1[50] is out of bounds (proper indexes are 0 to 49 for a 50 element array).
Related
I've created a loop and random number generator that generates 100 numbers within the range of 1-100. I need to format these numbers so that it is 10 per line. I tried using printf and had a hard time. In addition, I have to find the average of all these numbers. The issue is I am unsure of how to do this because all the numbers are under the int variable 'randoms'. I can't add a single variable together and divide by 100.
public static void main(String[] args) {
Random rand = new Random();
int n = 100;
for (int i=1; i<=n; i++) {
int randoms = rand.nextInt(101);
}
}
You may print each number without a new line, and with spaces before to pad at 4-length string, and each 10 values, print a new line. For the average, use math : sum/count
Random rand = new Random();
int n = 100;
int total = 0;
for (int i = 1; i <= n; i++) {
int randoms = rand.nextInt(101);
total += randoms;
System.out.format("%4d", randoms);
if (i % 10 == 0) {
System.out.println();
}
}
System.out.println("AVG " + total / (double) n);
49 55 89 26 88 58 80 98 62 8
34 65 9 3 28 71 30 11 50 50
18 90 61 62 18 93 83 83 57 14
9 54 49 6 24 28 60 8 86 83
60 6 17 67 49 89 66 13 65 50
70 24 3 90 89 4 47 49 48 7
16 38 79 59 51 9 22 81 8 84
52 30 64 97 42 100 30 26 66 44
22 46 16 100 73 100 56 63 8 48
50 88 55 93 6 82 65 46 44 7
AVG 49.29
I wrote this code for a programming assignment given in a course about graphs on Coursera. enter code here. It passes on the test cases given in the question description but fails on one when submitted I'm new to graphs. Can some one help me find the error in this code?
import java.util.ArrayList;
import java.util.Scanner;
import java.util.Iterator;
public class Reachability {
private static boolean[] visited;
private static int reach(ArrayList<Integer>[] adj, int x, int y) {
if(x == y){
return 1;
}
visited[x] = true;
Iterator itr = adj[x].iterator();
while(itr.hasNext()){
x = (int)itr.next();
if(!visited[x]){
return reach(adj,x,y);
}
}
return 0;
}
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int n = scanner.nextInt();
int m = scanner.nextInt();
ArrayList<Integer>[] adj = (ArrayList<Integer>[])new ArrayList[n];
for (int i = 0; i < n; i++) {
adj[i] = new ArrayList<Integer>();
}
for (int i = 0; i < m; i++) {
int x, y;
x = scanner.nextInt();
y = scanner.nextInt();
adj[x - 1].add(y - 1);
adj[y - 1].add(x - 1);
}
int x = scanner.nextInt() - 1;
int y = scanner.nextInt() - 1;
visited = new boolean[n];
System.out.println(reach(adj, x, y));
}
}
Given below is the failed test case.
Failed case #6/16: (Wrong answer)
Input:
100 100
27 96
6 9
81 98
21 94
22 68
76 100
8 50
38 86
71 75
32 93
16 50
71 84
6 72
22 58
7 19
19 76
44 75
24 76
31 35
11 89
42 98
63 92
37 38
20 98
45 91
23 53
37 91
76 93
67 90
12 22
43 52
23 56
67 68
1 21
17 83
63 72
30 32
7 91
50 69
38 44
55 89
15 23
11 72
28 42
22 69
56 79
5 83
55 73
13 72
7 93
20 54
21 55
66 89
2 91
18 88
26 64
11 61
28 59
12 86
42 95
17 82
50 66
66 99
40 71
20 40
5 66
92 95
32 46
7 36
44 94
6 31
19 67
26 57
53 84
10 68
28 74
34 94
25 61
71 88
10 89
28 52
72 79
39 73
11 80
44 79
13 77
30 96
30 53
10 39
1 90
40 91
62 71
44 54
15 17
69 74
13 67
24 69
34 96
21 50
20 91
42 46
Your output:
0
Correct output:
1
The problem is that you do an early return from reach() if y cannot be reached via the first unvisited neighbor of x:
return reach(adj,x,y);
What you want to do instead is:
If y can be reached then return 1.
If y cannot be reached then continue with the next neighbor
That would read:
if (reach(adj, x, y) == 1)
return 1;
Unrelated comment: You may want to use Iterator<Integer> instead of the raw type Integer. This avoids the cast and compiler warnings.
I have a homework problem for my "Data Structure and Algorithm class" - Implement a Top Down Recursive Merge Sort in Java. Demonstrate that your sort works by generating a random sequence of 100 numbers, printing them in their raw unsorted form, sorting them, and then printing them out in their sorted order.
And i did a little bit of coding and it seems to be right but i am getting an error and can't figure out what i did wrong.
class RecursiveMergeSort
{
void TopDownMergeSort(int[] mainArray, int[] copyArray) // mainArray, copyArray, int n
{
CopyArray(mainArray, copyArray);
Split(copyArray, 0, 100, mainArray);
}
private void Split(int[] copyArray, int start, int end, int[] mainArray)
{
if(end - start < 2)
{
return;
}
int middle = (end + start) / 2;
Split(mainArray, start, middle, copyArray);
Split(mainArray, start, end, copyArray);
CombineArray(copyArray, start, middle, end, mainArray);
}
private void CombineArray(int[] mainArray, int start, int middle, int end, int[] copyArray)
{
int s = start; //a
int m = middle; //b
for (int i = start; i < end; i++)
{
if(s < middle && (m >= end || mainArray[s] <= mainArray[m]))
{
copyArray[i] = mainArray[s];
s = s + 1;
}
else
{
copyArray[i] = mainArray [m];
m = m + 1;
}
}
}
private void CopyArray(int[] mainArray, int[] copyArray)
{
System.arraycopy(mainArray, 0, copyArray, 0, 100);
}
void UnsortedArray(int[] unsortedArray)
{
for(int i = 0; i < unsortedArray.length; i++)
{
int random = (int)Math.floor(Math.random() * 100) + 1;
unsortedArray[i] = random;
System.out.println("\t" + i + unsortedArray[i]);
}
}
void SortedArray(int[] unsortedArray)
{
for(int i = 0; i < unsortedArray.length; i++)
{
System.out.println("\t: " + i + unsortedArray[i]);
}
}
}
And here is Driver:
public class RecursiveDriver
{
public static void main(String[] args)
{
int[] randomNumbers = new int[100];
int[] sorted = new int[100];
RecursiveMergeSort test = new RecursiveMergeSort();
System.out.println("Unsorted Array:");
test.UnsortedArray(randomNumbers);
System.out.println("Sorted Array");
test.TopDownMergeSort(randomNumbers, sorted);
test.SortedArray(randomNumbers);
}
}
This is what I am expecting:
Unsorted List: 100 61 8 76 51 89 30 63 11 1 47 74 85 63 80 45 18 34 74 25 8 90 61 44 25 2 40 100 47 1 72 24 86 80 87 75 46 85 14 30 43 31 27 48 96 96 26 20 44 1 67 1 30 35 87 78 18 46 37 31 6 61 62 92 71 45 6 10 12 38 96 14 22 83 96 31 65 74 58 47 87 65 28 61 91 73 3 92 87 22 68 0 9 18 13 89 36 8 35 44
Sorted List: 0 1 1 1 1 2 3 6 6 8 8 8 9 10 11 12 13 14 14 18 18 18 20 22 22 24 25 25 26 27 28 30 30 30 31 31 31 34 35 35 36 37 38 40 43 44 44 44 45 45 46 46 47 47 47 48 51 58 61 61 61 61 62 63 63 65 65 67 68 71 72 73 74 74 74 75 76 78 80 80 83 85 85 86 87
And that’s the outcome I get when I run my script:
But i am getting:
Unsorted Array:
035
175
270
392
436
And it keeps going until I get an error:
Sorted Array Exception in thread "main" java.lang.StackOverflowError at RecursiveMergeSort.Split(RecursiveMergeSort.java:16) at RecursiveMergeSort.Split(RecursiveMergeSort.java:17)
It seems like it has something to do with line 16/17 but i am not completely sure how to fix it. Thanks for all the help.
int middle = (end + start) / 2;
Split(mainArray, start, middle, copyArray);
Split(mainArray, start, end, copyArray);
CombineArray(copyArray, start, middle, end, mainArray);
Should be
int middle = (end + start) / 2;
Split(mainArray, start, middle, copyArray);
Split(mainArray, middle, end, copyArray);
CombineArray(copyArray, start, middle, end, mainArray);
You were super close, just the start index of the second recursive call should be from the middle index to the end, not the start all the way to the end again (resulting in the stack overflow error)
On a side note - you should rename your methods to comply with the standard, ex: they start with a lower-case letter such as:
private void combineArray(int[] mainArray, int start, int middle, int end, int[] copyArray)
The following code is for rotation of an integer array.
Takes user input for array size and then an input for the element upto which the array is to be rotated.
Doesn't work for large values of array size and the rotation element.
The following code works for 15 array elements and rotates by 11 numbers (I didn't try for higher numbers) but it fails for a 77 array element and for rotation by 69 numbers.
It works with both sorted and unsorted array.
Why is it not working and how can I fix this?
int dupRotate = D;
for(int j=N-1; j>=0; --j) {
/* checks whether loop is to be stopped or not.
bottom condition fails to stop the 1st iteration for
third loop run.
*/
if(dupRotate == 0) {
break;
}
/* Exchanges elements here.
for loop run1 -
arr = 1,2,3,4,5
after j reaches index 1
arr = 2,3,4,5,1.
for loop run2 -
arr = 2,3,4,5,1.
after j reaches index 1
arr = 3,4,5,1,2.
*/
int temp = arr[0];
arr[0] = arr[j];
arr[j] = temp;
/* if j reaches 1
decrements dupRotate and sets j = N
then for loop decrements j and starts loop again.
*/
if(j == 1 && dupRotate > 0) {
dupRotate--;
j = N;
}
}
77 69
40 13 27 87 95 40 96 71 35 79 68 2 98 3 18 93 53 57 2 81 87 42 66 90 45 20 41 30 32 18 98 72 82 76 10 28 68 57 98 54 87 66 7 84 20 25 29 72 33 30 4 20 71 69 9 16 41 50 97 24 19 46 47 52 22 56 80 89 65 29 42 51 94 1 35 65 25
Its Correct output is:
29 42 51 94 1 35 65 25 40 13 27 87 95 40 96 71 35 79 68 2 98 3 18 93 53 57 2 81 87 42 66 90 45 20 41 30 32 18 98 72 82 76 10 28 68 57 98 54 87 66 7 84 20 25 29 72 33 30 4 20 71 69 9 16 41 50 97 24 19 46 47 52 22 56 80 89 65
And Your Code's output is:
45 20 41 30 32 18 98 72 82 76 10 28 68 57 98 54 87 66 7 84 20 25 29 72 33 30 4 20 71 69 9 16 41 50 97 24 19 46 47 52 22 56 80 89 65 29 42 51 94 1 35 65 69 40 13 27 87 95 40 96 71 35 79 68 2 98 3 18 93 53 57 2 81 87 42 66 90
It's pretty hard to realise your problem. I have to add more description.
I think, if you use the correct algorithm of array rotation, then it does not depend on an array's length. This is one of the most efficient algorithm:
[1,2,3,4,5] -> k = 2 -> [4,5,1,2,3]
-----------------------------------
1. [1,2,3,4,5] -> [5,4,3,2,1]
2. [5,4,3,2,1] -> [4,5,3,2,1]
3. [4,5,3,2,1] -> [4,5,1,2,3]
public static void rotate(int[] arr, int k) {
if ((k %= arr.length) != 0) {
k = k < 0 ? arr.length + k : k;
swapSubArr(arr, 0, arr.length); // 1.
swapSubArr(arr, 0, arr.length - k); // 2.
swapSubArr(arr, arr.length - k, arr.length); // 3.
}
}
private static void swapSubArr(int[] arr, int from, int to) {
for (int i = from, j = to - 1; i < j; i++, j--)
swap(arr, i, j);
}
private static void swap(int[] arr, int i, int j) {
int tmp = arr[i];
arr[i] = arr[j];
arr[j] = tmp;
}
Move step by step
[1,2,3,4,5] -> k = 3 -> [4,5,1,2,3]
-----------------------------------
1. [1,2,3,4,5] -> [5,4,3,2,1]
2. [5,4,3,2,1] -> [4,5,3,2,1]
3. [4,5,3,2,1] -> [4,5,1,2,3]
Code
static void rotate(int arr[], int k) {
for (int i = 1; i <= k; i++) {
move(arr);
}
}
static void move(int arr[]) {
int i, n, tmp;
n = arr.length;
tmp = arr[0];
for (i = 0; i < n - 1; i++) {
arr[i] = arr[i + 1];
}
arr[i] = tmp;
}
public static void main(String[] args) {
int arr[] = { 1, 2, 3, 4, 5 };
int k = 3;
// [1, 2, 3, 4, 5]
rotate(arr, k);
// [4, 5, 1, 2, 3]
}
I tried to Google and search StackOverflow my question but I didn't found any answers to this.
I have made an array where both size and values are randomly generated. When the array values have been printed 20 times I would like to make a line break, but without printing the rest values with always new line.
Here is my code:
public static void catArr() {
Random rändöm = new Random();
int size = rändöm.nextInt(100);
int[] arr = new int[size];
for (int i = 0; i < size; i++) {
arr[i] = rändöm.nextInt(100);
}
Arrays.sort(arr);
for (int i = 0; i < size; i++) {
System.out.print(" " + arr[i]);
if (i > 20)
System.out.println(); //How to do this only once?
else if (i > 40)
System.out.println(); //Same here?
}
}
And this is one of the generated outputs:
3 8 10 25 30 31 34 38 46 50 55 59 62 66 67 68 68 68 72 76 76 81
82
83
84
86
91
92
93
94
94
97
I think that one way to solve this is using 2-D array, but I would like to know if there is another way.
Yay thanks to Patric, I got the wanted result:
0 2 3 7 7 9 11 14 14 16 18 19 24 25 26 28 28 30 30 31
31 33 33 34 41 41 41 42 43 44 45 46 51 51 52 53 59 60 61 62
62 62 63 65 65 67 67 68 69 70 74 74 76 78 82 83 84 84 87 88
89 93 93 94 94 94 95
try using
if ( ( i % 20 ) == 0 ){
System.out.println();
}
if i divided by 20 leaves no remainder then print a new line!
Maybe
if (i % 20==0)
can solve your else if problem.
Use (++i % 20) == 0 and remove i++ from loop; pre-increment avoid first unwanted line break.
Literally, this will do what you seem to want:
if (i == 20)
System.out.println();
else if (i == 40)
System.out.println();
But I have a feeling that you actually want to add a newline after the 20th, 40th, 60th and so on.
if (i % 20 == 0)
System.out.println();
And if you want to output exactly one newline at the end, then you need something like this:
for (int i = 0; i < size; i++) {
if (i > 1 && i % 20 == 1) {
System.out.println();
System.out.print(" " + arr[i]);
}
System.out.println();
You may use boolean for your Sys outs.
boolean myBoolean = true;
if(myBoolean){
//print
myBoolean = false; //set boolean to false.
}
On the other hand, in my preferences, I still stick with my integer flagging.
int isTrue = 1;
if(isTrue == 1){
//print
isTrue = 0;
}