繁体   English   中英

Java Generics - 无法应用于给定类型

[英]Java Generics - cannot be applied to given type

我有一些类似的代码:

public class Main {

    private static abstract class Bar {}

    private static class SubBar extends Bar {}

    private static abstract class Baz<T extends Bar> {

        private T t;

        public void setT(T t) {
            this.t = t;
        }

    }

    private static class SubBaz extends Baz<SubBar> {}


    private void foo(Baz<? extends Bar> baz, Bar bar) {
        baz.setT(bar);
    }
 }

这会导致错误:

error: method setT in class Baz<T> cannot be applied to given types;
required: CAP#1
found: Bar
reason: actual argument Bar cannot be converted to CAP#1 by method invocation conversion
where T is a type-variable:
T extends Bar declared in class Baz
where CAP#1 is a fresh type-variable:
CAP#1 extends Bar from capture of ? extends Bar

我不明白为什么。 方法setT应该接受扩展Bar的东西,并且我正在传递类Bar的东西。

方法setT应该接受扩展Bar的东西,并且我正在传递类Bar的东西。

这正是问题: <? extends Bar> <? extends Bar>表示“某些未知类型为Bar或其子类”。 由于您不知道它是哪种类型,因此除了使用null参数外,实际上不可能在该上下文中调用setT()

这将按预期工作:

private void foo(Baz<Bar> baz, Bar bar) {
    baz.setT(bar);
}

我确信,Stackoverflow上有数百种此类问题的变体。 看来几乎每个程序员起初都误解了什么? 通配符用于并错误地使用它。

它的实用程序是在您的Bar类具有public T getT()方法的情况下。 Baz<? extends Bar>变量 Baz<? extends Bar>可以保存Baz<Bar>Baz<SubBar> ,你可以在它上面调用getT()来得到一个Bar (或某个子类)并可以这样使用。

你要做的不是类型安全。 如果你有:

private static class OtherSubBar extends Bar {}

然后你可以这样做:

Baz<SubBar> baz = new Baz<SubBar>();
foo(baz, new OtherSubBar());

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM