Java 要捕获哪个断言错误
Java which assertion error to catch
我自己练习了一些 Java SE 7,遇到了以下问题。我写了一个 public static void 函数 ValidDate,它接受三个字符串,并且只在日期无效时抛出断言错误。 ValidDate 使用两个字符串数组(MONTHS 和 DAYS)作为库来验证给定的日期。 ValidDate 在每个断言测试结束时也有一个唯一的断言表达式:
public static void ValidDate(String month, String day, String year){
boolean validday = false;
boolean validmonth = false;
boolean validyear = true;
try{
Integer.parseInt(year);
}catch(NumberFormatException e){
validyear = false;
}
assert(validyear): "Error: year entry not written in integers.";
for(String m:MONTHS){
if(m.equals(month)){
validmonth = true;
}
}
assert (validmonth): "Error: month entry is not valid; must be an"
+ " integer between (0)1 and 12.";
...
}
我的目的是添加 ValidDate 作为 DOB setter (SetDOB ) 我的 public class 人 。当在 setter 和 中输入无效的 DOB 时,实现将 ValidDate 抛出异常然后 SetDOB 将输出一条消息,表明输入的 DOB 是不可接受的,并且不会更改当前的 DOB 值:
public void SetDOB(String newDOB){
String[] dates = newDOB.split("/");
boolean validdate = true;
if(dates.length == 3){
try{
ValidDate(dates[0],dates[1],dates[2]);
}
catch(AssertionError e){
System.out.println("Error: ValidDate threw an assert error.");
validdate = false;
}
if(validdate){
DOB = newDOB;
}
}
else{
System.out.println("Please enter a valid DOB of the form: Month/Day"
+ "/Year using integers.");
}
}
当我尝试 运行 SetDOB 时 DOB,然而,ValidDate 不会为 SetDOB 抛出 AssertionError 来捕获。也没有输出错误信息。我怀疑造成这种情况的原因与我在 ValidDate 或 SetDOB 中使用 try-catch 语句有关。但是,我也可能在没有意识到的情况下犯了一个不同的错误。我希望有人解释我做错了什么以及如何正确完成我的预期任务。如果其他人已经回答了这个或类似的问题,那么请在他们的 post 中添加一个 link。如果我在遇到 linked post.
时发现它多余,我也可能会删除它 post
断言用于测试您的代码假定的不变量。如果断言失败,那应该表明你的代码是错误的,而不是遇到了某种可预测的失败模式。断言不适合后者,因为是否在运行时评估断言完全取决于 VM 参数。
由此可见,抓AssertionError
很少是合适的。 (事实上 ,捕获任何 Error
很少是合适的。)只有在相当特殊的条件下,才有可能从程序本身的错误中恢复过来。
在您的特定情况下,您的代码可能 运行 没有启用断言。你没有抓住 AssertionError
因为 none 曾经被抛出。
然而,真正的问题是你误解了断言的目的。它们不是表示在执行程序的过程中出现问题,而是表示您对代码的假设是错误的。
当你这样写的时候
assert someValue != null : "some value should be set"
这意味着您编写代码的方式 someValue
以一种或另一种方式设置,并且当代码达到 assert
时,它 必须 已设置。如果有人修改您的代码,使其可以在不设置 someValue
的情况下到达 assert
,断言将捕获它。
另一方面,您的代码尝试使用断言进行验证。这就是 exceptions 的用途:
if (!validmonth) {
throw new InvalidMonthException("Error: month entry is not valid; must be an integer between (0)1 and 12.");
}
注意: 您的代码未捕获断言的最可能原因是您 have not enabled them.
创建您自己的异常 class 而不是 throwing/catching AssertionError。
不要在您的 SetDOB 方法中捕获此异常,而是向 setDOB 方法添加一个 throws 子句。调用 setDOB 方法时捕获异常。
我自己练习了一些 Java SE 7,遇到了以下问题。我写了一个 public static void 函数 ValidDate,它接受三个字符串,并且只在日期无效时抛出断言错误。 ValidDate 使用两个字符串数组(MONTHS 和 DAYS)作为库来验证给定的日期。 ValidDate 在每个断言测试结束时也有一个唯一的断言表达式:
public static void ValidDate(String month, String day, String year){
boolean validday = false;
boolean validmonth = false;
boolean validyear = true;
try{
Integer.parseInt(year);
}catch(NumberFormatException e){
validyear = false;
}
assert(validyear): "Error: year entry not written in integers.";
for(String m:MONTHS){
if(m.equals(month)){
validmonth = true;
}
}
assert (validmonth): "Error: month entry is not valid; must be an"
+ " integer between (0)1 and 12.";
...
}
我的目的是添加 ValidDate 作为 DOB setter (SetDOB ) 我的 public class 人 。当在 setter 和 中输入无效的 DOB 时,实现将 ValidDate 抛出异常然后 SetDOB 将输出一条消息,表明输入的 DOB 是不可接受的,并且不会更改当前的 DOB 值:
public void SetDOB(String newDOB){
String[] dates = newDOB.split("/");
boolean validdate = true;
if(dates.length == 3){
try{
ValidDate(dates[0],dates[1],dates[2]);
}
catch(AssertionError e){
System.out.println("Error: ValidDate threw an assert error.");
validdate = false;
}
if(validdate){
DOB = newDOB;
}
}
else{
System.out.println("Please enter a valid DOB of the form: Month/Day"
+ "/Year using integers.");
}
}
当我尝试 运行 SetDOB 时 DOB,然而,ValidDate 不会为 SetDOB 抛出 AssertionError 来捕获。也没有输出错误信息。我怀疑造成这种情况的原因与我在 ValidDate 或 SetDOB 中使用 try-catch 语句有关。但是,我也可能在没有意识到的情况下犯了一个不同的错误。我希望有人解释我做错了什么以及如何正确完成我的预期任务。如果其他人已经回答了这个或类似的问题,那么请在他们的 post 中添加一个 link。如果我在遇到 linked post.
时发现它多余,我也可能会删除它 post断言用于测试您的代码假定的不变量。如果断言失败,那应该表明你的代码是错误的,而不是遇到了某种可预测的失败模式。断言不适合后者,因为是否在运行时评估断言完全取决于 VM 参数。
由此可见,抓AssertionError
很少是合适的。 (事实上 ,捕获任何 Error
很少是合适的。)只有在相当特殊的条件下,才有可能从程序本身的错误中恢复过来。
在您的特定情况下,您的代码可能 运行 没有启用断言。你没有抓住 AssertionError
因为 none 曾经被抛出。
然而,真正的问题是你误解了断言的目的。它们不是表示在执行程序的过程中出现问题,而是表示您对代码的假设是错误的。
当你这样写的时候
assert someValue != null : "some value should be set"
这意味着您编写代码的方式 someValue
以一种或另一种方式设置,并且当代码达到 assert
时,它 必须 已设置。如果有人修改您的代码,使其可以在不设置 someValue
的情况下到达 assert
,断言将捕获它。
另一方面,您的代码尝试使用断言进行验证。这就是 exceptions 的用途:
if (!validmonth) {
throw new InvalidMonthException("Error: month entry is not valid; must be an integer between (0)1 and 12.");
}
注意: 您的代码未捕获断言的最可能原因是您 have not enabled them.
创建您自己的异常 class 而不是 throwing/catching AssertionError。 不要在您的 SetDOB 方法中捕获此异常,而是向 setDOB 方法添加一个 throws 子句。调用 setDOB 方法时捕获异常。