assert
稍短一些,但我不确定有多重要。 >#1 楼
谨防!除非在编译代码时明确指定“启用断言”,否则在运行时将删除断言。 Java断言不应在生产代码上使用,而应限于私有方法(请参见Exception与Assertion),因为私有方法应被开发人员所知并使用。同样,
assert
会抛出AssertionError,它扩展了Error
而不是Exception
,并且通常表明您有一个非常异常的错误(例如“ OutOfMemoryError”,很难从中恢复,不是吗?),您不希望能够处理。 br /> 删除“ enable assertions”标志,并通过调试器进行检查,您将看到您不会踩IllegalArgumentException throw调用...因为此代码尚未编译(同样, ea”已删除)
最好将第二种构造用于公共/受保护的方法,如果您希望在一行代码中完成某件事,至少我知道一种方法的。我个人使用Spring Framework的
Assert
类,该类具有一些用于检查参数的方法,并在失败时抛出“ IllegalArgumentException”。基本上,您要做的是:Assert.notNull(obj, "object was null");
...实际上,这将执行与您在第二个示例中编写的代码完全相同的代码。还有一些其他有用的方法,例如
hasText
,hasLength
。 我不喜欢编写多余的代码,所以当我将编写的行数减少2(2行> 1行)时感到很高兴:-)
评论
啊,我忘记断言了!好答案。我会稍等一下,看是否还有其他东西,然后接受:)
–丹妮丝
2012-2-27在19:17
请注意,没有标志可以在编译时删除断言(尽管可以通过条件编译将其删除)。断言默认是在运行时禁用的(我认为JVM将其视为NOOP),但可以通过java -ea和以编程方式启用。 @Jalayn我认为在生产代码中包含断言是完全有效的,因为它们对于在现场进行调试非常有用
–贾斯汀·穆勒(Justin Muller)
2014年1月24日在7:30
@ Jalayn,-1。编译器不会删除断言代码。即使它们不运行,除非您执行cmd java -ea。
–起搏器
14年8月26日在16:15
可以使用Objects.requreNonNull时不需要Spring框架
–含蓄
17-10-10在18:12
#2 楼
您需要使用一个例外。使用断言可能会滥用该功能。未经检查的异常旨在检测库用户的编程错误,而断言旨在检测自己逻辑中的错误。这些是单独的问题,不应混在一起。
例如,一个断言
此断言确保
myConnection
已连接;如果上面的代码未能获得有效的连接,则它应该在到达此点之前引发异常或返回。” /> assert myConnection.isConnected();
表示“未建立连接即调用我的库是编程错误”。
评论
这些信息确实有帮助,但是我接受Jalayn的建议,因为它指出了我可能如何使用assert方法引入错误。
–丹妮丝
2012年2月27日在21:43
优点:“未经检查的异常旨在检测库用户的编程错误,而断言旨在检测您自己的逻辑中的错误。这些是单独的问题,不应混在一起。”
–阿西姆·加法尔(Asim Ghaffar)
2013年9月19日在12:41
是的,但这是假设OP正在编写一个库。如果它们的代码仅供内部使用,则可以使用断言。
–user949300
18年4月24日在4:12
#3 楼
如果编写的函数不允许null
作为有效参数值,则应在签名中添加@Nonnull
批注,并使用Objects.requireNonNull
检查参数是否为null
,如果存在则抛出NullPointerException
。 @Nonnull
注释用于文档说明,在某些情况下会在编译时提供有用的警告。它不会阻止在运行时传递null
。void doStuff(@Nonnull Object obj) {
Objects.requireNonNull(obj, "obj must not be null");
// do stuff...
}
更新:
@Nonnull
批注不是Java标准库的一部分。相反,有来自第三方库的众多竞争标准(请参阅我应该使用哪个@NotNull Java注释?)。这并不意味着使用它不是一个坏主意,只是它不是标准的。评论
感谢您指出Objects.requireNonNull()对我来说是新的。您知道哪里有类似的“ requireTrue()”或“ requireEqual()”方法吗?没有什么反对Spring的断言,但不是每个人都在使用它。
–user949300
17年10月11日,0:01
@ user949300 Objects.requireNonNull()用于参数验证。如果要求一个参数为真或等于某个值,则该参数是没有意义的。对于非法参数以外的错误情况,应引发一个异常,以更准确地描述该错误。也有JUnit声明,但这是用于测试的。
–含蓄
17-10-11在0:15
我想的更像是说平方根函数Objects.requireTrue(x> = 0.0); ,或者对于某些哈希,Objects.requireEquals(hash.length == 256)
–user949300
17年11月19日在20:00
我必须使用哪个@Nonnull? javax.validation.constraints.NotNull吗?
–敏捷
18 Mar 26 '18在8:39
我将使用Eclipse JDT批注,因为它们是由聪明人制作的:)。文档:help.eclipse.org/neon/…-您也可以配置IntelliJ来使用它们。
– koppor
18年7月9日在21:29
#4 楼
我总是更喜欢抛出IllegalArgumentException而不是断言。因此,可能会给其他开发人员以错误的印象,即您的方法是测试方法。这与Java开发人员遵循的Exception Handling约定更加一致。评论
断言比JUnit早40年左右-向C程序员询问ASSERT宏。
– JBR威尔金森
13年2月22日在22:04
这个问题不是关于c的。关于Java。所以我已经在Java上下文中回答了。
– rai.skumar
13年2月23日在5:43
不要混淆assert(保留关键字)和Assert(JUnit类),它们都用于对变量执行检查,但除此之外,它们是两个截然不同的事物,并且行为也截然不同。
– Newtopian
17-10-11在22:01
#5 楼
我没有使用很多aserts,而是使用Lombock @NonNull的常用方法: NonNull;public class NonNullExample extends Something {
private String name;
public NonNullExample(@NonNull Person person) {
super("Hello");
this.name = person.getName();
}
}
Java版本:
import lombok.NonNull;
public class NonNullExample extends Something {
private String name;
public NonNullExample(@NonNull Person person) {
super("Hello");
if (person == null) {
throw new NullPointerException("person");
}
this.name = person.getName();
}
}
Lombok是一个非常不错的库,我在各处都使用了
评论
我更喜欢简单的obj.hashCode();-)