我创建了一个由某些类实现的通用接口。看起来像:
public interface KingdomElementService<T> {
public T findById(Long id);
public T save(Optional<T> object);
public void update(T t);
}
保存时我的IntelliJ大喊大叫,写着“ Optional用作参数”。我了解接受可能存在和可能不存在的事物的怪异逻辑。为什么考虑这样做是为了重写
if(something){
do();
}
else{
throw new Expression();
}
到
something.orElseThrow(Expression::new);
现在我想知道我使用Optional的解决方案是否在这里过大。你怎么看?我应该考虑改回来吗?
答案 0 :(得分:3)
没有任何特定于Optional
的内容,而是通过将其用作参数来强制所有调用者将Optional
传递给此方法。我宁愿为此使用@Nullable
,例如:
public T save(@Nullable T object);
这意味着您将不得不编写该if..else
块(或三元运算符),但我认为这样做的复杂性远不如强迫客户通过Optional
。
此外,如果您想使用相同的控件结构,则可以在方法实现的第一行写Optional.of(object);
,并将其用于其余的方法代码。
答案 1 :(得分:3)
Java语言架构师的观点是,Optional应该仅用作返回类型。这表示返回类型可能为null
。所以要小心。
Optional
作为输入参数将要求您始终检查该参数是否存在,并添加一些检查。如果要添加任何验证,则也可以不添加Optional。将输入参数标记为“可选”没有额外的价值。
另外,将参数传递给另一个接受Optional的方法的调用方法也必须包装Object并发送。这是开销。
我还没有考虑过Edge情况。
编辑:从“ Java语言非常清晰”变为更为真实。
答案 2 :(得分:1)
使用save(Optional<T> object);
我仍然可以打save(null);
的电话,这就是为什么这里的可选设置没有意义的原因。
您可以在方法中实现简单的空检查
void save(T object){
if(object == null){
// do smth
}
}
或在方法内部使用Optional.ofNullable()
void save(T object){
Optional.ofNullable(object)
.map(..)
.orElseGet(IllegalAccessError::new);
}
答案 3 :(得分:1)
如果您有KingdomElementService<T>
的实例,似乎希望save
的调用者可以选择是否传递T的实例。因此,给定一些变量:
KingdomElementService<T> kes = ... ;
T someT = ... ;
呼叫者可以这样做:
kes.save(Optional.of(someT)); // 1
kes.save(Optional.empty()); // 2
这给呼叫者带来了很多不便。相反,您应该修改KingdomElementService
来提供save
方法的重载:一个使用arg,一个不使用args:
interface KingdomElementService<T> {
T save(T t);
T save();
}
如果您这样做,则调用者不必费心将所有内容包装在Optional
中:
kes.save(someT); // 1
kes.save(); // 2
本质上,Optional
对希望采用可选参数的API没有帮助。