假设我有List<SomeObject>
并且有一个函数可以返回该对象的引用(如果可用)。
SomeObject GetSomeObject(List<SomeObject>, int x){
/* Search for object in list that has a properties
with value x */
if (found)
return /* The object found */
else
return NULL;
}
void DoSomething(SomeObject S){
if(S!=NULL){
/* Do action 1 */
}
else{
/* Do action 2 */
}
}
我已经在某处读过,返回NULL
不是清洁代码的一部分。所以我想知道这个案例的等效代码是什么。
更新:我已阅读this question,我认为我的情况有所不同。在这种情况下,如果返回NULL
则不执行任何操作,而如果返回NULL
则需要执行某些操作
答案 0 :(得分:6)
如果你使用的是Java 8,请考虑{{3}}类,但请注意它并不适用于所有地方。
许多人认为(包括我)Optional
仅应用于返回值,而不应用于参数,尤其不应用于对象属性。然而,一如既往没有硬规则,只要小心你不要盲目地用Optional
替换空处理,而不理解你是否从中获得任何好处。
例如,在示例代码中,Optional
对您没有任何帮助。由于您执行某些操作而不管是否为null,因此您只需将if(s == null)
更改为if(s.isPresent())
即可。但是,如果逻辑只在s非空时才执行某些操作,而没有else
,则可以使用Optional.ifPresent()
来使事情变得更清晰。当然,Optional
中还有其他有用的方法可以为您提供更清晰的代码,例如可以有效使用默认值的orElse()
。
答案 1 :(得分:4)
看起来你的意思是special case模式(特定的实现是Option或Null Object模式。)
在Java 8和Guava库中有一些名为Optional
的Option类型的Java实现。
在您的情况下,您将使用Optional<SomeObject>
并实现此实现(我正在使用Guava实现):
Optional<SomeObject> getSomeObject(List<SomeObject>, int x) {
/* Search for object in list that has a properties
with value x */
if (found) {
return Optional.of(objectFound);
} else {
return Optional.absent(); // or Optional.empty(); in Java 8
}
// if objectFound variable is null when not found, you can simply use
// return Optional.fromNullable(objectFound);
// or return Optional.ofNullable(objectFound); in Java 8
}
因此代码可以自我解释返回一个可选对象。然后你会:
void doSomething(Optional<SomeObject> o) {
if (o.isPresent()) {
SomeObject someObject = o.get();
/* Do action 1 */
} else {
/* Do action 2 */
}
// or opt.map(/* action 1 */).orElse(/* action 2 */); in Java 8
}
答案 2 :(得分:1)
你可以抛出NoSuchElementException,这与"fail fast"的美食学很顺利。
然而,如果您的代码开始使用异常机制进行流量控制 - 这是一个非常大的禁忌,您应该避免它。
一个好的经验法则是,如果元素不存在,则抛出异常,仅当您的API也支持contains()
(或HasSomeObject(obj)
)方法时。
免责声明:此答案适用于java-8代码之前,对于java8,更好的做法可能是可选的,as suggested by @Kayman
答案 3 :(得分:0)
您可以考虑的一种常见方法是Null Object Pattern。
不是返回NULL,而是返回正确对象类型的实例,在调用其方法时不执行任何操作。它并不适合所有情况,但值得思考。