保护计算器不被 0 除
Protect calculator from dividing by 0
当用户试图在我的计算器中将某个数字除以 0 时,我希望在编译器中没有错误,但我不知道如何才能做到这一点。当用户执行计算器时,计算器的结果应该为 0,但我希望在 Java 编译器中没有错误。
protected void handleOnAnyButtonClicked(ActionEvent evt) {
Button button = (Button)evt.getSource();
final String buttonText = button.getText();
if (buttonText.equals("C") || buttonText.equals("AC")) {
if (buttonText.equals("AC")) {
left = BigDecimal.ZERO;
}
selectedOperator = "";
numberInputting = false;
display.setText("0");;
return;
}
if (buttonText.matches("[0-9\.]")) {
if (!numberInputting) {
numberInputting = true;
display.clear();
}
display.appendText(buttonText);
return;
}
if (buttonText.matches("[+-×÷]")) {
left = new BigDecimal(display.getText());
selectedOperator = buttonText;
numberInputting = false;
return;
}
if (buttonText.equals("=")) {
final BigDecimal right = numberInputting ? new BigDecimal(display.getText()) : left;
left = calculate(selectedOperator, left, right);
display.setText(left.toString());
numberInputting = false;
return;
}
}
static BigDecimal calculate(String operator, BigDecimal left, BigDecimal right) {
switch (operator) {
case "+":
return left.add(right);
case "-":
return left.subtract(right);
case "×":
return left.multiply(right);
case "÷":
// if user divides by 0
try {
left.divide(right);
} catch(ArithmeticException e) {
e.printStackTrace();
return display.setText("0");
}
return left.divide(right);
default:
}
return right;
}
public static void main(String[] args) {
launch(args);
}
谁能帮我解决我的代码中的哪些问题?我是 Java 初学者,如果有任何建议或帮助,我将不胜感激。
这类似于:
但略有不同,因为此代码使用 BigDecimals 而不是双精度数,并且双精度数在除以零时的行为与 BigDecimal 不同。我最初将这个问题作为重复问题关闭,但由于差异而重新打开它。
对于 BigDecimal:
BigDecimal.valueOf(1).divide(BigDecimal.ZERO))
将抛出 ArithmeticException 而不是 return 结果,而将两个双精度相除不会抛出异常,而是 return 一个无限结果。
无论如何,正如 Ms3x 在评论中所建议的那样,无论如何进行除法,最好都以相同的方式进行编码。首先检查零值,只有在正确的值不为零时才执行除法。
注:
BigDecimal.valueOf(1).divide(BigDecimal.valueOf(3)
也会抛出 ArithmeticException,因为没有舍入的结果可能是无限长的数字,这不是您想要的。
此外,您正在尝试从 calculate() return display.setText("0"),但编译失败,因为计算需要 BigDecimal 结果和 display.setText("0 ) 将 return 无效(假设显示是一个 TextField,这似乎很可能)。
您应该对 calculate() 函数进行一些更改:
- calculate() 及其引用的任何字段都不应是静态的。
- 在除法之前检查 calculate() 中的正确值以确保它不为零。
- return BigDecimal.ZERO 如果正确的值为零,如果这是你想要做的。
- 使用除法 rounding mode or math context。
- 通过在这种情况下不尝试 return display.setText("0") 来修复 calculate() 中的编译错误
- return BigDecimal.ZERO 如果这是你想要做的。
示例代码
遵循上面列出的建议修复。
它还使用了 switch expression,但如果您不想,则不需要使用它。
该示例使用断言,您使用 Java VM 参数启用它们 -ea
。
import java.math.BigDecimal;
import java.math.MathContext;
public class BigDecimalTest {
public static void main(String[] args) {
BigDecimal result;
BigDecimalTest test = new BigDecimalTest();
result = test.calculate("÷", BigDecimal.valueOf(1), BigDecimal.valueOf(3));
assert(BigDecimal.valueOf(0.3333333).equals(result));
result = test.calculate("÷", BigDecimal.valueOf(28.2), BigDecimal.valueOf(0));
assert(BigDecimal.ZERO.equals(result));
}
private BigDecimal calculate(String operator, BigDecimal left, BigDecimal right) {
return switch (operator) {
case "+" -> left.add(right);
case "-" -> left.subtract(right);
case "×" -> left.multiply(right);
case "÷" ->
BigDecimal.ZERO.equals(right)
? BigDecimal.ZERO
: left.divide(right, MathContext.DECIMAL32);
default -> right;
};
}
}
然后您可以轻松地将文本字段设置为结果:
display.setText(
calculate(
selectedOperator, left, right
).toString()
);
当用户试图在我的计算器中将某个数字除以 0 时,我希望在编译器中没有错误,但我不知道如何才能做到这一点。当用户执行计算器时,计算器的结果应该为 0,但我希望在 Java 编译器中没有错误。
protected void handleOnAnyButtonClicked(ActionEvent evt) {
Button button = (Button)evt.getSource();
final String buttonText = button.getText();
if (buttonText.equals("C") || buttonText.equals("AC")) {
if (buttonText.equals("AC")) {
left = BigDecimal.ZERO;
}
selectedOperator = "";
numberInputting = false;
display.setText("0");;
return;
}
if (buttonText.matches("[0-9\.]")) {
if (!numberInputting) {
numberInputting = true;
display.clear();
}
display.appendText(buttonText);
return;
}
if (buttonText.matches("[+-×÷]")) {
left = new BigDecimal(display.getText());
selectedOperator = buttonText;
numberInputting = false;
return;
}
if (buttonText.equals("=")) {
final BigDecimal right = numberInputting ? new BigDecimal(display.getText()) : left;
left = calculate(selectedOperator, left, right);
display.setText(left.toString());
numberInputting = false;
return;
}
}
static BigDecimal calculate(String operator, BigDecimal left, BigDecimal right) {
switch (operator) {
case "+":
return left.add(right);
case "-":
return left.subtract(right);
case "×":
return left.multiply(right);
case "÷":
// if user divides by 0
try {
left.divide(right);
} catch(ArithmeticException e) {
e.printStackTrace();
return display.setText("0");
}
return left.divide(right);
default:
}
return right;
}
public static void main(String[] args) {
launch(args);
}
谁能帮我解决我的代码中的哪些问题?我是 Java 初学者,如果有任何建议或帮助,我将不胜感激。
这类似于:
但略有不同,因为此代码使用 BigDecimals 而不是双精度数,并且双精度数在除以零时的行为与 BigDecimal 不同。我最初将这个问题作为重复问题关闭,但由于差异而重新打开它。
对于 BigDecimal:
BigDecimal.valueOf(1).divide(BigDecimal.ZERO))
将抛出 ArithmeticException 而不是 return 结果,而将两个双精度相除不会抛出异常,而是 return 一个无限结果。
无论如何,正如 Ms3x 在评论中所建议的那样,无论如何进行除法,最好都以相同的方式进行编码。首先检查零值,只有在正确的值不为零时才执行除法。
注:
BigDecimal.valueOf(1).divide(BigDecimal.valueOf(3)
也会抛出 ArithmeticException,因为没有舍入的结果可能是无限长的数字,这不是您想要的。
此外,您正在尝试从 calculate() return display.setText("0"),但编译失败,因为计算需要 BigDecimal 结果和 display.setText("0 ) 将 return 无效(假设显示是一个 TextField,这似乎很可能)。
您应该对 calculate() 函数进行一些更改:
- calculate() 及其引用的任何字段都不应是静态的。
- 在除法之前检查 calculate() 中的正确值以确保它不为零。
- return BigDecimal.ZERO 如果正确的值为零,如果这是你想要做的。
- 使用除法 rounding mode or math context。
- 通过在这种情况下不尝试 return display.setText("0") 来修复 calculate() 中的编译错误
- return BigDecimal.ZERO 如果这是你想要做的。
示例代码
遵循上面列出的建议修复。
它还使用了 switch expression,但如果您不想,则不需要使用它。
该示例使用断言,您使用 Java VM 参数启用它们 -ea
。
import java.math.BigDecimal;
import java.math.MathContext;
public class BigDecimalTest {
public static void main(String[] args) {
BigDecimal result;
BigDecimalTest test = new BigDecimalTest();
result = test.calculate("÷", BigDecimal.valueOf(1), BigDecimal.valueOf(3));
assert(BigDecimal.valueOf(0.3333333).equals(result));
result = test.calculate("÷", BigDecimal.valueOf(28.2), BigDecimal.valueOf(0));
assert(BigDecimal.ZERO.equals(result));
}
private BigDecimal calculate(String operator, BigDecimal left, BigDecimal right) {
return switch (operator) {
case "+" -> left.add(right);
case "-" -> left.subtract(right);
case "×" -> left.multiply(right);
case "÷" ->
BigDecimal.ZERO.equals(right)
? BigDecimal.ZERO
: left.divide(right, MathContext.DECIMAL32);
default -> right;
};
}
}
然后您可以轻松地将文本字段设置为结果:
display.setText(
calculate(
selectedOperator, left, right
).toString()
);