Implementing methods: search, load and print - java

Please see my comments in the code to better explain things. Basically having issues with the methods below. I can get the load method to run but I am unsure whether the numbers entered by the user are actually being stored in the array.
In addition, the search method has been throwing things off and i think its going in a loop.
See below for more. Thank you in advance.
import java.util.Scanner;
public class MyContainer {
private int[] values;
private int size;
public MyContainer(){
values=new int[50];
size=0;}
//Load Method - Display a message to the user
//and get positive intergers from user
public void load()
{
int input;
Scanner in = new Scanner(System.in);
System.out.println("Enter a series of positive integers (Negative to Terminate): ");
input=in.nextInt();
while (input >=0) {
values[size]=input;
size++;
input=in.nextInt();
}
}//End Load
//Compute Average from the above entered numbers
public double computeAverage() {
double avg= 0.0;
int count = 0;
while(values[size] >=0)
{avg = avg + values[size];
count++;
}
size = size + 1;
avg = avg / size;
return avg;
}
//Get user input to search for a number in the array
public boolean search(int myInt){
while(values[size] >=0) {
if (values[size] == myInt){
return true;}
else{
size++;}
}
return false;
}
//print the position of the number
public void print(){
for(int i=0;i>=size;i++) {
System.out.println("The number at position " + i + " is " + values[i]);
}
}
}
That is what I have so far. I also have created a tester class for the above container.
class Tester {
public static void main(String[] args) {
MyContainer in = new MyContainer();
in.load();
in.computeAverage();
in.search(); //i know for a fact this is wrong just stuck
in.print();
}
}
Any advise/help would be greatly appreciated. My professor is terrible at teaching and the book only partially explains things.

Your search() method has parameters that you aren't passing.
you declare it as...
public boolean search(int myInt) {
while (values[size] >= 0) {
if (values[size] == myInt) {
return true;
} else {
size++;
}
}
return false;
}
but call it with...
in.search();
This code won't even compile. For argument sake I set this to 5.
In your computeAverage() method, this is an infinite loop...
while (values[size] >= 0) {
avg = avg + values[size];
count++;
}

The main problem I believe you are running into is the reuse of your size variable. In the load function it will work as expected say for loading in 10 numbers size will be 10 and elements 0->9 in values will have numbers in them. However when you get to computeAverage size will still be 10. So you are in an infinite loop.
while(values[size] >= 0) {
avg = avg + values[size];
count++;
}
First iteration you will check values[10] (which is wrong remember valid elements are only in 0->9 if size is 10). Next iteration avg and count are increased but size remains the same so you will add the same number to avg and continue in the loop. You should use a different conditional for your while loops in computeAverage and search. The last negative number entered to quit will not be in the array; you will need to use something else. As a hint it will involve count and size.

Related

How to pass method output into an array element?

The basis of my problem is here: https://github.com/experiencethebridge1/primeGap
Bottom line, I want to create an array in which the output of a method will populate the elements of the new array.
This is not homework.
package primenumbermethod;
import java.util.Scanner;
public class PrimeNumberMethod {
public static void main(String[] args) {
System.out.print("How many prime numbers do you want to work with? ");
Scanner input = new Scanner(System.in);
int arraySize = input.nextInt();
// Invoke printPrimeNumbers method
System.out.println("If I can ever get it to work, the number of the "
+ "elements in the array I want to build will be " + arraySize +".");
System.out.println();
printPrimeNumbers(arraySize);
// How can I read parts of a method into elements of an array?
int[] myList = new int[arraySize];
}
public static int printPrimeNumbers(int numberOfPrimes) {
final int NUMBER_OF_PRIMES_PER_LINE = 10; // Display 10 per line
Scanner input = new Scanner(System.in);
System.out.print("What number do you want to start from? ");
int number = input.nextInt();
int count = 0; // Count the number of prime numbers
// Repeatedly find prime numbers
while (count < numberOfPrimes) {
// Print the prime number and increase the count
if (isPrime(number)) {
count++; // Increase the count
if (count % NUMBER_OF_PRIMES_PER_LINE == 0) {
// Print the number and advance to the new line
System.out.printf("%-15d\n", number);
} else {
System.out.printf("%-15d", number);
}
}
number++;
}
return 0;
}
// Method for checking if number is prime
public static boolean isPrime(int number) {
for (int divisor = 2; divisor <= number / 2; divisor++) {
if (number % divisor == 0) {// If true, number is not prime
return false; // Number is not a prime
}
}
return true; // Number is prime
}
}
Tried using global variables, abstraction does not apply (but could).
The main method initiates the program, then traces to method printPrimeNumbers, then into method boolean isPrime. I want to return the output of that method into a new array...
The array size will be defined by the user input <"How many prime numbers do you want to work with? ">, and then <"What number do you want to start with?>
Problem, I can't seem to pass the output of a method into the elements of an array.
Thoughts?
I would suggest you should restructure your code in the following way:
public static void main(String[] args) {
int numberOfPrimes = readIntFromCommandLine...;
int numberToStartWith = readIntFromCommandLine...;
int[] primeNumbers = getPrimeNumbers(numberOfPrimes, numberToStartWith);
// maybe extract this to another method as well
for (int prime : primeNumbers) {
// do whatever you want with prime, e.g. print it - or sum it, or multiply or whatever
}
}
public static int[] getPrimeNumbers(int amount, int from) {
int[] primes = new int[amount];
int count = 0;
/* now put your current prime logic here and whenever you
find a prime set primes[count] = newlyFoundPrime; */
}
public static boolean isPrime(int number) { /* stays the same */ }
It is generally a good idea to only ask for user input at a well defined point in your code, not all over the place. Therefore I placed the two inputs at the front. Another generally good idea is to make every method (maybe except for the main method) only do one thing. Your isPrime is a good example of that. Moving the printing logic out of getPrimeNumbers simplifies that method and lets you handle the printing at another, dedicated place.

Why does my code only execute once

I want to print all the even numbers, but it only gives me 0!!
public class DataType {
public static void main(String[] args){
int number=0;
int max=20;
do{
System.out.println("this is an even number"+ number);
number++;
}while(number<=max&&EvenNumber(number));
}
public static boolean EvenNumber(int a)
{
if((a%2)==0)
{
return true;
}else
return false;
}
}
that is what your condition states: do while both conditions meet!, afters doing number++ for the 1st time the left side of the condition returns false and your loop is done!
you mean for sure:
do {
if (isEvenNumber(number)) {
System.out.println("this is an even number" + number);
}
number++;
} while (number <= max);
remember, following code means
while(number <= max && EvenNumber(number))
while BOTH conditions meet...
After number++;, number becomes 1, and thus the condition becomes false, and the loop terminates.
I assume, you wanted to do
do {
if (isEvenNumber(number)) System.out.println(number);
number++;
} while(number<=max);
Because in your code, If number is equals to 1, while condition is false
If you intend to find all even number between [0, 20] you may change your code to this version:
public static void main(String[] args) {
int max=20;
for (int number = 0; number <= max; number++) {
if (number % 2 == 0) {
System.out.printf("%d is an even number.\n", number);
}
}
}
This reads like:
start with number 0
while number not past 20
if number is even print it
continue with next number
Because in the second iteration the loop will exit.
if you want to print even numbers then the code should be
do{
if(EvenNumber(number)) {
System.out.println("this is an even number"+ number);
}
number++;
}while(number<=max );

Trying to solve a palindrome using integer arrays

I am writing a program that would help me find whether the number entered is a palindrome or not but i am trying it using arrays. And i would like to know if that is even possible?? And if it is possible then what am i doing wrong.
I have marked the code where i think the problem lies but feel free to suggest anything.!!!!
Thanks!!!
import java.util.Scanner;
public class palindrome
{
public static void main(String args[])
{
int size = 10,i,j,flag=0;
int num[] = new int[size];
Scanner sc = new Scanner(System.in);
System.out.println("Enter the size of the number ");
size = sc.nextInt();
System.out.println("Enter the number ");
for(i=0;i<size;i++)
{
num[i]=sc.nextInt();
}
i=size-1;
for(j=0;j<(size/2);j++,i--)
{
if(i>(size/2))
{
if(num[i]==num[j])
{
flag = 1;
}
}
}
if(flag==1)
{
System.out.println("The number is a palindrome");
}
else
System.out.println("The number is not a palindrome ");
}
}
Edit: Guys the problem is actually solved because i was doing a blunder mistake i.e. i was asking the user to enter the number in the form of an arry but i was not actually entering the digits in the number one by one instead i was entering the whole number in the first iteration.
But still a lot of thanks for the replies. I would still try your ideas and let you guys know. Thanks
:)
Try
public boolean isPalindrome(int[] num){
for(int i = 0 ; i < num.length/2 ; i++) {
if(num[i]!=num[num.length-(i+1)]) return false;
}
return true;
}
Yes it's possible, moreover, it's possible by using ArrayList, String - whatever you like. In order to write down a correct implementation, first decompose your current solution:
// Extract a method, do not cram all code into main()
// note: all you need is array, to get size of the array, put value.length
private static boolean isPalindrome(int[] value) {
...
}
public static void main(String args[]) {
int userInput[];
...
if (isPalindrome(userInput)) {
System.out.println("The number is a palindrome");
}
else {
System.out.println("The number is not a palindrome");
}
}
Now, let's implement isPalindrome():
private static boolean isPalindrome(int[] value) {
if (null == value)
return true; //TODO: or false, or throw exception
for (int i = 0; i < value.length / 2; ++i)
if (value[i] != value[value.length - 1 - i])
return false;
return true;
}
The easiest and most intuitive way (imo) to check for palindromes is through recursion. The idea is simple:
Is the first and last char the same?
YES Remove first and last char and check first and last char of the new String
NO There is no palindrome.
When the input is only 1 char then it's trivial.
Have a look at this code:
private void isPalindrome(String number){
if(number.length() == 1){
System.out.println("yes");
}else if(number.charAt(0) == number.charAt(number.length()-1)){
isPalindrome(number.substring(1, number.length()-1));
}else{
System.out.println("no");
}
}
Testing with:
isPalindrome(String.valueOf(232)) Returns "yes"
isPalindrome(String.valueOf(23)) Return "no"
Of course this also works with Arrays just as easily. Replace the parameter with an array and search through the indices the same way. When cutting down the array just create a new smaller array without first and last index of the previous array.
Your class has several issues:
First you're not checking if a number is a palindrome or not. Your algorithm is flawed
Second, you're asking to enter a size but in the end, the user inputs it but you don't use it yourself. Instead, you're using that introduced value in the number array.
Here's how you should do it.
public class Palindrome {
private static boolean isPalindrome(int[] array) {
for (int i = 0, j = array.length-1; i < j; i++, j--) {
if (array[i] != array[j]) {
return false;
}
}
return true;
}
public static void main(String args[]) {
Scanner scanner = new Scanner(System.in);
System.out.print("How many numbers do you want to enter? ");
int size = scanner.nextInt();
int[] numbers = new int[size];
for (int i = 0; i < size; i++) {
System.out.printf("Enter number %s: ", i+1);
numbers[i] = scanner.nextInt();
}
if (isPalindrome(numbers)) {
System.out.println("The number is a palindrome");
} else {
System.out.println("The number is not a palindrome");
}
}
}

How can I use get methods in an Array?

This assignment is comprised of creating a program to read up to (but not more) 25 test grades, then report the number of grades entered; and compute the arithmetic mean (average) and standard deviation of the grades. I don't understand how to use the get methods I have created so I can implement it in my program. Here is my code so far
package my.meancalculator;
import javax.swing.JOptionPane;
import javax.swing.JFrame;
public class MeanCalcUI extends javax.swing.JFrame {
private double average;
private double stdDeviation;
public double[] gradeArray;
public int numElem;
public double sum;
public int i;
public double numGrades;
public MeanCalcUI() {
initComponents();
}
public double getAverage(double[] gradeArray, int numElem) {
double sum = 0;
for (int i = 0; i < numElem; i++) {
sum = sum + gradeArray[i];
}
return (sum / numElem);
}
public double getStdDev(double[] gradeArray, int numElem, double average) {
double sum = 0;
for (int i = 0; i < numElem; i++) {
sum = sum + Math.pow((gradeArray[i] - average), 2);
}
return Math.sqrt(sum / numElem);
}
/**
* This method is called from within the constructor to initialize the form.
* WARNING: Do NOT modify this code. The content of this method is always
* regenerated by the Form Editor.
*/
#SuppressWarnings("unchecked")
private void btnExitActionPerformed(java.awt.event.ActionEvent evt) {
System.exit(0);
}
private void btnEnterGradesActionPerformed(java.awt.event.ActionEvent evt) {
gradeArray = new double[25];
JFrame frame = new JFrame();
boolean enterGrades = true;
while (enterGrades) {
try {
String gradeInput = JOptionPane.showInputDialog(frame,
"Enter Grade",
"Enter Grade",
JOptionPane.PLAIN_MESSAGE);
if ((gradeInput != null) && (gradeInput.length() > 0)) {
gradeArray[i] = Double.parseDouble(gradeInput);
average = getAverage;
numElem = numGrades + 1; //right here I know it doesn't work but i have no idea on how to make it the total of the grades entered. numElem is what the sum is getting divided by to find the average
txtNumGrades.setText((numGrades) + "");
txtMean.setText(average);
txtStdDeviation.setText(stdDeviation);
} else {
enterGrades = false;
}
} catch (NumberFormatException e) {
JOptionPane.showMessageDialog(frame,
"Your input must be numeric!",
"Bad Data!",
JOptionPane.ERROR_MESSAGE);
}
}
}
Also, I don't know how I can make another catch block in case the user enters more than 25 grades. Here is my program guidelines from my teacher so you can have a better understanding on what it looks like and what is exactly being asked. http://homepages.uc.edu/~thomam/OOProg_1/assignment5.html
Can you guys help me out?
EDIT: Another question. How can I make the variable numElem work? I don't know how I can make that equal to the sum of all the grades entered.
The main problem you are asking about is trying to access those other methods you wrote, like getAverage(). You need to always pass those methods parameters; a name without parentheses after it is treated as just a variable, but through the magic of syntax the moment you put some parentheses with parameters, it becomes a method call: getAverage(gradeArray, numberOfGradesInput).
That said, there are faster ways to do most of what you're working on.
////////// CLASS FIELDS //////////
private double[] gradeArray = new double[25];
private int numberOfGradesInput = 0;
// You do not need any other fields! None! This is all you need to remember!
////////// BUTTON PRESSED //////////
if (numberOfGradesInput == 25) {
// We've already finished entering the max # of grades
JOptionPane.showMessageDialog(frame,
"You've already entered the maximum of 25 grades.",
"Error",
JOptionPane.ERROR_MESSAGE);
return;
}
do {
String gradeInput = JOptionPane.showInputDialog(frame,
"Enter Grade",
"Enter Grade",
JOptionPane.PLAIN_MESSAGE);
// When we receive empty/null input, we're done entering grades
if (gradeInput == null || gradeInput.length() == 0) break;
double gradeValue = 0d; // Set to avoid 'may be unset' compiler error
try {
gradeValue = Double.parseDouble(gradeInput);
} catch (NumberFormatException e) {
JOptionPane.showMessageDialog(frame,
"Your input must be numeric!",
"Bad Data!",
JOptionPane.ERROR_MESSAGE);
continue; // start over again
}
// Put the grade into the array and update the number of grades entered
gradeArray[numberOfGradesInput] = gradeValue;
numberOfGradesInput++;
// Add to the grade total
txtNumGrades.setText(Integer.toString(numberOfGradesInput));
// ---> You should look at using a number formatter so you don't get a million digits
double gradeAverage = getAverage(gradeArray, numberOfGradesInput);
txtMean.setText(Double.toString(gradeAverage));
double standardDeviation = getStdDev(gradeArray, numberOfGradesInput, gradeAverage);
txtStdDeviation.setText(Double.toString(standardDeviation));
} while (numberOfGradesInput < 25);
This code should work a bit more smoothly. Notice how it keeps track of the total number of grades input in numberOfGradesInput and only loops until either a blank entry is encountered or it's reached its maximum. Using enterGrades to track whether you're in the loop works, but the break statement is a much faster, cleaner, and more readable way to do it.
I must warn you to be extremely cautious of your fields! You are declaring a bunch of public fields at the top, then using them as local variables and loop variables. You are even hiding some of these variables with parameter names:
public int numElem;
-vs-
public double getAverage(double[] gradeArray, int numElem) {
This should be avoided to maintain clean code and avoid bugs. The best way to do it is to avoid using public fields whenever possible. By and large, if you only need a value in a certain method once at a time and don't need to remember it in between executions, it should not be a field, let alone a public one. Use instance variables inside your method instead! If possible, create these variables only inside their own loop rather than reusing them. Think of it this way: the farther away a variable can be touched, the more can go wrong. A quick example:
You defined the field public int i;. Let's say you're using that as a loop variable in getAverage(): for (i = 0; i < numElements; i++) {. Now, you also want to use a loop in a method called, say, enterGrades():
for (i = 0; i < 25; i++) {
getAverage(gradeArray, i);
}
Every time you jump over to getAverage(), it's messing with the exact same value you're trying to use to control the other loop you're already in. Problems will occur!
Again, if you don't need variables outside their loop, define them inside it: for (int i = 0; .... If you need to know what number it ended on, just define a local variable right before the loop. And even if you aren't using them, defining fields like public int i when you are accustomed to using those names for loops etc. is just inviting disaster: if you forget to define your local variable i, your IDE probably won't warn you that you're using the public field.
Best of luck.
This line of code:
average = getAverage; // from your if((gradeInput != null) && (gradeInput.length() > 0)) block;
The "getAverage(args)", the average = getAverage() <-- requires parameters to be passed into the method for further operation;
Replace "args" in the brackets with the parameters it requires and it should work;

Need help writing a program that finds the highest and second highest number is a series

The program is designed for the user to enter a series of numbers until the user enters the sentinel which i set to the value of 0. After the user enters the sentinel the program is supposed to print the highest number and the second highest number in that list. The trouble I'm having is where I expect the second highest number to be it prints 0 instead.
Is there a more elegant way of solving this problem by using the ?: operator? Is it possible?
import acm.program.*;
public class LargestAndSecondLargest extends ConsoleProgram {
public void run() {
int a = 0;
int b = 0;
while (true) {
int value = readInt(" ?: ");
if (value == SENTINEL) break;
if (value > a) {
a = value;
}
else if (value > b) {
b = value;
}
}
println("the largest value is " + a);
println("the second largest number is" + b);
}
private static final int SENTINEL = 0;
}
There are two issues:
The second comparison is wrong.
When you encounter a new highest number, you need to shift the previous highest number into the second-highest slot. Otherwise the sequence 1, 2, 3 would produce 3 and 1 as the two highest numbers.
else if ( b > value )
The above else if condition should be: -
else if ( value > b )
Else, your b will never get changed, if you are entering only positive numbers, and hence the 2nd largest value will be 0.
Also see 2nd requirement in #NPE's answer that is necessarily required.
insert the values into an array. Sort the array then assign the top two values from the array into your output. if only one value is given depending on requirements set them both to the same value or one to 0.
Here my solution (that you can adapt with your superclass):
public class LargeAndSecondLargest {
public static void main(String[] args) {
new LargeAndSecondLargest().run("1 2 2");
}
public void run(String input) {
final int SENTINEL = 0;
int currVal;
Scanner scanner = new Scanner(input);
List<Integer> numbers = new ArrayList<>();
while (scanner.hasNextInt() && ((currVal = scanner.nextInt()) != SENTINEL)) {
numbers.add(currVal);
}
printFirstAndSecondLargest(numbers);
}
private void printFirstAndSecondLargest(List<Integer> numbers) {
Collections.sort(numbers, Collections.reverseOrder());
System.out.println("the largest value is " + numbers.get(0));
System.out.println("the second largest number is " + numbers.get(1));
}
}

Categories