2

我很难弄清楚如何使用 Guice 将接口绑定到枚举。

public interface Snack {
    public int caloriesCount();
}

public enum Chocolate implements Snack {
    MILK(20),
    DARK(5),
    WHITE(10);

    private int calCount;

    private Chocolate(int calCount) {
        this.calCount = calCount;
    }

    @Override
    public int caloriesCount() {
        return calCount;
    }   
}

如果我尝试: bind(Snack.class).to(Chocolate.class);

我明白了No implementation for Chocolate was bound

我知道,与其尝试绑定到枚举,我应该绑定到该枚举值的集合,但这让我无法做到这一点。感谢任何提示。谢谢, 马切克

4

1 回答 1

13

像这样绑定到枚举类是不可能的,因为 Guice 无法创建自己的实例。在这里,默认行为是创建 的新实例Chocolate,这没有多大意义—<a href="http://docs.oracle.com/javase/tutorial/java/javaOO/enum.html " rel="noreferrer">每个可能的枚举实例都必须在编译时在枚举本身内声明,Guice 不会为您选择任意现有的实例。

您可能想做以下三件事之一:

  1. 绑定Snack到特定类型的Chocolate.

    bind(Snack.class).toInstance(Chocolate.DARK);
    
  2. 绑定SnackChocolateChocolate特定类型的Chocolate. 这和上面的一样,但是现在你可以直接请求Chocolate并获取一个实例,而不是只能请求一个Snack.

    bind(Snack.class).to(Chocolate.class);
    bind(Chocolate.class).toInstance(Chocolate.DARK);
    
  3. 允许开发人员注入一个Set<Snack>,它恰好返回所有Chocolate实例。

    // manual wildcard required so we don't get an ImmutableSet<Chocolate>
    Set<Snack> setOfSnacks = ImmutableSet.<Snack>copyOf(Chocolate.values());
    
    // bind a Set<Snack> specifically
    bind(new TypeLiteral<Set<Snack>>() {}).toInstance(setOfSnacks);
    

    您可以使用任何 Set 实现,但由于所有toInstance绑定都是隐式单例,因此如果您使用GuavaImmutableSet或至少Collections.unmodifiableSet. 如果这接近您想要的,您可能有兴趣了解可选的Multibindings 插件

    当然,您也可以编写自己Provider<Set<Snack>>的方法或方法@Provides Set<Snack>,从而每次都获得一个新的集合实例......但如果您希望在您的应用程序中使用它,那么共享一个不可变副本可能更有意义。

于 2013-10-31T03:14:37.983 回答