简体   繁体   English

Java:使用泛型的类包装器

[英]Java : Class wrapper using generic

I would in some way store many different type in a HashMap, but in a way that when i extract them they will be well typed (and not an object). 我会以某种方式在HashMap中存储许多不同的类型,但是以某种方式,当我提取它们时,它们将被很好地键入(而不是对象)。

So i think about a wrapper that use generics 所以我想一个使用泛型的包装器

 public class Value <T>
 {
     private T innerValue ;

     public Value ( T _value )
     {
         innerValue = _value ;
     }

     public T read ()
     {
         return innerValue ;
     }
 }

but it does not work, for a test i made : 但它不起作用,对于我进行的测试:

 Value <Integer> va = new Value <Integer> ( 1 ) ;
 Value vc = va ;
 int restA = vc.read();

but i get a design time error, because vc.read() will return an Object() and not an Integer. 但是我收到设计时错误,因为vc.read()将返回Object()而不是Integer。 So what should i do to avoid this behaviour? 那么我应该怎么做才能避免这种行为? (if possible i would a solution that prevent 'va' from losing information about T instead of other workaround) (如果可能的话,我会提供一个解决方案,以防止'va'丢失有关T的信息,而不是其他解决方法)

Thanks in advance for any help. 在此先感谢您的帮助。

You casted va to a raw Value , vc . 您将va转换为原始Value vc When you use the raw form of a class, your T generic type parameter is replaced by Object . 使用类的原始形式时,您的T泛型类型参数将替换为Object So you cannot assign an Object to an int . 因此,您不能将Object分配给int

If you just call va.read() , then it will return an Integer , which will be unboxed to an int upon assignment to restA . 如果仅调用va.read() ,则它将返回一个Integer ,在分配给restA时将其拆箱为int

I would in some way store many different type in a HashMap, but in a way that when i extract them they will be well typed (and not an object). 我会以某种方式在HashMap中存储许多不同的类型,但是以某种方式,当我提取它们时,它们将被很好地键入(而不是对象)。

Short answer is: this is not possible. 简短的答案是:这是不可能的。 And type erasure is not the reason: it simply does not make much sense to have this information at compile time. 而且类型擦除不是原因:在编译时获取此信息根本没有多大意义。 Suppose that Java compiler had some kind of mechanism to keep track of the types of objects stuffed into a HashMap. 假设Java编译器具有某种机制来跟踪填充到HashMap中的对象的类型。 Then it also would have to cope with something like this: 然后,它也将不得不处理这样的事情:

HashMap<Integer, Value<?>> myMap = new HashMap<Integer, Value<?>>;
if (Math.random() > 0.5) {
    myMap.put(0, new Value<String>("hello world"));
} else {
    myMap.put(0, new Value<MacaroniExtruder>(new MacaroniExtruder()));
}
[whatDoYouWantToWriteHere?] value = myMap.get(0);

What you want is probably rather something like "type-union". 您想要的可能是“类型联合”之类的东西。 Unfortunately, it does not exist neither in Java, nor in Scala (where we have case-classes, which are almost just as good for that). 不幸的是,它既不存在于Java中,也不存在于Scala中(Scala中有案例类,对此几乎同样有用)。 So all you can do is basically: 因此,您所能做的基本上是:

A) Use polymorphism, define a proper interface, so that the concrete implementations become completely irrelevant, and work with that interface as second argument to your hash Map (preferred). A)使用多态性,定义一个适当的接口,以使具体的实现完全不相关,并使用该接口作为哈希映射的第二个参数(首选)。

B) Use instanceof and long if-else switches (ugly) B)使用instanceof和长的if-else开关(丑陋)

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

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