collections - Java excplicit cast of nested maps -
why cast work?
import java.util.hashmap; import java.util.map; public class testmap { public static void main(string[] args) { map<string, map<string, map<string, map<string,integer>>>> resultmap = new hashmap<>(); map<string, object> amap = new hashmap<string, object>(); map<string, integer> hiddenmap = new hashmap<string, integer>(); hiddenmap.put("fortytwo", 42); amap.put("key", hiddenmap); resultmap = (map<string, map<string, map<string, map<string, integer>>>>) amap.get("key"); system.out.println(resultmap); } }
also this:
map<string, map<string, map<string, map<string,map<string,integer>>>>> resultmap = new hashmap<>(); ... resultmap = (map<string, map<string, map<string, map<string,map<string,integer>>>>>) amap.get("key");
and on...
how happen hidden map map<string, integer>
gets cast map<string, map<string, map<string, map<string,integer>>>> resultmap
?
always prints:
{fortytwo=42}
also works (map instead of map):
public static void main(string[] args) { map<string, map<string, map<string, map<string,map<string,integer>>>>> resultmap = new hashmap<>(); map<string, map> amap = new hashmap<string, map>(); map<string, integer> hiddenmap = new hashmap<string, integer>(); hiddenmap.put("fortytwo", 42); amap.put("key", hiddenmap); resultmap = (map<string, map<string, map<string, map<string,map<string,integer>>>>>) amap.get("key"); system.out.println(resultmap); }
edit: @shizhz says, because of type erasure of course! code above equivalent to:
map resultmap = new hashmap(); map amap = new hashmap(); map hiddenmap = new hashmap(); hiddenmap.put("fortytwo", 42); amap.put("key", hiddenmap); resultmap = (map) amap.get("key");
which works
because java generics used @ compile time provide tighter type checks, type parameter erased compiler according type erasure rules:
- replace type parameters in generic types bounds or object if type parameters unbounded. produced bytecode, therefore, contains ordinary classes, interfaces, , methods.
- insert type casts if necessary preserve type safety.
- generate bridge methods preserve polymorphism in extended generic types.
in code map<string, map> amap = new hashmap<string, map>();
, value in amap
raw type map
, means compiler has no idea what's type contains, when try cast raw type of map
generics type of map
map<string, integer>
, best compiler can giving warning. generic type erased @ compile time , type cast generated when value generic map, can runtime classcastexception
exception if type mismatchs.
let's have @ following example:
public static void main(string[] args) { map map = new hashmap(); map.put("hello", "world"); map.put(new integer(1), 1); map.put(new object(), lists.newarraylist("hello")); map<string, integer> m = (map<string, integer>) map; system.out.println(m); integer = m.get("hello");// classcastexception happens @ here @ runtime }
i'm trying convert map
containing kinds of keys , values map<string, integer>
there's no compile error, after type erasure, above code equivalent to:
public static void main(string[] args) { map map = new hashmap(); map.put("hello", "world"); map.put(new integer(1), 1); map.put(new object(), lists.newarraylist("hello")); map m = (map) map; system.out.println(m); integer = (integer)m.get("hello"); }
now can tell why last line caused classcastexception
.
Comments
Post a Comment