is there a Java equivalent to null coalescing operator (??) in C#?
是否可以在Java中执行类似于以下代码的操作
更多关于??
-
@theprise谢谢!
-
投票重新开放,不重复。 这个问题是"x存在吗",另一个问题是"因为x不存在,我怎么得到y"。
-
在Java8 +上有jdk中的Optional类。 用法示例Optional.ofNullable(x).orElse(-1)。 其他良好用法用法可选方法图。 假设对象a相当于json对象:"a":{"b":{"c":1}}。 读取c值可以是这样的结构:Optional.ofNullable(a).map(a-> a.b).map(b-> b.c).orElse(-1)。 比C#更难看的文字语法,但是使用级联运算符是更好的选择吗?:
可悲的是没有。你最接近的是:
1
| int y = (x != null) ? x : -1; |
当然,如果您觉得有必要(可能不会减少很多长度),您可以将它包装在库方法中,但在语法级别上没有更简洁的可用。
-
当然,只有当x是Integer时才有效,因为int无法与null进行比较。
-
@musiKk:C#等价物只适用于int? (或者更确切地说是任何引用类型或可空)
-
@jmoreno我不是C#开发人员,所以我不知道。
-
@musiKk:打字?是你如何声明一个可空类型的变量。 c#null coalescing运算符仅适用于可空或引用类型。如果上面的例子是C#,那么x的类型是int吗? - 但是使用空合并运算符更好地编写为y = x ?? -1;
-
@jmoreno哦,我以为这是一个问题......
-
这就是code blocks的用途,因此您可以判断int?是数据类型,而不是问题。 :)
Guava有一个类似于MoreObjects.firstNonNull(T,T)的方法。
1 2
| Integer x = ...
int y = MoreObjects. firstNonNull(x, -1); |
当你有类似的东西时,这会更有帮助
1
| int y = firstNonNull(calculateNullableValue(), -1); |
因为它可以避免两次调用潜在的昂贵方法或者在代码中声明一个局部变量来引用两次。
-
不幸的是,如果所有值都为null,则会抛出NullPointerException。虽然coalesce可以返回null。
-
@Stefan:没错,虽然我确实说它"相似"并不完全一样。对于你想要一个固定的非null默认值(如果某些东西是null),这类事情到目前为止是最有用的(也是最常用的)。鉴于此,如果第二个参数为null,则firstNonNull会失败,以帮助更快地捕获程序员错误。
-
像这样的解决方案的真正问题在于它牺牲了空合并延迟评估。由于必须将所有值传递给Objects.firstNonNull,因此将评估您传递的所有函数。这使得它的计算成本远远高于C#的??。
-
@AndrewCoonce:当然,但是有很多用例(比如这个例子),你只需要一个默认值或者计算成本不高的东西。当替代方案的计算费用昂贵时,总会有三元数。
简答:不
您可以做的最好的事情是创建一个静态实用程序方法(以便可以使用import static语法导入它)
1 2 3 4
| public static < T > T coalesce(T one, T two)
{
return one != null ? one : two;
} |
上面的内容相当于@ColinD的Guava的方法firstNonNull,但这可以扩展得更多
1 2 3 4 5 6 7
| public static < T > T coalesce(T... params)
{
for (T param : params)
if (param != null)
return param;
return null;
} |
-
我没有谈论C#,我谈到了Swift语言和他的可选链接。
-
请注意,如果两个参数都为null,则Guava的方法抛出异常!
不,并且请注意,变通方法功能并不完全相同,真正的空合并运算符短路如&&和|| do,这意味着如果第一个表达式为null,它将只尝试计算第二个表达式。
来自Apache Commons Lang 3的ObjectUtils.firstNonNull(T...)是另一种选择。因为与番石榴不同,我更喜欢这种方法,这种方法不会抛出Exception。它只会返回null;
Java中的基元永远不能为空,因此该语句在概念上没有意义。但是,包装类(Integer,Character等)以及任何其他可实例化的类都可以为null。
除此之外,空合并运算符没有任何简写语法。您必须使用展开的表单。
-
x不一定是原始的。除了我们说Java <5。
-
是的,像:Integer x = ... ; int y = (x != null) ? x : -1;