Java Exam Error Checking - java

I have the following code from a previous past paper:
int n = arr.length;
double min = 0;
int minLocation=0;
for(int i = 1; i <= n; i++) {
if( arr[i] < min ) {
min = arr[i];
}
minLocation = i;
}
System.out.print("The minimal value is arr[");
System.out.println(minLocation + "] = " + min);
I have to answer the following questions from the code:
(i) The line on which the error appears
(ii) What effect the error would have
(iii) How the error should be corrected.
You may assume arr[] is a non-empty array of double values that has been
properly declared and initialized.
I know there will be a runtime error at the line with the if statement which i'm still not sure how. As I am unable to correct it I can't see how I get the undesired results. I can see it's such a straight forward question and I am missing out something extremely obvious but I have been looking at it for a while and i'm completely missing it.

There are several mistakes in that code. Here a list of them including explanation of impact and how to fix them:
You are initialising min with 0
Effect: If your array e.g. only consists of {1.1, 2.2} your code would claim that 0 is the minimum, what obviously is wrong because there doesn't exist an index i that arr[i] == 0
Fix: double min = Double.MAX_VALUE;
Your for-loop starts at index 1 for (int i = 1; ...)
Effect: You are skipping arr[0]
Fix: for (int i = 0 ...)
Your loop iterates once to often because of the condition or ( ... ; <= n; ...)
Effect: You will encounter an AIOOBE (ArrayIndexOutOfBoundsException)
Fix: for ( ... ; i < n; ...)
Your are overwriting minLocation in every iteration of the loop
Effect: After the last iteration of the loop, minLocation will always be = n
Fix: Place minLocation = i; inside the if-statement.
Corrected version
int n = arr.length;
double min = Double.MAX_VALUE;
int minLocation = 0;
for(int i = 0; i < n; i++) {
if(arr[i] < min) {
min = arr[i];
minLocation = i;
}
}

I know there will be a runtime error at the line with the if statement
which i'm still not sure how
This runtime error will be IndexOutOfBoundsException. This error occur because array index is one less than array size.
Your loop should be like.
for(int i = 0; i < n; i++)

Did you intend your for() loop to start at index 1? By convention it starts at 0;
It should really be: for(int i=0;i

Your for loop needs to be:
for(int i = 0; i < n; i++)
Otherwise you will get an IndexOutOfBoundsException since you access the array outside of its range.
Also you should change your min value initialiaztion to:
double min = Double.MAX_VALUE;
Otherwise you will only find the minimum if your array only contains negative values.

There are logical errors in your program, if it is intended to find the minimal value and position of given array.
Initialize
double min = arr[0];
End for loop at
i < n
Include
minLocation = i;
as
if( arr[i] < min )
{
min = arr[i];
minLocation = i;
}

Java array indices start at 0. So the for loop should be for( int i = 0; i < n; i++ ).
The minimum is only computed if the the elements of the array are non-negative.

Related

nested for loops integers missing from array

Beginner here. I'm having problems running this series of for loops to find which integers are missing from an array.
public class FunWithArrays{
public static void main(String[] args){
String nString = args[0];
int n = Integer.parseInt(nString);
int inputArray [] = {1,2,4};
System.out.println(" The missing numbers are " );
findMissingNum(n, inputArray);
}
public static void findMissingNum(int n, int[] inputArray){
for (int i = 1; i <= inputArray.length; i++){
int count = 0;
for( int j = 0; j < n; j++){
if(inputArray[j] == i){
count ++;
}
if (count == 0){
System.out.println(i);
}
}
}
}
}
I get the answer I want, namely 3, however it doesn't print but rather shows up in a runtime error:
java.lang.ArrayIndexOutOfBoundsException: 3
at FunWithArrays.findMissingNum(FunWithArrays.java:17)
at FunWithArrays.main(FunWithArrays.java:9)
the method should take an input n from the user (when the program is run) as the largest value of the array and print all the ones missing
The logic is the outer for loop should traverse the array for numbers 1-n, and the inner loop should add to the count variable each time it finds a certain number. At the end of iteration it should print any numbers with a final "count" of 0. THIS IS LITERALLY DRIVING ME CRAZY!!! thanks in advance :)
First of all, you should traverse from 0 to (inputArray.length-1) index of inputArray. This will get rid of the ArrayIndexOutOfBoundsException, because java array indexing starts from 0 not 1.
And for inner loop, run from 0 to n, since n is the max number.
And Thirdly, it should be inputArray[i] == j, not inputArray[j] == i, same for printing the value. In you case I believe you have n>=4, so it was trying to access inputArray[3] via inputArray[j] call. That's why you are getting this out of bound error.
I think your code means like this: nest loop always run through inner loop first before run the outer loop.
public static void findMissingNum(int n, int[] inputArray){
for (int i = 1; i <= n; i++){
int count = 0;
for( int j = 0; j < inputArray.length; j++){
if(inputArray[j] == i){
count ++;
}
if (count == 0){
System.out.println(i);
}
}
}
}
I will just use a while loop instead:
int num =1;
while(num<=n){
for(int i = 0;i<inputArray.length;i++){
if(inputArray[i]!=num){
System.out.println(num);
}
}
num++;
}
The i incrementing to <= ipnutArray.length is not causing the error because i is never used as the index. What is causing the error is when n > length.
Also, you should not be checking n elements starting from the beginning because n is the max value, not the number of elements.

Going back to the first index after reaching the last one in an array

After my array in the for loop reaches the last index, I get an exception saying that the index is out of bounds. What I wanted is for it to go back to the first index until z is equal to ctr. How can I do that?
My code:
char res;
int ctr = 10
char[] flames = {'F','L','A','M','E','S'};
for(int z = 0; z < ctr-1; z++){
res = (flames[z]);
jLabel1.setText(String.valueOf(res));
}
You need to use an index that is limited to the size of the array. More precisely, and esoterically speaking, you need to map the for-loop iterations {0..9} to the valid indexes for the flame array {0..flames.length()-1}, which are the same, in this case, to {0..5}.
When the loop iterates from 0 to 5, the mapping is trivial. When the loop iterates a 6th time, then you need to map it back to array index 0, when it iterates to the 7th time, you map it to array index 1, and so on.
== Naïve Way ==
for(int z = 0, j = 0; z < ctr-1; z++, j++)
{
if ( j >= flames.length() )
{
j = 0; // reset back to the beginning
}
res = (flames[j]);
jLabel1.setText(String.valueOf(res));
}
== A More Appropriate Way ==
Then you can refine this by realizing flames.length() is an invariant, which you move out of a for-loop.
final int n = flames.length();
for(int z = 0, j = 0; z < ctr-1; z++, j++)
{
if ( j >= n )
{
j = 0; // reset back to the beginning
}
res = (flames[j]);
jLabel1.setText(String.valueOf(res));
}
== How To Do It ==
Now, if you are paying attention, you can see we are simply doing modular arithmetic on the index. So, if we use the modular (%) operator, we can simplify your code:
final int n = flames.length();
for(int z = 0; z < ctr-1; z++)
{
res = (flames[z % n]);
jLabel1.setText(String.valueOf(res));
}
When working with problems like this, think about function mappings, from a Domain (in this case, for loop iterations) to a Range (valid array indices).
More importantly, work it out on paper before you even begin to code. That will take you a long way towards solving these type of elemental problems.
While luis.espinal answer, performance-wise, is better I think you should also take a look into Iterator's as they will give you greater flexibility reading back-and-forth.
Meaning that you could just as easy write FLAMESFLAMES as FLAMESSEMALF, etc...
int ctr = 10;
List<Character> flames = Arrays.asList('F','L','A','M','E','S');
Iterator it = flames.iterator();
for(int z=0; z<ctr-1; z++) {
if(!it.hasNext()) // if you are at the end of the list reset iterator
it = flames.iterator();
System.out.println(it.next().toString()); // use the element
}
Out of curiosity doing this loop 1M times (avg result from 100 samples) takes:
using modulo: 51ms
using iterators: 95ms
using guava cycle iterators: 453ms
Edit:
Cycle iterators, as lbalazscs nicely put it, are even more elegant. They come at a price, and Guava implementation is 4 times slower. You could roll your own implementation, tough.
// guava example of cycle iterators
Iterator<Character> iterator = Iterators.cycle(flames);
for (int z = 0; z < ctr - 1; z++) {
res = iterator.next();
}
You should use % to force the index stay within flames.length so that they make valid index
int len = flames.length;
for(int z = 0; z < ctr-1; z++){
res = (flames[z % len]);
jLabel1.setText(String.valueOf(res));
}
You can try the following:-
char res;
int ctr = 10
char[] flames = {'F','L','A','M','E','S'};
int n = flames.length();
for(int z = 0; z < ctr-1; z++){
res = flames[z %n];
jLabel1.setText(String.valueOf(res));
}
Here is how I would do this:
String flames = "FLAMES";
int ctr = 10;
textLoop(flames.toCharArray(), jLabel1, ctr);
The textLoop method:
void textLoop(Iterable<Character> text, JLabel jLabel, int count){
int idx = 0;
while(true)
for(char ch: text){
jLabel.setText(String.valueOf(ch));
if(++idx < count) return;
}
}
EDIT: found a bug in the code (idx needed to be initialized outside the loop). It's fixed now. I've also refactored it into a seperate function.

Radix sorting code confusion

I have a question about this algo:
(Slide taken from here.)
int N = a.length;
int[] count = new int[R];
for (int i = 0; i < N; i++)
count[a[i]+1]++;
for (int k = 1; k < 256; k++)
count[k] += count[k-1];
for (int i = 0; i < N; i++)
temp[count[a[i]++]] = a[i]
for (int i = 0; i < N; i++)
a[i] = temp[i];
Can someone elaborate about the 3rd for loop where we move the records from a[] to temp[]?
I know after we accumulate counts they're supposed to be some sort of offset. So we can insert the letters in proper place in temp[].
I'm just not sure what the a[i]++ is doing in there. (<-main question) I know where referencing the letter in the count array, but why do we increment the letter too? Did we change letters? Thanks.
Grateful for any help.
it looks like a typo:
it should be:
temp[count[a[i]]++]
the next element should go into the next empty space
in step1 prepares for adds type_i counts to cnt_{i+1}, this way making space for type_i elements...
step2 is a prefix on the counts
step3 uses counts as R index pointers and sends all elements from a to its final destination
invariant holded at this step:
count[ x ] points to the next empty space where an type_x element can be placed (or there are no more x elements in the input)

Java integer array, I cant do simple maths it seems

I have the code below:
int lines = 0;
while(lines < 2)
{
int[] oldarr = parr;
for(int i = 0; i < arrsize; i++)
System.out.print(" " + oldarr[i]);
System.out.println();
for(int i = 0; i < arrsize; i++)
{
if(i == 0)
parr[i] = 0;
else
parr[i] = Math.abs(oldarr[i] - oldarr[i-1]);
}
lines++;
}
parr is an array of integers of size [arrsize]. Each time through this loop I want to print the value of each index in parr, then set each index to the difference between the index before it and itself. Currently it gives me the correct (hardcoded) originally parr. But the next(first) iteration of changing parr gives me unexpected values; they are not even close to the difference between the two neighboring values..
Any ideas?
You aren't copying your array with this line:
int[] oldarr = parr;
The two variables are still pointing at the same array.
To get a copy, you can do:
int[] oldarr = Arrays.copyOf(parr, parr.length);
In your second for loop, you are setting the new value to the difference of the current value and the previous value, but the previous value was already changed in the previous iteration of the for loop.
Change your second for loop iteration to iterate through the array backwards, so your calculations don't depend on previous calculations.
for(int i = arrsize - 1; i >= 0; i--)

Array index out of bounds but shouldn't be

I'm making a pretty simple java-program and I get the following error (where n is a random number based on previous input from console):
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: n
the line that is supposed to cause trouble is the if-statement here:
for(int i = 0; 0 < x; i++){
if(TalArray[i] < min){
min = TalArray[i];
}
}
the variable "min" is previously initzialized to TalArray[0] and is keeping track of the lowest number. All variables mentioned are int-variables
The correct code is...
for(int i = 0; i < x; i++){
if(TalArray[i] < min){
min = TalArray[i];
}
}
It's not clear what's the value of x in the code, but anyway the loop condition should look like this:
for (int i = 0; i < TalArray.length; i++)
Or like this, to avoid accessing the length at each iteration:
for (int i = 0, x = TalArray.length; i < x; i++)
The 0 < x comparison is mistaken: you're not modifying the value of x inside the loop, so the loop will either enter an infinite loop or not enter the loop at all, depending on the initial value of x.
The problem is, that your variable X is never changing so
your condition 0 < x is always true.
I guess the correct condition would be
for(int i = 0; i < x; i++)

Categories