三元运算符的重载方法调用歧义

overloaded method call ambiguity with ternary operator

我正在为数字创建一个简单的包装器 class。简单地说,我希望它显示值 4242.0;但是,它应该将值 1.6180338 显示为该数字。够简单了。

代码

private double number;

...

@Override
public String toString() {

    return String.valueOf(
            number == longValue()
                    ? longValue()
                    : number );

}

...

@Override 
public long longValue() { 

    return (long) number; 

}

问题

问题是 42.0 的值总是显示 不是 toString(...) 方法中正确的 42

我的想法

虽然 String.valueOf(...) 方法有很多重载方法来将正确的原始值显示为字符串,但使用哪个重载方法存在歧义。它可以使用 String.valueOf(double)String.valueOf(long)。这是因为 三元运算符 语句和结果类型。

我认为编译器能够识别 long 类型并调用适当的 String.valueOf(long) 方法。情况似乎并非如此;相反,JVM 将在 编译时 选择最安全但最受限制的重载方法。在这种情况下,即 String.valueOf(double) 因为它可以安全地将 long 转换为 double.

问题

我知道目前在 Java 中无法做到这一点,但目前其他语言是否提供类似的功能?是否有某种定义解释了这种方法,你能更详细地解释一下吗?

我的意思是像 CovarianceContra-variance 这样的定义。注意:我意识到定义不是这两个中的一个:)

由于Java是静态类型语言,三元运算符的结果必须有明确的类型,在编译期间定义,这样编译器才能继续处理外部表达式。由于三元的两个分支都是数字,因此它们被提升为 JLS 15.25 and 5.6.2 中描述的更精确的类型。您可以解决此问题,将参数转换为对象:

return String.valueOf(
        number == longValue()
                ? (Object)longValue()
                : (Object)number );

通过这种方式,您可以将数字装箱并使用 String.valueOf(Object),这对两个分支都适用。