2011-08-12 29 views
24

Tôi có một câu hỏi tương tự như một số câu hỏi tại stackoverflow nhưng không ai thực sự trả lời được vấn đề của tôi. Tôi sử dụng ObjectMapper của Jackson và muốn phân tích chuỗi JSON này vào một danh sách các đối tượng sử dụng:Jackson JSON + Java Generics được LinkedHashMap

[{ "user" : "Tom", "role" : "READER" }, 
{ "user" : "Agnes", "role" : "MEMBER" }] 

tôi xác định một lớp bên trong như thế này:

public class UserRole { 

    private String user 
    private String role; 

    public void setUser(String user) { 
     this.user = user; 
    } 

    public void setRole(String role) { 
     this.role = role; 
    } 

    public String getUser() { 
     return user; 
    } 

    public String getRole() { 
     return role; 
    } 
} 

Để phân tích cú pháp JSON String để một Danh sách của UserRoles tôi sử dụng Generics:

protected <T> List<T> mapJsonToObjectList(String json) throws Exception { 
    List<T> list; 
    try { 
     list = mapper.readValue(json, new TypeReference<List<T>>() {}); 
    } catch (Exception e) { 
     throw new Exception("was not able to parse json"); 
    } 
    return list; 
} 

Nhưng những gì tôi nhận được lại là một List của LinkedHashMaps.

Có gì sai với mã của tôi?

+1

Đó là ngôn ngữ Java, và loại tẩy xoá khét tiếng: T trong đó là một biến kiểu chứ không phải gõ nét; và về cơ bản có nghĩa là bạn đang yêu cầu Danh sách . Sau đó Jackson liên kết JSON bằng các kiểu đối tượng 'tự nhiên', và đối tượng JSON sau đó trở thành Bản đồ (thuộc loại LinkedHashMap lưu giữ thứ tự). Bạn đã giải quyết được vấn đề một cách chính xác bằng cách chuyển Class, sau đó xác định loại thực tế. – StaxMan

Trả lời

30

Các công trình sau đây và theo lời khuyên của StaxMan không còn sử dụng phương pháp tĩnh không được chấp nhận collectionType() nữa.

public class SoApp 
{ 

    /** 
    * @param args 
    * @throws Exception 
    */ 
    public static void main(String[] args) throws Exception 
    { 
     System.out.println("Hello World!"); 

     String s = "[{\"user\":\"TestCity\",\"role\":\"TestCountry\"},{\"user\":\"TestCity\",\"role\":\"TestCountry\"}]"; 
     StringReader sr = new StringReader("{\"user\":\"TestCity\",\"role\":\"TestCountry\"}"); 
     //UserRole user = mapper.readValue(sr, UserRole.class); 

     mapJsonToObjectList(new UserRole(),s,UserRole.class); 

    } 

    protected static <T> List<T> mapJsonToObjectList(T typeDef,String json,Class clazz) throws Exception 
    { 
     List<T> list; 
     ObjectMapper mapper = new ObjectMapper(); 
     System.out.println(json); 
     TypeFactory t = TypeFactory.defaultInstance(); 
     list = mapper.readValue(json, t.constructCollectionType(ArrayList.class,clazz)); 

     System.out.println(list); 
     System.out.println(list.get(0).getClass()); 
     return list; 
    } 
} 

...

public class UserRole{ 

    private String user; 
    private String role; 

    public void setUser(String user) { 
     this.user = user; 
    } 

    public void setRole(String role) { 
     this.role = role; 
    } 

    public String getUser() { 
     return user; 
    } 

    public String getRole() { 
     return role; 
    } 

    @Override 
    public String toString() 
    { 
     return "UserRole [user=" + user + ", role=" + role + "]"; 
    } 

} 

đầu ra ...

Hello World! 
[{"user":"TestCity","role":"TestCountry"},{"user":"TestCity","role":"TestCountry"}] 
[UserRole [user=TestCity, role=TestCountry], UserRole [user=TestCity, role=TestCountry]] 
class com.test.so.fix.UserRole 
+2

Đúng. Một lưu ý nhỏ là để có được xung quanh vấn đề không dùng nữa, bạn có thể gọi 'objectMapper.getTypeFactory()' để sử dụng các phương thức không tĩnh; sự thay đổi này (để sử dụng các thể hiện TypeFactory) trong Jackson 1.8 là cần thiết để hỗ trợ các ngôn ngữ JVM như Scala có các kiểu Collection/Map riêng của chúng ... – StaxMan

+0

@StaxMan - cảm ơn cập nhật để bao gồm phương thức không được chấp nhận – nsfyn55

+1

@ nsfyn55 câu trả lời của bạn bao gồm hai chính điểm của loại câu hỏi đó. Sử dụng 'T' và xử lý nó bằng các phương thức không được chấp nhận. Bỏ phiếu. – kamaci

Các vấn đề liên quan