Android Generics Error:该方法不适用于参数

时间:2013-08-06 13:59:15

标签: java android generics

我正在开发一个Android应用程序,我正在使用泛型来完成它的一部分。但是我收到了一个我无法理解的编译器错误。

我有以下架构:

public interface IMakeableEncryptionBundle<T, F> {
  public void setConfigurationFactory(F configurationFactory);
}

public class VigEncryptionBundle 
    implements IMakeableEncryptionBundle<ITextContent, VigConfigurationFactory> {
  @Override
  public void setConfigurationFactory(VigConfigurationFactory configFactory) {
    // Set the factory.
  }
}


public interface IConfigurationFactory { }

public final class VigConfigurationFactory implements IConfigurationFactory { }

我这样使用它:

private IMakeableEncryptionBundle<
    ITextContent,
    ? extends IConfigurationFactory> encryptionBundle
  = new VigEncryptionBundle();

这就是导致错误的原因:

VigConfigurationFactory configFactory = (VigConfigurationFactory) configObj;
encryptionBundle.setConfigurationFactory(configFactory);

“IMakeableEncryptionBundle类型中的方法setConfigurationFactory(捕获#8-of?extends IConfigurationFactory)不适用于参数(VigConfigurationFactory)”

但这不是“延伸”应该做的吗?允许您使用子类/实现吗?

这也不起作用:

encryptionBundle.setConfigurationFactory((IConfigurationFactory) configFactory);



修改 我想要实现的是,具有特定IConfiguration实现的独立性,并将encryptionBundle的实例化放在外部类中。

同时我需要泛型来确保特定的IMakeableEncryptionBundle实现可以使用它自己的IConfiguration实现。

此外,以下建议的下列内容给出了另一个错误:

private IMakeableEncryptionBundle<
    ITextContent,
    IConfigurationFactory> encryptionBundle
  = new VigEncryptionBundle();

“类型不匹配:无法从VigEncryptionBundle转换为IMakeableEncryptionBundle”


我甚至试图声明以下内容而没有任何变化:

public interface IMakeableEncryptionBundle<T, F extends IConfigurationFactory>

2 个答案:

答案 0 :(得分:2)

? extends IConfigurationFactory中的encryptionBundle类型表示“某些您不知道扩展IConfigurationFactory的类型。”变量encryptionBundle被赋值给某个值的事实可以给出更精确的类型是无关紧要的;类型检查器在检查赋值是否有效后立即忘记它。)

因此,当您尝试在setConfigurationFactory上致电VigConfigurationFactory时,类型检查器会理所当然拒绝它:您只知道F中显示的setConfigurationFactory参数类型是扩展IConfigurationFactory类,而不是特别是VigConfigurationFactory

如何解决这个问题取决于您想要首先使用该类型声明encryptionFactory的原因。如果可行,那么只需将? extends IConfigurationFactory更改为VigConfigurationFactory即可。否则,你如何解决问题将取决于你所追求的目标。

答案 1 :(得分:1)

我能够通过更改

让您的代码正常工作
private IMakeableEncryptionBundle<ITextContent, ? extends IConfigurationFactory> encryptionBundle = new VigEncryptionBundle();

private IMakeableEncryptionBundle<ITextContent, IConfigurationFactory> encryptionBundle = new VigEncryptionBundle();

我不太确定它背后的原因,但我认为它与IConfigurationFactory是一个接口这一事实有关。