Exception in thread "main" java.lang.IndexOutOfBoundsException: [duplicate] - java

This question already has answers here:
sublist index out of bound exception
(3 answers)
Closed 4 years ago.
The program uses methods to:
get the numbers used to calculate the average,
get the number of lowest numbers to drop before calculating the
get the weight, a double greater than 0 and less than or equal to 1,
calculate the weighted average of the numbers (except the lowest n numbers) entered by the user, and
print the results.
The first method should take no arguments and return an array list of doubles.
The second method should take no arguments and return a single integer, the number of the lowest numbers to drop before calculating the average.
The third method should take no arguments and return a double (the weight)
The fourth method should take three arguments: an array list of numbers (the return value of the first method above); an integer (the number of smallest items to drop before calculating the average); and a double (the weight). This method should return a double (the weighted average of all the numbers except the lowest n values).
The fifth method should take four arguments: an array list of numbers (the return value of the first method above); an integer (the number of smallest numbers to drop before calculating the average); a double (the weight); and a double (the weighted average returned from the fourth method above). This method should have no return value.
For example:
If the user gives these numbers for calculating the average:
40 60 80 100 20
and the user gives the number 2 to indicate how many of the lowest values should be dropped before calculating the average, and gives a weight of 0.5, then the program should give as output:
The weighted average of the numbers is 40.0, when using the data 40.0, 60.0, 80.0, 100.0, 20.0, where 0.5 is the weight used, and the average is computed after dropping the lowest 2 values.
import java.util.*;
import java.lang.*;
import java.util.ArrayList;
import java.util.Collections;
public class MyClass
{
public static ArrayList<Double> getALInfo()
{
Scanner in=new Scanner(System.in);
ArrayList<Double> inputs = new ArrayList<>();
System.out.println("Please enter 5 - 10 integers, Q to quit: ");
String [] tokens = in.nextLine().split("\\s");
for (int i = 0; i < tokens.length; i++)
inputs.add(Double.parseDouble(tokens[i]));
return inputs;
}
public static int getLowestnum()
{
int lowNum = 0;
System.out.println("How many of the lowest values should be dropped? ");
Scanner in = new Scanner(System.in);
lowNum = in.nextInt();
return lowNum;
}
public static double weight()
{
Scanner in = new Scanner(System.in);
System.out.println("Enter the weight: ");
double weight = in.nextDouble();
return weight;
}
public static double calculateAvg(ArrayList<Double> inputs,double weight, int lowNum)
{
double sum = 0;
double average = 0;
Collections.sort(inputs);
ArrayList<Double> inputs1 = new ArrayList<Double>(inputs.subList(lowNum, inputs.size()+1));
for (int i = 0; i < inputs1.size(); i++)
{
if (inputs1.get(i) > lowNum)
{
sum = sum + inputs.get(i);
}
}
sum=weight*sum;
average = (sum / inputs1.size());
return average;
}
public static void getAvg(ArrayList<Double> inputs,int n,double weight, double average)
{
System.out.println("The weighted average of the numbers is " + average + ", when using the data " + inputs + " where " +weight+ " is the weight used, and the average is computed after dropping the lowest " +n+" values");
}
public static void main(String args[])
{
int lowNum = 0;
double average;
double weight=0;
ArrayList<Double> inputs= getALInfo();
lowNum = getLowestnum();
weight=weight();
average = calculateAvg(inputs,weight, lowNum);
getAvg(inputs, lowNum,weight, average);
}
}
The program is running fine util you enter the weight after that it shows an array out of bounds exception error. Can you point out where im going wrong .

The error comes from new ArrayList<Double>(inputs.subList(lowNum, inputs.size()+1))
Because you try to reach, as end index, the last element +1 so it does not exists
Solve :
new ArrayList<Double>(inputs.subList(lowNum, inputs.size()))
!! Also, your for loop is wrong
don't need to check with this strange if
you don't pick up from the correct list : use better names
for (int i = 0; i < inputs1.size(); i++) {
if (inputs1.get(i) > lowNum) {
sum = sum + inputs.get(i);
}
}
Solve
ArrayList<Double> subList = new ArrayList<>(inputs.subList(lowNum, inputs.size()));
for (int i = 0; i < subList.size(); i++) {
sum = sum + inputs.get(i);
}

Related

How to input an array list and output sum in java

I have this code that reads an array list until the user enters 0 and calculate the sum of the array. My way only read half of the input. Please help me check and find out what is wrong. Thank you!!
Here is the supposed input and output
(sample input)
1 2 3 2 1 0
(sample output from Eclipse - includes both input and output)
This program will store numbers in an ArrayList and compute the sum of numbers.
Enter the numbers one at a time. Enter a 0 to terminate the input.
1 2 3 2 1 0
The items in the ArrayList are [1.0, 2.0, 3.0, 2.0, 1.0]
There are 5 items in the ArrayList
The sum of items in the ArrayList is 9.0
and here is what I am working on
import java.util.ArrayList;
import java.util.Scanner;
public class SumArrayList {
public static void main(String[] args) {
Scanner scnr = new Scanner(System.in);
ArrayList<Double> list = new ArrayList<Double>();
int n=0;
double sumVal = 0;
System.out.println("This program will store numbers in an ArrayList and compute the sum of numbers.\r\n" +
"Enter the numbers one at a time. Enter a 0 to terminate the input.");
while(scnr.nextDouble() != 0)
{
list.add(scnr.nextDouble());
}
System.out.print("The items in the ArrayList are ");
for(int i=0; i < list.size(); i++)
{
System.out.print(list.get(i) + " ");
sumVal += list.get(i);
n = i+1;
}
System.out.println();
System.out.println("There are " + n + " items in the ArrayList");
System.out.println("The sum of " + n + " items in the ArrayList is " + sumVal);
}
}
You are using nextDouble twice therefore it is expecting twice the input
try
double value = scnr.nextDouble();
while(value != 0)
{
list.add(value);
value = scnr.nextDouble();
}
If you only want the stats (and not the values) you could dispense with your list altogether and just keep the aggregate. Something like:
DoubleSummaryStatistics stats = DoubleStream.generate(scnr::nextDouble)
.takeWhile(d -> d > 0).summaryStatistics();
You then have count, sum, average, range available.

How to average random numbers in java?

thanks in advance for any help I'm in an intro to java class and our home work was to generate 10 random numbers between 1&50 which I got and then average the generated numbers. I can't figure out how to average them here's what I have. Is there a way to store each random number as a variable?
public class randomNumberGen
{
public static void main(String [] args)
{
Random r=new Random();
for (int i=1;i<=10;i++){
System.out.println(r.nextInt(50));
System.out.println();
int average = (i/4);
System.out.println("your average is"+average);
}
}
}
use streams with java 8
final int numberOfRandom = 10;
final int min = 0;
final int max = 50;
final Random random = new Random();
System.out.println("The ave is: "+random.ints(min, max).limit(numberOfRandom).average());
First of all you have to replace "r.nextInt(50)" for "r.nextInt(50) + 1" because r.nextInt(n) returns a number between 0 (inclusive) and n (exclusive). Then, you know that an average is just a sum of n values divided by n. What you can do is just declare a "total" variable initialized to 0 before the loop. On each iteration you add to this variable the random value generated by r.nextInt(50). After the loop you can just divide the total by 10 so you get the average.
PS: it's a good practice to don't use "magic numbers", so it would be perfect (and luckily your teacher will have it in count) if you declare a constant for the number of iterations and then use it both in the loop condition and in the average calculation. Like this, if you have to make it for 100 numbers you only have to change the constant value from 10 to 100 instead of replacing two 10's por two 100's. Also this gives you the chance to give semantic value to these numbers, because now they will be "AMOUNT_OF_NUMBERS = 10" instead of just "10".
Like every average, it's sum of elements / amount of elements. So let's apply it here:
import java.util.Random;
public class randomNumberGen
{
public static void main(String [] args)
{
Random r=new Random();
double sum = 0; // is double so to prevent int division later on
int amount = 10;
int upperBound = 50;
for (int i = 0; i < amount; i++){
int next = r.nextInt(upperBound) + 1; // creates a random int in [1,50]
System.out.println(next);
sum += next; // accumulate sum of all random numbers
}
System.out.println("Your average is: " + (sum/amount));
}
}
Store variables outside of the loop to store both the total amount of numbers generated as well as the sum of those numbers. After the loop completes, divide the sum by the total amount of numbers.
public static void main(String [] args)
{
Random r=new Random();
double sum = 0;
int totalNums;
for (totalNums=1;totalNums<=10;totalNums++){
int randomNum = r.nextInt(50);
sum += randomNum;
System.out.println(randomNum);
}
double average = sum/totalNums;
System.out.println("your average is: "+average);
}
Average = Sum of numbers / amount of numbers
int sum = 0;
for (int i=1;i<=10;i++){
sum += r.nextInt(50) +1; //nextInt 50 produces value 0 to 49 so you add 1 to get 1 to 50 OR as suggested in the comments sum/10d
}
System.out.println("Average is: " + sum/10) // If you want the result in double (with decimals) just write sum*1.0/10
You could also do the same with a while loop.
int i = 0;
int sum = 0;
while(i < 10){
sum += r.nextInt(50) +1;
i++;
}
System.out.println("Average is: " + sum*1.0/i);
Or even shorter with lambda expressions: (/java 8 streams)
OptionalDouble average = IntStream.range(1, 10).map(x-> x = r.nextInt(50) +1).average();
System.out.println("Average is "+ average.getAsDouble());
.map(x-> x = r.nextInt(50) +1) // maps (changes) each value from 1 to 10 to a random number between 1 and 50
.average(); // calculates the average.
Simply create a variable sum starting at zero that you increment at each iteration. After the loop, simply divide by the number of elements..
Average means you should add everything up and devide it by the number of elements (50).
import java.util.Random;
class Homework {
public static final Random RANDOM = Random(); // never regenerate randoms
public static void main(String args[]) {
final int N = 50;
int sum = 0;
for (int i = 0; i < N; ++i) {
sum += RANDOM.nextInt(50)+1;
}
System.out.println("Avg: "+ sum / (float) N);
}
}
This should do the trick. Try to learn from it not just C+P.
Ps: Friggin annoying to write code on a phone.

wrong results from simple java method [duplicate]

This question already has answers here:
Simple division in Java - is this a bug or a feature?
(5 answers)
Closed 7 years ago.
I'm trying to write a program that asks for the size of an array of integers, the values of the array, and then finds the average of the positive integers and prints it. When I run it, I sometimes get wrong results. I haven't identified on what the wrong results depends but for example if I enter the following input: "array size: 4, array values: 1, 2, -5, 5" I get an average of "2.0"
Here's my code:
import java.util.Scanner;
public class Mitra {
private static Scanner user_input;
double avg (int[] arr, int size)
{
int sum = 0;
int numbers = 0;
for (int i=0; i<size;i++)
{
if (arr[i]>0)
{
sum = sum+arr[i];
numbers++;
}
else{
continue;
}
}
double average = sum/numbers;
return average;
}
public static void main(String[] args) {
user_input = new Scanner (System.in);
System.out.println("enter array length");
int alength = user_input.nextInt();
int[] array_1 = new int[alength];
for (int i=0; i<alength;i++)
{
System.out.println("Enter array value "+i);
array_1[i] = user_input.nextInt();
}
Mitra obj = new Mitra();
double result = obj.avg(array_1, alength);
System.out.println("The average of the positive numbers of the array is "+result);
}
}
Change
double average = sum/numbers;
to
double average = (double)sum/numbers;
to force floating point division.
Otherwise, int division (which is the operation that takes place when dividing two variables of int type) will give you 2 when dividing 8/3 (as you do in your example).
When you evaluate sum/numbers it stores the result in a temporary variable(and the decimal part is already truncated) and then assigns it on the left side.You need to typecase it with (Double) like this:
double average = (double)sum/numbers;

Finding standard deviation

I cant seem to figure out how exactly to find the standard deviation using what i have. the thing that is confusing me is really the whole standard deviation equation and how to exactly put it into code.
import java. util.Scanner;
public class StandardDeviation
{
public static void main (String[] args)
{
int array;
float sum = 0;
float mean;
Scanner scan = new Scanner(System.in);
System.out.println("Enter wanted array length:");
array = scan.nextInt();
float[] numbers = new float[array];
System.out.println("The size of the array: " + numbers.length);
for (int index = 0; index < numbers.length; index++)
{
System.out.print("Enter number " + (index+1) + ": ");
numbers[index] = scan.nextFloat();
}
for (float i : numbers)
{
sum += i;
}
mean = sum/numbers.length;
System.out.println("The mean is: " + mean);
}
}
You already have the mean, which is the first step in finding the standard deviation.
First, you loop through your array of numbers. You subtract the number from the mean, then square the answer. Add the squared answers together.
Next, divide your squared answer sum by the length of your array of numbers, minus 1.
Finally, take the square root of the result of the last step.
Sum (x - mean) * (x - mean)
Sum from step 1. / (length - 1)
Square root of the result from step 2.
Math.pow(number, 0.5D) gives you the square root of a double.

output blank--Java program to calculate average of array

I am writing a program that takes 10 floating point numbers as inputs, and displays the average of the numbers followed by all of the numbers that are greater than the average. I am using a method that takes an array of doubles as a parameter and returns the average of the data in the array. However, my problem is that when I run my program the output window is completely blank. I assume this is because I did not call in my method to the main method. However, I am not sure how to write that code. Thank you.
import java.util.Scanner;
public class Average {
public static void main(String[] args) {
}
public double average(double[] number) {
Scanner scanner = new Scanner(System.in);
int x = 0;
double sum = 0;
double[] numberList = new double[10]; //array to hold all numbers
double[] largerList = new double[10]; //array to hold numbers greater than the average
int numberIndex = 0;
int largerIndex = 0;
System.out.printf("Please enter 10 floating-point numberes.\nIf more than 10 values are entered, the numbers following 10 are ignored.\nIf less than 10 numbers are entered, the program will wait for you to enter 10.\n");
for (int i = 0; i < 10; i++) {
try { //try catch exception to catch decimal inputs as well as more /less than 10 integers
x = scanner.nextInt();
sum += numberList[x]; //add up all inputs to find sum
} catch (Exception e) {
System.out.println("Invalid input! Please reenter 10 integer values.");
scanner = new Scanner(System.in);
i = -1;
numberIndex = 0;
largerIndex = 0;
numberList = new double[10];
largerList = new double[10];
continue;
}
}
for (int i = 0; i < number.length; i++) {
sum = sum + number[i];
double average = sum / number.length;
System.out.println("Average value of your input is: " + average);
System.out.println();
//return average;
if (x > average) {
largerList[largerIndex] = x; //add negative input to negativeList array
largerIndex = largerIndex + 1;
}
}
for (int i = 0; i < largerIndex; i++) {
System.out.println(largerList[i]);
}
return 0;
}
}
to answer the main question...
However, my problem is that when I run my program the output window is completely blank. I assume this is because I did not call in my method to the main method. However, I am not sure how to write that code.
public static void main(String[] args) {
new Average().average(new double[10]);
}
Or maybe you are thinking something like this...
public static void main(String[] args) {
double[] numbers = {2,3,4,5,6,4,3,2,1,3};
new Average().average(numbers);
}
A output run from above (with the doubles given):
Please enter 10 floating-point numberes.
If more than 10 values are entered, the numbers following 10 are ignored.
If less than 10 numbers are entered, the program will wait for you to enter 10.
2
3
3
4
1
2
3
4
5
1
Average value of your input is: 0.2
Average value of your input is: 0.5
Average value of your input is: 0.9
Average value of your input is: 1.4
Average value of your input is: 2.0
Average value of your input is: 2.4
Average value of your input is: 2.7
Average value of your input is: 2.9
Average value of your input is: 3.0
Average value of your input is: 3.3
1.0
1.0
1.0
Press any key to continue . . .
If you have question about the code itself, then it would be better to create a new question or edit it to make it more clear.
Good luck with your coding.
Your method average() takes an array of doubles, but then retrieves an other array from standard input. That doesn't make sense.
Either get the doubles and pass them to the method, or don't pass them to the method and get them from standard input.
What you need to do is create an instance of Average class in your main method and call the average() method.
Why parse double array in your average() method when you take the input from user?
well,you are using a non static method "average()" for your task which needs an instances of the class to run which are not creating anywhere.so there are only two options:-
#1.create an instances of your class then call it.
public static void main(String... s)
{
Average obj=new Average();
obj.average();
}
#2.make "average()" a static method by adding static keyword.
public static double average()
{
//your code.....
}
public sttatic void main(String... s)
{
average();
}
your dont need to keep an argument in your method.

Categories

Resources