Java sentinel - reading text file into array - java

I've written a Java program which reads a series of real numbers from a text file into an array. I would like to use -1.0 as a sentinel so that scanner stops reading from the file when it reaches -1.0.
I'm struggling to insert the sentinel in the correct position, and also unsure if this should be done with an if or while statement. Any help much appreciated:
import java.util.Scanner;
import java.io.File;
import java.io.FileNotFoundException;
public class CalculatingWeights {
public static void main(String[] args) throws FileNotFoundException {
//Create file and scanner objects
File inputFile = new File("in.txt");
Scanner in = new Scanner(inputFile);
//declare variables
double [] myArray = new double [100];
int i = 0;
double min = myArray[0];
double max = myArray[0];
//Read numbers from file, add to array and determine min/max values
while(in.hasNextDouble()) {
myArray[i] = in.nextDouble();
if(myArray[i] < min) {
min = myArray[i];
}
if(myArray[i] > max) {
max = myArray[i];
}
i++;
}
//Calculate and print weighting
for(int index = 0; index < myArray.length; index++) {
double num = myArray[index];
double weighting = (num - min) / (max - min);
System.out.printf("%8.4f %4.2f\n", num, weighting);
}
}
}

without changing a lot of your code use this
double [] myArray = new double [100];
int count = 0;
double min = myArray[0];
double max = myArray[0];
//Read numbers from file, add to array and determine min/max values
while(in.hasNextDouble()) {
myArray[count] = in.nextDouble();
//sentinel
if(myArray[count]==-1.0)
break;
if(myArray[count] < min) {
min = myArray[count];
}
if(myArray[count] > max) {
max = myArray[count];
}
count++;
}
//Calculate and print weighting
for(int index = 0; index < count; index++) {//<-----NOTE HERE: as the array is filled upto "count"
double num = myArray[index];
double weighting = (num - min) / (max - min);
System.out.printf("%8.4f %4.2f\n", num, weighting);
}

Related

Creating array from range of numbers

I need to create an array of doubles given a max and min and interval. So array will look something like {2.9, 4.9, 6.9,... etc}
I am getting an array of zeros.
public class FoolinAround {
public static void main(String[] args) {
double min = 2.9;
double max = 20.6;
double gap = 2.0;
double count = (max - min) / gap + 2; // as will need first and last
// element also
double array[] = new double[(int) count];
for (int j = 0; j < array.length; j++) {
double i = array[j];
min = min + gap;
}
for (double k : array) {
System.out.print(array[(int) k] + ",");
}
}
}
It appears you are missing the assignment to your array (array[j] = something;). It appears from your explantation that array is supposed to contain the results. If I understand the problem you are trying to solve, this looks like a solution.
public class FoolinAround {
public static void main(String[] args) {
double min = 2.9;
double max = 20.6;
double gap = 2.5;
double count = (max - min) / gap + 2; // as will need first and last
// element also
double array[] = new double[(int) count];
for (int j = 0; j < array.length; j++) {
array[j] = min + (j*gap);
}
for (double k : array) {
System.out.print(array[(int) k] + ",");
}
}
}
I didn't verify that this calculation will give you the correct size for your array: double count = (max - min) / gap + 2;. I suggest that you verify this calculation. Since you are relying on truncation, rather than rounding, you may have an off-by-one error.
Here is how
double[] array = DoubleStream.iterate(min, prev -> prev + gap)
.limit(count)
.toArray();
Link to DoubleStream
The problem that I found was with the assignment and the for-each loop. Here is how you can do it:
double min = 2.9;
double max = 20.6;
double gap = 2.0;
double count = (max - min) / gap + 2.0;
System.out.println(count);
double array[] = new double[(int) count];
for (int j = 0; j < array.length; j++) {
// double i = array[j]; /*Not sure why this assignment is used
// here?*/
array[j] = min;
min += gap;
}
for (double k : array) {
System.out.print(k + "\n"); // Here k is the double value from the
// array. array[(int)k] will give you
// element of array indexed at the
// element of array.
}

How to use an array as type double?

I'm first using a scanner for user input and then calculating the mean.
I keep getting the error "lossy conversion from double to int".
It works when I use everything as type integer, but when calculating the mean it just converts it to an integer and it most of the time the mean isn't a whole number.
import java.util.Scanner;
public class CalculateMean {
public static void main(String[] args) {
Scanner enterValues = new Scanner(System.in);
System.out.println("Enter the number of values. ");
double n = enterValues.nextDouble();
double[] set = new double[n];
System.out.println("Enter values.");
for(double x=0; x<n; x++) {
set[x] = enterValues.nextDouble();
}
double sum = 0;
for(double cnt=0; cnt < set.length; cnt++) {
sum += set[cnt];
}
double mean = sum / n;
System.out.println("The average of the values is " + mean);
}
}
Even if the array element type is double, the index type is int. So your n, x, and cnt should be int, as you're using them to index into the array.
See the comment markers below:
import java.util.Scanner;
public class CalculateMean {
public static void main(String[] args) {
Scanner enterValues = new Scanner(System.in);
System.out.println("Enter the number of values. ");
int n = enterValues.nextInt(); // <== They won't give you 6.3 values, will they?
double[] set = new double[n];
System.out.println("Enter values.");
for (int x = 0; x < n; x++) { // <==
set[x] = enterValues.nextDouble();
}
double sum = 0;
for (int cnt = 0; cnt < set.length; cnt++) { // <==
sum += set[cnt];
}
double mean = sum / n;
System.out.println("The average of the values is " + mean);
}
}
To iterate the loop and in size of array use int not double like:
int n = enterValues.nextInt();
double[] set = new double[n];
...
for(int x=0; x<n; x++)
....
for(int cnt=0; cnt < set.length; cnt++)
Here is the code
package newPack;
import java.util.Scanner;
public class CalculateMean
{
public static void main(String[] args)
{
Scanner enterValues = new Scanner(System.in);
System.out.println("Enter the number of values. ");
int n = enterValues.nextInt();
double[] set = new double[n];
System.out.println("Enter values.");
for(int x=0; x<n; x++)
{
set[x] = enterValues.nextDouble();
}
double sum = 0;
for(int cnt=0; cnt < set.length; cnt++)
{
sum += set[cnt];
}
double mean = sum / n;
System.out.println("The average of the values is " + mean);
}
}

Displaying odd values in an array

I am trying to display the odd numbers in an array, but only once per number (i.e. numbers[3] = 3,3,1; would only display 3 and 1 instead of 3, 3 and 1.)
this is the code that I have as of now, the program completely will create an with the specific length entered by the user and then will calculate the max min, and odd values in the array.
import java.util.Scanner;
public class ArrayLab
{
static Scanner input = new Scanner (System.in);
public static void main(String[] args)
{
System.out.println("Enter the number of numbers: ");
final int NUMBER_OF_ELEMENTS = input.nextInt();
double[] numbers = new double[NUMBER_OF_ELEMENTS];
System.out.println("Enter the numbers: ");
for (int i = 0; i < NUMBER_OF_ELEMENTS; i++)
{
numbers[i] = input.nextDouble();
}
input.close();
double max = numbers[0];
double min = numbers[0];
for (int i = 0; i < NUMBER_OF_ELEMENTS; i++)
{
if (numbers[i] > max)
{
max = numbers[i];
}
}
System.out.println("The max is: " + max);
for (int i = 0; i < NUMBER_OF_ELEMENTS; i++)
{
if (numbers[i] < min)
{
min = numbers[i];
}
}
System.out.println("The min is: " + min);
for (int i = 0; i < NUMBER_OF_ELEMENTS; i++)
{
if (numbers[i] % 2 != 0)
{
System.out.println ("The odd numbers are: " + numbers[i]);
}
}
}
}
thanks for any help.
Set<Integer> set = new HashSet<Integer>();
for (int i = 0; i < NUMBER_OF_ELEMENTS; i++)
{
if (numbers[i] % 2 != 0)
{
set.add(numbers[i]);
}
}
System.out.println ("The odd numbers are: " +set);
This can be done a lot simpler using Java8:
double[] d = Arrays.toStream(numbers).filter(d -> (d % 2) == 1).distinct().toArray();
for(double tmp : d)
System.out.println(tmp);
System.out.println("min: " + Arrays.toStream(numbers).min((a , b) -> new Double(a).compareTo(b)));
System.out.println("max: " + Arrays.toStream(numbers).max((a , b) -> (new Double(a).compareTo(b))));
For you're solution: you never eliminate repeating numbers, thus the duplicates remain in the array until you print all odd numbers and the maximum-number.
This elimination can be done in several ways:
Using Java8 as above
add all values to a Set, since these don't allow duplicate values
eliminate them in your own way (i won't provide any code for this since it's rather complicated to design an efficient solution for this)
Updated solution for what you need. And Please use a better coding standard. Do note the condition check !oddNumbers.contains(numbers[i]) is not very necessary as HashSet never takes any duplicate values.
import java.util.HashSet;
import java.util.Scanner;
public class ArrayLab {
static Scanner input = new Scanner(System.in);
public static void main(String[] args) {
System.out.println("Enter the number of numbers: ");
final int NUMBER_OF_ELEMENTS = input.nextInt();
double[] numbers = new double[NUMBER_OF_ELEMENTS];
System.out.println("Enter the numbers: ");
for (int i = 0; i < NUMBER_OF_ELEMENTS; i++) {
numbers[i] = input.nextDouble();
}
input.close();
HashSet<Double> oddNumbers = new HashSet<Double>(NUMBER_OF_ELEMENTS);
double max = numbers[0];
double min = numbers[0];
for (int i = 0; i < NUMBER_OF_ELEMENTS; i++) {
if (numbers[i] > max) {
max = numbers[i];
}
if (numbers[i] < min) {
min = numbers[i];
}
if (numbers[i] % 2 != 0 && !oddNumbers.contains(numbers[i])) {
oddNumbers.add(numbers[i]);
}
}
System.out.println("The max is: " + max);
System.out.println("The min is: " + min);
System.out.println("The odd numbers are: " + oddNumbers);
}
}
A more meaningful solution to your approach would be as follows:
int[] tempArray; //temporary array to store values from your original "array"
int count=0;
for(int i=0; i<numbers.length; i++) {
if(numbers[i]%2 != 0) {
count++;
}
}
tempArray = new int[count]; //initializing array of size equals to number of odd digits in your array
int j = 0;
for(int i=0; i<numbers.length; i++) {
boolean check = true;
for(int k=0; k<j; k++) {
if(tempArray[k] == numbers[i]) {
check = false; //this will prevent duplication of odd numbers
}
}
if(numbers[i]%2 != 0 && check) {
tempArray[j]=numbers[i];
j++;
}
}
//Now print the tempArray which contains all the odd numbers without repetition
A few people have mentioned sets, but there is a different way as well. Simply sort the array, then scan through it, checking each number against the last one printed. i.e.,
int lastPrinted = 0;
// Sort the array
Arrays.sort(numbers);
System.out.print("The odd numbers are: ");
// Scan through the array
for (int i = 0; i < NUMBER_OF_ELEMENTS; i++)
{
// if it's odd and doesn't match the last one...
if (numbers[i] % 2 != 0 && numbers[i] != lastPrinted)
{
// ...print it and update lastPrinted
System.out.print( "" + numbers[i] );
lastPrinted = numbers[i];
}
}
System.out.println("");
As a side note, you really don't have to scan through the array twice to find your max and min, you can do that in one go.
I think you can use inbuilt hashmap class and its method to achieve the task without affecting the complexity of algorithm to any great extent .
import java.util.HashMap;
public class Hashing {
public static void main(String[] args) {
//declare a new hasmap
HashMap<Integer, Integer> map = new HashMap<>();
//consider Arr as your Array
int Arr[] = {3,3,1,4,5,5,7,8};
//traverse through the array
for(int i=0;i<Arr.length;i++){
//check if the required condition is true
if(Arr[i]%2==1){
/*now we insert the elements in the map but before
that we have to make sure that we don't insert duplicate values*/
if(!map.containsKey(Arr[i])){// this would not affect the complexity of Algorithm since we are using hashMap
map.put(Arr[i], Arr[i]);//We are storing the Element as KEY and as VALUE in the map
}
}
}
//now We can get these element back from map by using the following statement
Integer[] newArray = map.values().toArray(new Integer[0]);
//All the required elements are now present in newArray
for(int ele:newArray){
System.out.println(ele);
}
}
}

Find largest average set of results in array

I have a 2D array and I want to find the largest average set of results, so far I can calculate the average of each set of results but I'm not sure how to select the biggest from the output.
My code:
static int[][] studentMarksArray = new int[10][3];
for(int i=0;i<10;i++){
double total = (studentMarksArray[i][0]*studentMarksArray[i][1]*studentMarksArray[i][2])/3;
System.out.println(total);
}
An attempted solution:
for(int i=0;i<10;i++){
double total = (studentMarksArray[i][0]*studentMarksArray[i][1]*studentMarksArray[i][2])/3;
double newTotal = total;
if(newTotal>total){
newTotal = total;
System.out.println(newTotal);
}
}
Like this:
double max = 0;
for(int i = 0; i < 10; i++){
double total = (studentMarksArray[i][0]*studentMarksArray[i][1]*studentMarksArray[i][2])/3;
max = Math.max(max, total);
}
or if you want the index:
int index = -1;
double max = 0;
for(int i = 0; i < 10; i++){
double total = (studentMarksArray[i][0]*studentMarksArray[i][1]*studentMarksArray[i][2])/3;
if(Math.max(max, total) == total) {
index = i;
max = total;
}
}
Ok if you want to have an array of averages at the end, do this:
int index = -1;
double max = 0;
double [] averages = new double[10];
for(int i = 0; i < 10; i++){
double total = (studentMarksArray[i][0]*studentMarksArray[i][1]*studentMarksArray[i][2])/3;
averages[i] = total;
if(Math.max(max, total) == total) {
index = i;
max = total;
}
}
add this after variable initialisation
int largest=0,lp=0;
add this before forloop ends but after calculating total
if(largest<total){
largest=total;lp=i;
}
at the end of forloop you will have largest average in the variable largest and its position in variable i.
You can save the outPut at every step in to a priority queue(which saves the elements in natural ordering) and in the last step the pull() the highest value from this priority queue.
import java.util.PriorityQueue;
public class Test1 {
public static void main(String[] arg){
int[][] studentMarksArray = new int[10][3];
PriorityQueue<Double> pq = new PriorityQueue<Double>();
for(int i=0;i<10;i++){
double total = (studentMarksArray[i][0]*studentMarksArray[i][1]*studentMarksArray[i][2])/3;
System.out.println(total);
pq.add(total);
}
System.out.println(pq.poll());;
}
}

No result in console, most likely a logical error

I'm relatively new to the world of OOP, and for some reason, the console of IntelliJ and Eclipse doesn't give me an output in the console for the following program. I'm trying to store 12 numbers into an array using scanner and to find the standard deviation, mean, lowest number, and highest number. Can anyone spot what's wrong?
import java.util.Arrays;
import java.util.Scanner;
public class untitled
{
public static void main(String[] args)
{
Scanner in = new Scanner(System.in);
int[] grades = new int[12];
int size = grades.length;
for (int i = 0; i < size; i++)
{
grades[i] = in.nextInt();
}
Arrays.sort(grades);
int low = grades[0];
int high = grades[11];
int sum = 0;
for (int i: grades)
{
sum += i;
}
int m = sum / size;
double var = 0;
double variance;
double sd;
for (int i = 0; i < size; i++)
{
var = var + ((grades[i] - m) * (grades[i] - m));
}
variance = (int) var / size;
sd = Math.pow(variance,.5);
String lowest = ("Lowest Grade:" + low);
String highest = ("Highest Grade:" + high);
String average = ("Average Grade:" + m);
String standdev = ("Standard Dev.:" + sd);
System.out.println(lowest);
System.out.println(highest);
System.out.println(average);
System.out.println(standdev);
}
}
Thanks.
What you have done is to accept 12 inputs.. try entering 12 inputs in console and then your output will appear..
And yeah this doesnt seem to use OOP concepts. Please refer this link for more info regarding OOPS :
http://en.wikipedia.org/wiki/Object-oriented_programming
The problem is, that you need to enter values first, before the calculation and output can continue. Without having some printed text on the console (like "Enter a new number: ") the console will just stay empty.
You could either enter 12 numbers, or fill the list automatically with Random values. In this case the output will immediately be visible on the console.
...
nt[] grades = new int[12];
int size = grades.length;
Random random = new Random();
for (int i = 0; i < size; i++) {
grades[i] = random.nextInt(15); // value between 0 and 14
}
Arrays.sort(grades);
int low = grades[0];
...

Categories

Resources