具有功能接口作为值的复杂Map中的不兼容类型

时间:2019-07-18 22:17:18

标签: java generics functional-interface

我需要创建一个静态映射,该映射存储一些依赖于类类型作为键的实现。下面的代码片段中出现了一些类型兼容性问题。我花了很长时间解决这个问题,但没有成功。

// interface and classes to bound keys within Map
public interface IKey { ... }
public class Key1 extends IKey { ... }
public class Key2 extends IKey { ... }

// interface and classes to bound values within map
public interface IValue { ... }
public class Value1 implements IValue { ... }
public class Value2 implements IValue { ... }

public class Container {

    public static Map<Class<? extends IKey>, Function<? extends Set<? extends IValue>, Integer> funcs = new HashMap<>();

    static {
        funcs.put(Key1.class, Container::method1);
        funcs.put(Key2.class, Container::method2);
    }

    public static int method1(Set<Value1> s) {
        return 1;
    }

    public static int method2(Set<Value1> s) {
        return 2;
    }

}

问题描述:

Incompatible types: Set<? capture of IValue> is not convertible to Set<Value1>

我真的很困惑,因为当我更改Map定义时它正在工作,但是我无法绑定Set:(

public static Map<Class<? extends IKey>, Function<Set, Integer> funcs = new HashMap<>();

我也注意到,下面的代码是正确的(在静态块中)

Function<Set<Value1>, Integer> m1 = Container::method1;
Function<Set<Value1>, Integer> m2 = Container::method2;
List<Function<? extends Set<? extends IValue>, Integer>> l1 = Arrays.asList(m1, m2);
//adding new element is not working
l1.add(Container::method1);

期望您能期望我的方法不正确,以及如何构建类似的结构:)

感谢帮助

修改

Set<IValue>包含任何对象实现IValue,因此同时添加Value1Value2实例以进行设置是正确的。 Set<? extends IValue可以采用两种形式:Set<Value1>Set<Value2>。因此,Set<? extends IValue>的变量可以通过分配它们之一来初始化,无法添加新的值进行设置(类型未知) Set<? extends <Set<? extends IValue>>>外部集可以同时包含Set<Value1>Set<Value2>,但也不能更改。

就我而言:

public static Map<Class<? extends IKey>, Function<? extends Set<? extends IValue>, Integer>> funcs = new HashMap<>(); 

应该正常工作。更改静态块时确实如此:

static {
    Function<Set<Value1>, Integer> m = Container::method1;
    funcs.put(Key1.class, m);
}

我不知道为什么。也许方法引用上下文中有任何内部机制?

0 个答案:

没有答案