Java在通用返回类型的方法中编译错误 [英] Java compile error in method with generic return type

查看:101
本文介绍了Java在通用返回类型的方法中编译错误的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述



  class Foo {
< p< T延伸Foo> T方法(){
返回this;






错误是: Type mismatch:can not convert from Foo to T

为什么不能? T 被定义为 Foo 或其子类。

在相关说明中,一个等效的Scala示例不会编译,所以Java错误不是由于JVM的限制。

  class Foo {
def method [T <:Foo] = this
}






更新:我在Java教程中找到了关于泛型方法
$ b


泛型方法允许使用类型参数来表示方法和/或其返回类型的一个或多个参数类型之间的依赖关系。如果不存在这样的依赖关系,则不应使用泛型方法。


我的解释是通用方法只适用于在两种情况下。


  1. 方法的两个(或多个)参数类型之间存在依赖关系。

  2. 在方法的返回类型和其一个(或多个)参数类型之间存在依赖关系。

显然,简单由于没有参数,因此所讨论的代码在其参数和返回类型之间没有依赖关系。所以一个通用的方法是不合适的。




UPDATE2:现在我知道了,我已经注意到一对夫妇这个反模式在开源项目中的例子。






UPDATE3:我想我已经找到了一个不涉及多个参数或返回类型的泛型方法的需求。多重继承似乎是Java教程上述规则的一个例外。

 < T extends Foo&酒吧及GT; void方法(T foobar){
//调用Foo方法。
//呼叫栏方法。


解决方案

我想你误解了Java泛型工作:

 < T extends Foo> T方法(){

这意味着该方法的调用者可以选择他们想要的 Foo 的任何子类型并询问它。例如,你可以编写

  Foo foo = new Foo(); 
SubFoo subfoo = foo。< SubFoo> method();

...并期待一个 SubFoo 返回,但是你的方法实现不能返回一个 SubFoo ,这将会失败。 (我不会说斯卡拉,但我认为这意味着您的Scala实现实际上不是等价的。)



如果您希望您的方法能够返回 实现的子类型,而不是调用者,然后写

  Foo方法(){
return this;
}


I can't explain why this simple code doesn't compile.

class Foo {
    <T extends Foo> T method() {
        return this;
    }
}

The error is: Type mismatch: cannot convert from Foo to T.
Why not? T is defined to be Foo or its subclass.

On a related note, an equivalent Scala example does compile, so the Java error is not due to a limitation of the JVM.

class Foo {
  def method[T <: Foo] = this
}


UPDATE: I found a succinct piece of advice in the Java Tutorials regarding generic methods.

Generic methods allow type parameters to be used to express dependencies among the types of one or more arguments to a method and/or its return type. If there isn't such a dependency, a generic method should not be used.

My interpretation is that a generic method is only appropriate in two scenarios.

  1. There is a dependency between two (or more) of the method's argument types.
  2. There is a dependency between the method's return type and one (or more) of its argument types.

Obviously, the simple code in question has no dependency among its arguments and return type, since there are no arguments. So a generic method is inappropriate.


UPDATE2: Now that I'm aware of it, I've noticed a couple examples of this anti-pattern in open-source projects.


UPDATE3: I think I've found a requirement for generic methods that doesn't involve multiple parameters or a return type. Multiple inheritance would seem to be an exception to the above rule from Java's Tutorials.

<T extends Foo & Bar> void method(T foobar) {
    // Call Foo method.
    // Call Bar method.
}

解决方案

I think you misunderstand how Java generics work:

<T extends Foo> T method() {

This means that the caller of that method can pick whatever subtype of Foo they want and ask for it. For example, you could write

Foo foo = new Foo();
SubFoo subfoo = foo.<SubFoo>method();

...and expect a SubFoo back, but your method implementation couldn't return a SubFoo, and this would have to fail. (I don't speak Scala, but I presume this means that your Scala implementation is not in fact "equivalent.")

If you want your method to be able to return a subtype of Foo that the implementation chooses, instead of the caller, then just write

Foo method() {
  return this;
}

这篇关于Java在通用返回类型的方法中编译错误的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆