2015-07-20 55 views
1

我在java中编写了一些JSON解析代码,我有几个方法,它们之间的唯一区别是它们是否返回JSONObjectJSONArray。我想从这个去:创建模板类型的新对象,参数

private JSONArray getJsonArray(String path) throws IOException { 
    HttpGet httpget = new HttpGet(path); 
    httpget.setConfig(requestConfig); 

    try (CloseableHttpClient httpClient = httpClientBuilder.build()) { 
     try (CloseableHttpResponse result = httpClient.execute(apiHost, httpget)) { 
     return new JSONArray(new JSONTokener(result.getEntity().getContent())); 
     } 
    } 
    } 

    private JSONObject getJsonObject(String path) throws IOException { 
    HttpGet httpget = new HttpGet(path); 
    httpget.setConfig(requestConfig); 

    try (CloseableHttpClient httpClient = httpClientBuilder.build()) { 
     try (CloseableHttpResponse result = httpClient.execute(apiHost, httpget)) { 
     return new JSONObject(new JSONTokener(result.getEntity().getContent())); 
     } 
    } 
    } 

这个(无效代码):

private <T> get(String path, Class<T> type) throws IOException { 
    HttpGet httpget = new HttpGet(path); 
    httpget.setConfig(requestConfig); 

    try (CloseableHttpClient httpClient = httpClientBuilder.build()) { 
     try (CloseableHttpResponse result = httpClient.execute(apiHost, httpget)) { 
     return new T(new JSONTokener(result.getEntity().getContent())); 
     } 
    } 
    } 

如何正确初始化类型T的带参数的新对象?我能否以某种方式将T的可能值限制为JSONObject/JSONArray?我知道的<T extends Something>形式,但是这两个似乎从Object没有共同的接口:(

+0

'org.json'(我”假设你正在使用)不支持基因ric反序列化。使用更复杂的东西,如杰克逊或Gson。 –

+0

@SotiriosDelimanolis我不认为这是一个愚蠢的问题。另一个问题基本上是“如何解析JSON”,而这是“如何创建对应于泛型参数的类的实例”,它完全独立于JSON。 –

+0

@SotiriosDelimanolis提供的代码只是为了更好地说明我的观点。 tobias_k得到了我的问题的本质。 –

回答

1

你可以使用反射来获取并调用匹配的构造函数,如果有的话,如果没有这样的构造存在引发异常直继承。

private <T> T get(String path, Class<T> type) throws IOException { 
    HttpGet httpget = new HttpGet(path); 
    httpget.setConfig(requestConfig); 

    try (CloseableHttpClient httpClient = httpClientBuilder.build()) { 
     try (CloseableHttpResponse result = httpClient.execute(apiHost, httpget)) { 
      Constructor<T> constructor = type.getConstructor(JSONTokener.class); 
      return constructor.newInstance(new JSONTokener(result.getEntity().getContent())); 
     } catch (ReflectiveOperationException e) { 
      throw new IllegalArgumentException("Provided result class does not accept JSONTokener parameter."); 
     } 
    } 
} 

注意,这是有点duck typing,即你真的不限制类型JSONObjectJSONArray而是一切提供了相应的构造是好的。

+0

谢谢,这正是我正在寻找的。考虑到我的大部分编程经验都是用鸭子语言编写的,我对此很满意。我限制为'JSONObject' /'JSONArray'的思路是为了让编译器能够推断出T总是会有正确的构造函数,而不是限制函数被调用的方式。 –

相关问题