【问题标题】:Test if it is JSONObject or JSONArray测试是 JSONObject 还是 JSONArray
【发布时间】:2012-04-16 19:31:12
【问题描述】:

我有一个 json 流,它可以是:

{"intervention":

    { 
      "id":"3",
              "subject":"dddd",
              "details":"dddd",
              "beginDate":"2012-03-08T00:00:00+01:00",
              "endDate":"2012-03-18T00:00:00+01:00",
              "campus":
                       { 
                         "id":"2",
                         "name":"paris"
                       }
    }
}

或类似的东西

{"intervention":
            [{
              "id":"1",
              "subject":"android",
              "details":"test",
              "beginDate":"2012-03-26T00:00:00+02:00",
              "endDate":"2012-04-09T00:00:00+02:00",
              "campus":{
                        "id":"1",
                        "name":"lille"
                       }
            },

    {
     "id":"2",
             "subject":"lozlzozlo",
             "details":"xxx",
             "beginDate":"2012-03-14T00:00:00+01:00",
             "endDate":"2012-03-18T00:00:00+01:00",
             "campus":{
                       "id":"1",
                       "name":"lille"
                      }
            }]
}   

在我的 Java 代码中,我执行以下操作:

JSONObject json = RestManager.getJSONfromURL(myuri); // retrieve the entire json stream     
JSONArray  interventionJsonArray = json.getJSONArray("intervention");

在第一种情况下,上述方法不起作用,因为流中只有一个元素.. 如何检查流是object 还是array

我尝试使用json.length(),但没有成功..

谢谢

【问题讨论】:

标签: java json


【解决方案1】:

也许是这样的支票?

JSONObject intervention = json.optJSONObject("intervention");

如果干预对象不是 JSON 对象,则返回 JSONObjectnull。接下来,执行以下操作:

JSONArray interventions;
if(intervention == null)
        interventions=jsonObject.optJSONArray("intervention");

如果它是有效的JSONArray,这将返回一个数组,否则它将返回null

【讨论】:

    【解决方案2】:

    应该这样做:

    JSONObject json;
    Object     intervention;
    JSONArray  interventionJsonArray;
    JSONObject interventionObject;
    
    json = RestManager.getJSONfromURL(myuri); // retrieve the entire json stream     
    Object intervention = json.get("intervention");
    if (intervention instanceof JSONArray) {
        // It's an array
        interventionJsonArray = (JSONArray)intervention;
    }
    else if (intervention instanceof JSONObject) {
        // It's an object
        interventionObject = (JSONObject)intervention;
    }
    else {
        // It's something else, like a string or number
    }
    

    这样做的好处是只从主JSONObject 获取属性值一次。由于获取属性值涉及遍历哈希树或类似的,这对性能很有用(对于它的价值)。

    【讨论】:

      【解决方案3】:

      我没试过,但也许……

      
      JsonObject jRoot = RestManager.getJSONfromURL(myuri); // retrieve the entire json stream
      JsonElement interventionElement = jRoot.get("intervention");
      JsonArray interventionList = new JsonArray();
      
      if(interventionElement.isJsonArray()) interventionList.addAll(interventionElement.getAsJsonArray());
      else interventionList.add(interventionElement);
      

      如果是 JsonArray 对象,只需使用 getAsJsonArray() 进行转换即可。如果不是,它是一个单一的元素,所以只需添加它。

      无论如何,您的第一个示例已损坏,您应该要求服务器所有者修复它。 JSON 数据结构必须一致。这不仅仅是因为有时干预只带有一个元素,它不需要是一个数组。如果它只有 1 个元素,它将是一个只有 1 个元素的数组,但仍然必须是一个数组,以便客户端可以使用始终相同的模式对其进行解析。

      【讨论】:

        【解决方案4】:

        为简单起见,您只需检查服务器结果中的第一个字符串。

        String result = EntityUtils.toString(httpResponse.getEntity()); //this function produce JSON
        String firstChar = String.valueOf(result.charAt(0));
        
        if (firstChar.equalsIgnoreCase("[")) {
            //json array
        }else{
            //json object
        }
        

        这个技巧只是基于JSON格式的String {foo : "bar"}(object) 或[ {foo : "bar"}, {foo: "bar2"} ](数组)

        【讨论】:

          【解决方案5】:
              //returns boolean as true if it is JSONObject else returns boolean false 
          public static boolean returnBooleanBasedOnJsonObject(Object jsonVal){
                  boolean h = false;
                  try {
                      JSONObject j1=(JSONObject)jsonVal;
                      h=true;
                  } catch (Exception e) {
                      // TODO Auto-generated catch block
                      e.printStackTrace();
             if(e.toString().contains("org.json.simple.JSONArray cannot be cast to     org.json.simple.JSONObject")){
                          h=false;
                      }
                  }
                  return h;
          
              }
          

          【讨论】:

            【解决方案6】:
                  Object valueObj = uiJSON.get(keyValue);
                    if (valueObj instanceof JSONObject) {
                        this.parseJSON((JSONObject) valueObj);
                    } else if (valueObj instanceof JSONArray) {
                        this.parseJSONArray((JSONArray) valueObj);
                    } else if(keyValue.equalsIgnoreCase("type")) {
                        this.addFlagKey((String) valueObj);
                    }
            

            // 迭代 JSONArray 私有 void parseJSONArray(JSONArray jsonArray) 抛出 JSONException { for (Iterator iterator = jsonArray.iterator(); iterator.hasNext();) { JSONObject 对象 = (JSONObject) iterator.next(); this.parseJSON(object); } }

            【讨论】:

              【解决方案7】:

              您可以使用以下代码获取输入字符串的对象。

              String data = "{ ... }";
              Object json = new JSONTokener(data).nextValue();
              if (json instanceof JSONObject)
               //do something for JSONObject
              else if (json instanceof JSONArray)
               //do something for JSONArray
              

              链接:https://developer.android.com/reference/org/json/JSONTokener#nextValue

              【讨论】:

              • 在我的情况下这是最好的方法,并且还可以处理任何不适合这两种对象类型的响应
              • 这应该是正确的答案,尤其是在您有数据流的情况下。只需拉下 nextValue 并测试类型。
              猜你喜欢
              • 2011-09-01
              • 2017-10-13
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              相关资源
              最近更新 更多