2016-08-09 14 views
6

Bây giờ tôi viết một cách phổ biến để lấy dữ liệu JSONObject từ một khóa. Bây giờ tôi phải thay đổi kiểu này thành một phương thức chung?Làm thế nào để thay đổi phương pháp của tôi thành một phương pháp chung?

String a= (String) ObdDeviceTool.getResultData(result, "a", String.class); 
Double b= (Double) ObdDeviceTool.getResultData(result, "b", Double.class); 
public static Object getJSONObjectData(JSONObject result,String key,Object type){ 
    if (result.containsKey(key)) { 
     if(type.equals(String.class)) 
      return result.getString(key); 
     if(type.equals(Double.class)) 
      return result.getDouble(key); 
     if(type.equals(Long.class)) 
      return result.getLong(key); 
     if(type.equals(Integer.class)) 
      return result.getInt(key); 
    } 
    return null; 
} 
+0

@ JonnyHenly, tôi đã thử, nhưng tìm thấy nó không thể thay đổi.public static T getJSONObjectData (kết quả JSONObject, String key, loại T) – flower

Trả lời

3
private static <T> T getJSONObjectData(JSONObject result, String key, Class<T> type) 
{ 
    Object value = result.get(key); 
    return type.cast(value); 
} 

Những gì bạn phải được nhận thức của:

  • Một JSONException sẽ nổi lên nếu key không tồn tại trong result
  • Một ClassCastException sẽ nổi lên nếu type không phù hợp với các loại thực của value

Hãy thoải mái xử lý các cấp ở trên nếu cần thiết.

+0

Nó có lỗi, nếu giá trị khóa là0, result.getDouble (key) OK.But Double.cast (0) là sai. – flower

+0

@flower Hum bạn nói đúng. Tuy nhiên tôi không chắc cách tiếp cận tốt nhất là giải quyết điều đó. Có thể chấp nhận để bạn lấy giá trị dưới dạng 'Số' không? Nếu không với giải pháp này, bạn sẽ phải chú ý chèn '0.0' khi bạn biết rằng bạn sẽ lấy giá trị này làm gấp đôi. – Spotted

+0

Có, nếu nó trả về 0 nhưng đôi khi trả lại giá trị gấp đôi, tôi không thể sử dụng theo cách của bạn. Tôi sử dụng cách cũ của tôi trong bản demo câu hỏi. – flower

1

JSONObject có phương thức trả về đối tượng.

Integer i = (Integer) result.get("integerKey"); 
String s = (String) result.get("stringKey"); 
Double d = (Double) result.get("doubleKey"); 

result là đối tượng JSONObject của bạn.

2

Lấy câu trả lời bằng @Spotted một chút nữa, tôi muốn sử dụng mô hình chiến lược và làm điều gì đó như thế này:

private static final Map<Class<?>, BiFunction<JSONObject, String, Object>> converterMap = 
    initializeMap(); 

private static Map<Class<?>, BiFunction<JSONObject, String, Object>> initializeMap() { 
    Map<Class<?>, BiFunction<JSONObject,String, Object>> map = new HashMap<>(); 
    map.put(String.class, (jsonObject, key) -> jsonObject.getString(key)); 
    map.put(Integer.class, (jsonObject, key) -> jsonObject.getInt(key)); 
    // etc. 
    return Collections.unmodifiableMap(map); 
} 

private static <T> Optional<T> getJSONObjectData(JSONObject json, String key, Class<T> type) { 

    return 
    Optional.ofNullable(converterMap.get(key)) 
    .map(bifi -> bifi.apply(json, key)) 
    .map(type::cast); 
} 

Bây giờ bạn có một bản đồ của bộ chuyển đổi, nơi mà quan trọng là loại mục tiêu. Nếu một trình biến đổi tồn tại cho loại của bạn, nó được sử dụng, và đối tượng của bạn được trả về đúng loại. Nếu không, Optional.empty() được trả về.

Đây là một ứng dụng của
Effective Java (2nd Edition) mục 29:
Consider typesafe heterogeneous containers.

+0

Tôi thích câu trả lời này cho việc truyền an toàn nhưng nó không biên dịch. Bạn nên thay thế 'Bản đồ <..., Hàm <...>>' bằng 'Bản đồ <..., BiFunction <...>>' và 'converterMap.get (khóa)' bằng 'converterMap.get (type)'. – Spotted

+0

@Spotted ah yes, được cấu trúc lại từ phiên bản cũ hơn và bị mất một địa điểm. cảm ơn –

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