【问题标题】:if clause and generic method returning booleanif 子句和泛型方法返回布尔值
【发布时间】:2016-04-13 06:06:25
【问题描述】:

我有一个在特定场景下返回布尔值的通用方法。

我的方法的方法签名是例如

public <T> T get() { return Boolean.true;}

到这里为止,它工作正常,没有编译器错误。 但是,当我尝试在 if 子句中使用相同的内容时,例如

if(get())

然后它返回错误说

类型不匹配:无法从 Object 转换为布尔值

我也怀疑这只发生在 Eclipse 中。这是一个现有代码,我正在尝试在我的工作区中编译它。

请帮忙。

更新:

这篇文章很好地解释了目标类型推断 - https://docs.oracle.com/javase/tutorial/java/generics/genTypeInference.html

正如下面@Codebender 所解释的,TargetType 推断适用于链式/嵌套方法,尽管它看起来不适用于 if、for、while 等语言结构。 我试着在下面写一个方法 -

 public void test(boolean val)

并尝试像这样称呼它

test(get())

而且效果很好。

解决方案:

最后,在这段代码中,我最终添加了像

这样的显式类型转换
if((Boolean)get())

它对我有用。

【问题讨论】:

  • get() 在这里用作原始类型,因此它确实返回Object。单个 Object 不代表有效条件。
  • 你能分享完整的上下文吗?另外,为什么这个方法需要是通用的?您知道您正在返回一个布尔值,而您的 if 语句将其视为布尔值 - 为什么不直接定义它呢?
  • 这个神奇的get() 方法是如何工作的,它可以返回任何所需类型的值,甚至不知道该类型是什么?这种方法唯一可以返回而不会(正确地)扰乱编译器的是null
  • 如今,您实际上可以在if 语句中使用泛型方法:ideone.com/wdI4KM。但这有意义吗? (可能不是...)如果您确定它返回 Boolean,为什么它是通用的?
  • 正如我所说,它是一个现有的代码,我正在尝试在我的 Eclipse 中编译。 Boolean.TRUE 不是一个实际的语句,周围发生了一堆方法调用,但最终在这种情况下,它返回布尔值。我正在使用 java8 和 eclipse Mars.2

标签: java eclipse


【解决方案1】:

为此:

 if(get())

你需要有一个类似get 方法的返回类型的布尔值,如下所示:

  public <T> boolean get() {...

【讨论】:

  • 它是一个现有的代码,我相信它可以在其他环境中编译。我不想改变它。
【解决方案2】:

代码在 Java 8 中可以正常工作(因为通用类型推断)...但在 Java 7 及更低版本中不行。

查看我的这个答案以了解什么是广义类型推断:https://stackoverflow.com/a/32294457/2775450 以及这个:https://stackoverflow.com/a/28474319/2775450

除此之外,您的代码似乎还有其他错误,例如 Boolean.TRUE 而不是 Boolean.true,您应该在 return 语句中明确转换为 T

【讨论】:

  • 是的 Boolean.TRUE 可能是一种类型。实际上它不是 Boolean.TRUE,而是其他一些语句。我把 Boolean.TRUE 用来简化语句。
  • 实际上我正在针对 java 8 进行编译,这就是为什么我对这个错误感到惊讶。与日食有什么关系吗?除了编译器设置中的源代码级别?
  • @AnandVaidya,不确定...它应该适用于 Java 8...您可能需要重新检查您是否真的在使用 Java-8...
  • 显然它看起来像 - 即使在 java8 中,改进的类型接口仍然不适用于 if、while、for 等语言结构。所以我想我必须更改代码。虽然它是现有的,而且我认为它是正确的,但看起来它是错误的。
【解决方案3】:
I think this is happening because if you see in the method signature 
public <T> T get(), you are making it Generics but in the return statement, boolean value is returned. So to make it work just try to change the return type in the method signature like below:- 
public static <T> Boolean get() { 
        return Boolean.TRUE;
}
then use it in the if condition :- if(get()){   }

【讨论】:

    【解决方案4】:

    你为什么不把你的方法定义为

    public <T> boolean get() { return Boolean.TRUE;}
    

    在这种情况下,您不会收到编译错误,而是按原样定义返回参数。在您的原始定义中,您希望该方法返回 T 而不是 boolean 类型的内容。

    更新:您的代码没有使用泛型。并且没有任何方法可以在您计划使用的 if 语句中使用通用返回值,因为 Java 不像脚本语言那样具有“虚假”值(例如 Python)。这里有一个通用方法的替代方法是添加一些通用值作为参数并在方法体中使用它:

    public <T> boolean get(T some value) { return Boolean.TRUE;}
    

    但如果您想在 if 中使用结果,请考虑添加如下内容:

    if(get() != null) {...}
    

    它也适用于通用方法。如果您总是从 get() 返回 boolean 值,则不需要使用泛型。

    【讨论】:

    • 那泛型在里面有什么用呢?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-12-19
    • 1970-01-01
    • 2013-12-12
    • 2022-12-17
    • 1970-01-01
    • 2013-10-01
    • 2015-09-01
    相关资源
    最近更新 更多