DecimalFormat the answer? [duplicate] - java

This question already has answers here:
How do I compare strings in Java?
(23 answers)
Closed 10 years ago.
Please forgive my ignorance, I'm a beginner.
Can anyone tell me why I am getting my error code in the if/else statement below? I think my result for the ln multiplication is is not exactly the same as the standard multiplication (there is a .00000000006 of a difference or something like that). Is there a work around for this? I have tried to use DecimalFormat but to no avail.
If I add:
DecimalFormat fmt = new DecimalFormat ("0.###");
to the tester and
if (fmt.format(z) != fmt.format(result)){
to the if statement I receive my own same error statement. What is wrong!?
Thank you very much.
Joe
import java.util.Scanner;
import java.lang.Math;
import java.text.DecimalFormat;
public class Logs {
//integer x field & encapsulation
private static double x;
// x encapsulation
public double getX(){
return x;
}
public void setX (double ex){
if (ex >= 0){
x = ex;
}
else{
System.out.println("You may not choose a negative number, 'x' = 0");
}
}
//integer y field
private static double y;
// y encapsulation
public double getY(){
return y;
}
public void setY (double why){
if (why >= 0){
y = why;
}
else{
System.out.println("You may not choose a negative number, 'y' = 0");
}
}
//tester
public static void main (String [] args){
Logs sample =new Logs();
Scanner var = new Scanner(System.in);
DecimalFormat fmt = new DecimalFormat ("0.###");
sample.setX (var.nextDouble());
sample.setY (var.nextDouble());
x = sample.getX();
y = sample.getY();
double z = (x*y);
double logX = Math.log(y);
double logY = Math.log(x);
double logZ = (logX +logY);
double result = (Math.exp(logZ));
if (z != result){
System.out.printf("%s", "Incorrect answer: be a better coder");
}
else {
System.out.printf("%s %.3d %s %.3d %s %.3d",
"The product of the values you chose is: ", + z,
"\nln(x) + ln(y) is: ", + logZ,
"\nCompute to e: ", + result);
}
}
}

You're comparing string references rather than their values, and you want String.equals() e.g. z.equals(result)
However, I think what you're trying to do is compare two decimal numbers to a certain precision. It's more intuitive to calculate the difference and determine if that's within an acceptable error bound e.g.
if (Math.abs(z - result) < 0.01) {
// ok
}
See Math.abs(double a) for more details

I'd suggest to try
if (!fmt.format(z).equals(fmt.format(result))) {

Use BigDecimal instead of double
Use StrictMath instead of Math

I think it's because of double. For best practice use BigDecimal instead.
Please, take a look at "Why do I see a double variable initialized to some value like 21.4 as 21.399999618530273?".

Related

how do i make the user input a double?

can somebody correct me what i did wrong here? my goal was for the user to input a number on the parameter System.out.print("Available Amount Before Upgrade:" + df.format(availAmount1));
double upgradeAccessories= sc.nextDouble(); but i can't seem to see the issue
public static void main(String[] args)
{
DecimalFormat df = new DecimalFormat("#####");
Scanner sc = new Scanner(System.in);
double availAmount;
Car owner = new Car();
owner.owner("Marcus Laurence", 2014);
double availAmount1=owner.upgradeAccessories(availAmount);
double remainAmount=owner.upgradeAccessories(availAmount);
System.out.println("Owner:" + owner.name);
System.out.println("Model:" + owner.model);
System.out.print("Available Amount Before Upgrade:" + df.format(availAmount1));
double upgradeAccessories= sc.nextDouble();
System.out.println("Installed AC:" + owner.hasAC);
System.out.println("Installed Leather Seats:" + owner.hasLeatherSeats);
System.out.println("Installed Back Wipers:"+ owner.hasBackWipers);
System.out.println("Installed Fog Lights:" + owner.hasFogLights);
System.out.println("Amount Remaining After Upgrade:" + df.format(remainAmount));
}
public double upgradeAccessories(double availAmount)
{
if(availAmount == 25000)
{
availAmount -= 21500;
hasAC=true;
}
else if(availAmount == 40000)
{
availAmount -= 21500;
availAmount -= 14400;
hasAC=true;
hasLeatherSeats=true;
}
else if(availAmount == 50500)
{
availAmount -=21500;
availAmount -=14400;
availAmount -=6250;
availAmount -=3300;
hasAC=true;
hasLeatherSeats=true;
hasBackWipers=true;
hasFogLights=true;
}
return availAmount;
}
how do i make the user input a double?
You did this part fine - scanner.nextDouble() is all it takes. Here's a really simple standalone example, including output:
System.out.print("enter a double: " );
Scanner sc = new Scanner(System.in);
double d = sc.nextDouble();
System.out.println("d: " + d);
enter a double: 123.456
d: 123.456
So reading a double is not the issue. However, this line is suspicious:
double upgradeAccessories = sc.nextDouble();
Why? A few reasons..
It defines a new variable "upgradeAccessories" which is not used anywhere else – so it's reading a value (from sc.nextDouble()) and then doing nothing with it. This is something that an IDE (such as IntelliJ or Eclipse) will help you see – it will draw attention to unused code, like declaring a value that is never used.
The name of the variable – "upgradeAccessories" – is the same as the method name defined elsewhere in your code, namely:
public double upgradeAccessories(double availAmount)
So to fix your code, it seems that you probably want to replace this:
double upgradeAccessories = sc.nextDouble();
with something like this:
double next = sc.nextDouble();
owner.upgradeAccessories(next);
Also, the way you're comparing doubles is dangerous. Generally, fractional numbers are never exactly equal. Instead, of doing comparisons like this:
if (availAmount == 25000) { ... }
It's better to do something like greater-than-or-equal:
if (availAmount >= 25000) { ... }
Or if you're using only whole-number values, use integer instead of double, and then direct x == y comparisons will work fine.
In this segment of your code...
double availAmount;
Car owner = new Car();
owner.owner("Marcus Laurence", 2014);
double availAmount1=owner.upgradeAccessories(availAmount);
... you passed the "availAmount" in to a function as a parameter. You haven't given that variable any value yet. You just declared it. If you assign a default value to it like 0.0, does it work?

Need help adding methods in main class

Hello I'm working on a project for my java class, I'm supposed to write a code for a Algebra tutor that goes like this:
Write a program with a that displays a randomly generated problem that asks the user to solve for the y variable, takes input from the user, and prints "correct" if the user answered correctly and prints "incorrect" if not. Your main should give one problem and then exit. Use one or more methods to produce this behavior.
This is regarding the formula mx + b. So here is what I have so far, and works!
import java.util.Random;
import java.lang.Math;
import java.util.Scanner;
class Main {
public static void main(String[] arg){
double min_value = -100;
double max_value = 100;
double m_value = (int)(Math.random()*((max_value-min_value)+1))+min_value;
double x_value = (int)(Math.random()*((max_value-min_value)+1))+min_value;
double b_value = (int)(Math.random()*((max_value-min_value)+1))+min_value;
System.out.println("Given: ");
System.out.println("m = " + m_value);
System.out.println("x = " + x_value);
System.out.println("b = " + b_value);
System.out.print("What is the value of y? ");
Scanner user_input = new Scanner(System.in);
String user_answer = "";
user_answer = user_input.next();
int correct_answer = (int)m_value * (int)x_value + (int)b_value;
if (user_answer.equals(correct_answer))
System.out.println("You are correct!");
else
System.out.print("Sorry, that is incorrect. ");
System.out.println("The answer is " + correct_answer);
}
}
so even tho the output is correct, I need to break down the code into smaller methods, this is where Im getting confused on how to take a piece of that code and put it in another method that once it runs it calls for that method too and gives me the same output. I been ready the material given but the more I read it the more confuse I get. If anybody has any ideas or suggestions please let me know any info will be really appreciate. Thank you
Here's a quick rundown on methods, so it's not completely done yet. Ask, if you need more help! Good luck on your homework and on becoming one of the beast developers!
public class Main {
public static void main(String[] args) {
int a = 1; // give a value of 1
methodTwo(a); // sending the int a into another method
}
// Here's method number two
static void methodTwo (int a) { // it gives a's type and value
System.out.println(a); //Gives out a's value, which is 1
}
}
Technically you've solved the problem correctly, you are using one or more methods, but perhaps what you trying to do is a common code refactor called the extract method / extract function refactor Executing this type of refactor leads to much more readable and maintainable code, and is easy to do.
As a starter, identify code that repeats or looks similar, in your case, the following lines look ripe for extract method:
double m_value = (int)(Math.random()*((max_value-min_value)+1))+min_value;
double x_value = (int)(Math.random()*((max_value-min_value)+1))+min_value;
double b_value = (int)(Math.random()*((max_value-min_value)+1))+min_value;
Notice that the RHS of each line is identicial, so we can replace the explicit code with a method call like this:
double m_value = getRandomDoubleBetween(max_value, min_value);
double x_value = getRandomDoubleBetween(max_value, min_value);
double b_value = getRandomDoubleBetween(max_value, min_value);
private double getRandomDoubleBetween(double max_value, double min_value) {
return (int)(Math.random()*((max_value-min_value)+1))+min_value;
}
You can identify other areas of code that either contain repetition or perhaps some hard to understand code that would be more understandable if it was extracted into a method that had a name that reveals what the code is doing.
Please review this, you are comparing string with integer,
if (user_answer.equals(correct_answer))
This may help you:
import java.util.Scanner;
class Main {
public static void main(String[] arg) {
double min_value = -100;
double max_value = 100;
double m_value = generateRandom(max_value, min_value);
double x_value = generateRandom(max_value, min_value);
double b_value = generateRandom(max_value, min_value);
System.out.println("Given: ");
System.out.println("m = " + m_value);
System.out.println("x = " + x_value);
System.out.println("b = " + b_value);
checkAnswer(m_value, x_value, b_value);
}
private static void checkAnswer(double m_value, double x_value, double b_value) {
System.out.print("What is the value of y? ");
Scanner user_input = new Scanner(System.in);
String user_answer = "";
user_answer = user_input.next();
int correct_answer = (int) m_value * (int) x_value + (int) b_value;
if (user_answer.equals(String.valueOf(correct_answer))) {
System.out.println("You are correct!");
} else {
System.out.print("Sorry, that is incorrect. ");
System.out.println("The answer is " + correct_answer);
user_input.close();
}
}
static int generateRandom(double max_value, double min_value) {
return (int) ((int) (Math.random() * ((max_value - min_value)
+ 1)) + min_value);
}
}

Java swing - list.add issues

I'm creating a GUI for use in a judged sporting event. There are 6 judges and they each input their score into the GUI. They then hit calculate, and the program is meant to sort the numbers from low to high and then take the numbers from position 1 through 4 and give an average.
I have written the code for input via console and that works, but when I try my Gui the 'list.add' doesn't work. I don't know if I am meant to use something else.
btnCalculate = new JButton("Calculate");
btnCalculate.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
inGui = new Scanner (System.in);
double firstRun = getAverageOfRun(1);
double secondRun = getAverageOfRun(2);
double best;
if (firstRun > secondRun) {
best = firstRun;
} else {
best = secondRun;
}
textFieldRun1Score.setText(Double.toString(best));
}
private double getAverageOfRun (int runNumber) {
double total, avg;
int num1, num2, num3, num4, num5, num6;
List<Integer> list = new ArrayList<Integer>();
num1 = Integer.parseInt(textFieldRun1Score1.getText());
System.out.print(""+runNumber +": ");
list.add(textFieldRun1Score1.getText());
list.add(textFieldRun1Score2.getText());
list.add(textFieldRun1Score3.getText());
list.add(textFieldRun1Score4.getText());
list.add(textFieldRun1Score5.getText());
list.add(textFieldRun1Score6.getText());
Collections.sort(list);
total = list.get(1) + list.get(2) + list.get(3) + list.get(4);
avg = total / 4;
textFieldBestScore.setText(Double.toString(avg));
return avg;
}
This code won't compile for a simple reason: type mismatch.
Just split this line:
list.add(textFieldRun1Score1.getText());
up: list.add(...) expects an int as parameter (since it's templatetype is Integer), textFieldRun1Score1.getText() returns a String. Thus you'll have to convert from String to int first. Most common way to solve this is int value = Integer.parseInt(string);
list.add(textFieldRun1Score1.getText());
won't work because you try to add a String to a list of Integers
Parse the String to an Integer first:
list.add(Integer.parseInt(textFieldRun1Score1.getText()));
.
edit (not an answer to your question, but a general advice):
Instead of doing:
double best;
if (firstRun > secondRun) {
best = firstRun;
} else {
best = secondRun;
}
simply use: double best = Math.max(firstRun, secondRun);

Java square root calculator?

Ok, I'm a beginner in java, learning on my own through websites and books. I tried a simple square root calculator with a for loop and a while loop (I've included what I tried below). Sadly, all my code does when I enter a number is terminate. Any help would be appreciated!
import java.util.Scanner;
public class The2RootProdject {
public static void main(String args[]) {
Scanner input = new Scanner(System.in);
double rootIt = input.nextDouble();
double dummy = 0.0000000;
while (dummy != dummy * dummy) {
dummy += 0.0000001;
if (rootIt == dummy * dummy) {
System.out.println("the squar root of " + rootIt + " is "
+ (dummy * dummy));
}
}
}
}
You have a couple of problems here:
1) Logical bug: 0 == 0 * 0
<= This means while (dummy != dummy * dummy) {..} will never be untrue, and you'll never even enter the loop
2) Floating point numbers are inexact, so your algorithm (which relies on "==") might not work anyway
Look here for more details on floating point imprecision:
http://www.lahey.com/float.htm
This is true for ANY language - your algorithm for square root must take this into account.
Try to use this algorithm which use Newton's iteration:
import java.util.Scanner;
public class Main
{
public static void main(String args[])
{
double number, t, squareRoot;
Scanner input = new Scanner(System.in);
number = input.nextDouble();
squareRoot = number / 2;
do
{
t = squareRoot;
squareRoot = (t + (number / t)) / 2;
}
while ((t - squareRoot) != 0);
System.out.println(squareRoot);
}
}
Newton's iteration is an algorithm for computing the square root of a number via the recurrence equation:
X(n+1) = (X(n) + number/X(n))/2
I think the while condition is supposed to be =
while(rootIt != dummy * dummy) {}
Your current condition will only ever be true if you initialized dummy as 1; but I don't that would be what you want anyways.

What does "Type mismatch: cannot convert from null to double" mean?

I'm trying to solve exercise from Art & Science of Java, solution for quadratic equation.
import acm.program.*;
public class QuadraticEquation extends ConsoleProgram {
public void run(){
println("Enter coefficients for quadratic equation");
int a = readInt("Enter first number: ");
int b = readInt("Enter second number: ");
int c = readInt("Enter third number: ");
double result = quadratic(a,b,c);
println("The first solution is: " + result);
}
private double quadratic(int a, int b, int c){
double underSquare = (b*b-4*a*c);
double x = (-b+Math.sqrt(b*b-(4*a*c)))/(2*a);
if (underSquare < 0) {
return null;
} else {
return (x);
}
}
}
I have an error in line:
return null;
saying:
Type mismatch: cannot convert from null to double
I don't really understand what this error, how should I solve this correctly?
You need to understand the difference between primitive types (e.g., double) and boxed object types (e.g., capital-D Double). Whereas Double is a reference to an object (and hence can be null), double is a primitive and can not be null.
The compiler is telling you that you declared the return type of your function to be double and so null can not be converted to a double.
Of course you could "fix" the problem by changing the return type to Double (which would make the null return legal, and cause your primitive doubles to be
auto-boxed into Doubles) but that would not really serve you well. You want a better error handling strategy (of which there are many ... some possibilities are to throw an exception, use an Optional return type, use a flag value such as not-a-number aka Double.NaN).
You are asserting that the method should return a primitive of type double, instead you are returning a null value, which doesn't match the stated contract of the method.
What you want to do here depends entirely on how you want to catch this kind of error and there are a number of different solutions here that would be correct, but throwing a null object isn't one of them.
It's also worth noting that in your shown example:
double underSquare = (b*b-4*a*c);
double x = (-b+Math.sqrt(b*b-(4*a*c)))/(2*a);
if (underSquare < 0) {
return null;
} else {
return (x);
}
should be:
double underSquare = (b*b-4*a*c);
double x = (-b+(Math.sqrt(underSquare)))/(2*a);
return x;
which is equivalent to:
double underSquare = (b*b-4*a*c);
double x = (-b+Math.sqrt(b*b-(4*a*c)))/(2*a);
if (underSquare < 0) {
return double.NaN;
} else {
return (x);
}
but far more readable.
Java is smart enough to know that it shouldn't be taking the square root of a negative number and so if you just return x in both cases the code should run just fine. That said, you should also try to catch any exception here. Since there are a lot of error that could occur in directly evaluating numbers you should try something of this sort:
double underSquare = (b*b-4*a*c);
try{
double x = (-b+(Math.sqrt(underSquare)))/(2*a);
} catch (Exception e){
throw e;
} finally {
return x
}
return x;
Since you seem to will to compute the real solutions of the equation you should probably consider throwing an exception.
You cannot return null because it can be used only with references while you want to return a double, which is a primitive data type
You have few problems in your code from returning null to a double method...I have revised your program compare it against yours and if there is any part that you have questions then add a comment to my answer and I'll do my best to help you.
public static void main(String[] args) {
run();
}
static void run(){
System.out.println("Enter coefficients for quadratic equation");
Scanner keyboard = new Scanner(System.in);
System.out.println("Enter first number: ");
Double a = keyboard.nextDouble();
System.out.println("Enter second number: ");
Double b = keyboard.nextDouble();
System.out.println("Enter third number: ");
Double c = keyboard.nextDouble();
resultParta(a,b,c);
}
public static void resultParta(Double a, Double b, Double c) {
double discriminant = Math.pow(b,2) - 4*a*c;
double answer1 = (-b + Math.sqrt(discriminant))/(2*a);
double answer2 = (-b - Math.sqrt(discriminant))/(2*a);
if(discriminant > 0)
{
System.out.println("answer1: " + answer1);
System.out.println("answer2: " + answer2);
}
else if(discriminant == 0)
{
System.out.println("answer2: " + answer1);
}
else
{
double root1complex = -b/(2*a);
double root1complex2 = Math.sqrt(-discriminant)/(2*a);
System.out.println(root1complex + " + " + root1complex2 + " i ");
System.out.println(" ");
System.out.println(root1complex + " - " + root1complex2 + " i ");
}
}
Why do you check for negative determinant after you take the square root? That makes no sense. Check before you do it.
You return a single double, in spite of the fact that quadratics have two roots. What about the one you don't return?
In that case the results are two complex conjugate roots. You could certainly write a Complex class and return both roots.
You don't check for special cases (e.g. a = 0, b = 0, c =0). You should.
Your equation is implemented in the naive style, ignoring numerical issues.
Bad implementation. Lots of room for improvement.

Categories

Resources