【问题标题】:How to get all keys/sub keys from JSONObject in java?java - 如何从Java中的JSONObject获取所有键/子键?
【发布时间】:2018-04-12 06:04:06
【问题描述】:

这是我的 JSONObject:

{
    "per_page": 3,
    "total": 12,
    "data": [{
            "color": "#98B2D1",
            "year": 2000,
            "name": "cerulean",
            "id": 1,
            "pantone_value": "15-4020"
        }, {
            "color": "#C74375",
            "year": 2001,
            "name": "fuchsia rose",
            "id": 2,
            "pantone_value": "17-2031"
        }
    ],
    "page": 1,
    "total_pages": 4
}

从这里我应该得到所有的键,包括per_page,total,data,color,year,pantone_value,name,pagetotal_pages

如果我使用 JSONObject.names() 或 JSONObject.keySet() 。我只得到最外面的键

【问题讨论】:

    标签: java json


    【解决方案1】:
    package com.samples;
    
    import java.util.Iterator;
    
    import gvjava.org.json.JSONArray;
    import gvjava.org.json.JSONException;
    import gvjava.org.json.JSONObject;
    
    public class JSONObjectSample {
    
        public static void main (String [] args) {
            String jsonString = new String("{\"per_page\": 3,\"total\": 12,\"data\": [{\"color\": \"#98B2D1\",\"year\": 2000,\"name\": \"cerulean\",\"id\": 1,\"pantone_value\": \"15-4020\" }, {\"color\": \"#C74375\",\"year\": 2001,\"name\": \"fuchsia rose\",\"id\": 2,\"pantone_value\": \"17-2031\" }], \"page\": 1,\"total_pages\": 4 }\r\n");
            try {
                JSONObject jsonObject = new JSONObject(jsonString);
                Iterator<String> keys = jsonObject.keys();
                while(keys.hasNext()) {
                    String key = keys.next();
                    System.out.println(key);
                    if(jsonObject.get(key) instanceof JSONArray) {
                        JSONArray array = (JSONArray) jsonObject.get(key);
                        JSONObject object = (JSONObject) array.get(0);
                        Iterator<String> innerKeys = object.keys();
                        while(innerKeys.hasNext()) {
                            String innerKey = innerKeys.next();
                            System.out.println(innerKey);
                        }
                    }
                }
    
            } catch (JSONException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
    
    }
    

    【讨论】:

    • 这只是为了解决手头的问题。您需要编写一个递归逻辑来进入每个内部 JSONArray 和 JSONObjects 以获取它们各自的键。
    • 我建议编写一个带有签名的简单函数,如 public String[] getKeys(JSONObject jsonObject) 并在遇到 JSONArray 或 JSONObject 类型的值对象时递归调用它。
    【解决方案2】:

    您可以使用 google gson 对象解析器。 (这不是很漂亮的代码,但它可以完成工作)

    import com.google.gson.JsonObject;
    import com.google.gson.JsonParser;
    
    import java.util.HashSet;
    import java.util.Set;
    
    public class GetKeys {
        public static void main(String[] args) {
            String jsonString = "{\"per_page\": 3,\"total\": 12,\"data\": [{\"color\": \"#98B2D1\",\"year\": 2000,\"name\": \"cerulean\",\"id\": 1,\"pantone_value\": \"15-4020\" }, {\"color\": \"#C74375\",\"year\": 2001,\"name\": \"fuchsia rose\",\"id\": 2,\"pantone_value\": \"17-2031\" }], \"page\": 1,\"total_pages\": 4 }\r\n";
            JsonParser parser = new JsonParser();
            JsonObject object = (JsonObject) parser.parse(jsonString);
            Set<String> keys = new HashSet<>();
    
            parseAllKeys(keys, object);
    
            keys.forEach(System.out::println);
        }
    
        private static void parseAllKeys(Set<String> keys, JsonObject object) {
            keys.addAll(object.keySet());
            object.entrySet().stream().filter(entry -> entry.getValue().isJsonObject()).forEach(entry -> parseAllKeys(keys, (JsonObject) entry.getValue()));
            object.entrySet().stream().filter(entry -> entry.getValue().isJsonArray()).forEach(entry -> entry.getValue().getAsJsonArray().forEach(subEntry -> parseAllKeys(keys, (JsonObject) subEntry)));
        }
    }
    

    【讨论】:

    • { "RestResponse": { "result": [{ "area": "12541302SKM", "country": "IND", "capital": "Srinagar Jammu", "name": "查谟和克什米尔”,“id”:65,“largest_city”:“斯利那加查谟”,“缩写”:“JK”}],“消息”:[“共找到 [36] 条记录。” ] } } .当我尝试使用这个 json 时,我得到 com.google.gson.JsonPrimitive 无法转换为 com.google.gson.JsonObject
    • 好吧,您给出的 json 与您的问题不同。当然,您可以调整代码以使其更通用。无论给出什么答案,您都需要理解代码。
    【解决方案3】:
    import org.json.JSONArray;
    import org.json.JSONException;
    import org.json.JSONObject;
    
    public class MyClass
    {
        public static ArrayList<String> keylist = new ArrayList<String>();
        public static void main(String args[]) throws JSONException
        {
            myfunction(myjson);
            System.out.println(keylist);
        }
    
        public static void myfunction(JSONObject x) throws JSONException
        {
            JSONArray keys =  x.names();
            for(int i=0;i<keys.length();i++)
            {
                String current_key = keys.get(i).toString();   
                if( x.get(current_key).getClass().getName().equals("org.json.JSONObject"))
                {
                    keylist.add(current_key);
                    myfunction((JSONObject) x.get(current_key));
                } 
                else if( x.get(current_key).getClass().getName().equals("org.json.JSONArray"))
                {
                    for(int j=0;j<((JSONArray) x.get(current_key)).length();j++)
                    {
                        if(((JSONArray) x.get(current_key)).get(j).getClass().getName().equals("org.json.JSONObject"))
                        {
                            keylist.add(current_key);
                            myfunction((JSONObject)((JSONArray) x.get(current_key)).get(j));
                        }
                    }
                }
                else 
                {
                    keylist.add(current_key);
                }
            }
        }
    }
    

    可能性:

    1. “键”:“值”
    2. “键”:{对象}
    3. “键”:[数组]

    逻辑:

    1. 如果它只包含值,我将键添加到我的列表中。
    2. 如果它是一个对象,我会存储键并将值递归地发送到同一个函数。
    3. 如果它是一个数组,我检查它是否包含一个对象,如果是,我存储键并将值递归地发送到同一个函数。

    【讨论】:

    • 尽管您的答案是否正确,但您应该提供一些解释,而不仅仅是代码
    【解决方案4】:

    下面的示例代码将采用 JsonObject 并将 Keys 转换为小写。这两种方法结合使用,如果请求中有任何数组,它也会在需要时转换这些键并使用递归。

    public JsonArray parseArrayKeysToLower(JsonArray arrRequest) {
        JsonArray arrayTemp = new JsonArray();
        for(int i = 0; i < arrRequest.size(); i++) {
          if (arrRequest.getValue(i) instanceof JsonObject) {
            arrayTemp.add(parseObjectKeysToLower((JsonObject) arrRequest.getValue(i)));
          } else if (arrRequest.getValue(i) instanceof JsonArray) {
            arrayTemp.add(parseArrayKeysToLower((JsonArray) arrRequest.getValue(i)));
          } else {
            arrayTemp.add(arrRequest.getValue(i));
          }
        }
        return arrayTemp;
      }
    
      public JsonObject parseObjectKeysToLower(JsonObject request) {
        JsonObject requestToLower = new JsonObject();
        try {
          request.forEach(e -> {
            String key = e.getKey();
            if (e.getValue() instanceof JsonObject) {
              requestToLower.put(key.toLowerCase(), parseObjectKeysToLower((JsonObject) e.getValue()));
            } else if (e.getValue() instanceof JsonArray) {
              requestToLower.put(key.toLowerCase(), parseArrayKeysToLower((JsonArray) e.getValue()));
            } else {
              requestToLower.put(key.toLowerCase(), e.getValue());
            }
          });
        } catch (Exception e) {
          e.printStackTrace();
        }
        return requestToLower;
      }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-10-02
      • 2014-07-29
      • 2012-08-07
      • 1970-01-01
      • 2010-11-25
      • 1970-01-01
      相关资源
      最近更新 更多