2010-12-07 147 views
2

你能帮我吗?下面的代码示例:Java泛型通配符扩展问题

public abstract class AbstractWorker { 

    public abstract void execute(); 

} 

public class Config { 

    public final String name; 

    public Config(final String name) { 
     this.name = name; 
    } 

} 

public abstract class AbstractWorkerFactory<C extends Config> { 

    public abstract AbstractWorker createWorker(final C configuration); 

} 

public class Service { 

    public AbstractWorker caramba(final AbstractWorkerFactory<? extends Config> factory, final Config configuration) { 
     // it is not compile :(
     return factory.createWorker(configuration); 
    } 

} 

下面的代码工作

public <C extends Config> AbstractWorker caramba(final AbstractWorkerFactory<C> factory, final C configuration) { 
    return factory.createWorker(configuration); 
} 

但是代码,使用服务无法指定泛型类型。是否有其他解决方案?
UPDATE(经过评估后):
1.集中工厂和配置实例在不同的地方(类)创建。
2.

public static class MegoConfig extends Config { 

public static class WorkerFactory extends AbstractWorkerFactory<Config> { 

public static class MegoWorkerFactory extends AbstractWorkerFactory<MegoConfig> { 

MegoWorkerFactory支持MegoConfig和配置。
我的任务的新解决方案。

public AbstractWorker caramba(final AbstractWorkerFactory<? super MegoConfig> factory, MegoConfig configuration) { 
     return factory.createWorker(configuration); 
} 

new Service().caramba(new WorkerFactory(), new MegoConfig("")); 
new Service().caramba(new MegoWorkerFactory(), new MegoConfig("")); 

非常感谢大家的回答!

+2

为什么使用Service的代码不能指定泛型?它有一个AbstractWorkerFactory ,还是Java 1.4? – ILMTitan 2010-12-07 21:17:23

回答

3

声明

public AbstractWorker caramba(final AbstractWorkerFactory<? extends Config> factory, final Config configuration) { 

太宽;它接受任何配置的WorkerFactory,而不是表示每个workerfactory都需要特定的配置。也就是说,写入

caramba(new AbstractWorkerFactory<FooConfiguration>() { ... }, new BarConfig()); 

即使该WorkerFactory不能使用该配置也是完全合法的。

在另一方面,声明

public <C extends Config> AbstractWorker caramba(final AbstractWorkerFactory<C> factory, final C configuration) 

正确地表示该供给WorkerFactory必须compatiable与所提供的结构,通过出现在这两个参数声明相同类型的可变的装置。

但是使用Service的代码无法指定泛型类型。是否有其他解决方案?

我不明白;为什么不能呢?为什么你需要另一种解决方案?

+0

嗨,非常感谢您的回答。我已更新帖子回答你的问题。 – 2010-12-08 06:40:34

0

这些都在同一个文件中吗?您不能在单个源文件中拥有多个公共类。虽然这不会解决泛型错误。

我在源文件与Service类提起这些,并得到了编译就好了:

class Config {} 
class AbstractWorker {} 
abstract class AbstractWorkerFactory<C extends Config> { 
    public abstract AbstractWorker createWorker(final C configuration); 
} 

那是什么用Service的代码?

0

没有,你所提供的解决方案可能是最好的:

public <C extends Config> AbstractWorker caramba(final AbstractWorkerFactory<C> factory, final C configuration) { 
    return factory.createWorker(configuration); 
} 

另外,您可以使用在的Caramba方法的原始签名,没有通配符,但这样会带来其他问题,比如编译器警告。