1

I am trying to write a generic code were a JSON array as below example can be converted to a map .

This is sample . where parent element is menu

{"menu": {    
    "items": [
        {"id": "Open"},
        {"id": "OpenNew", "label": "Open New"},        
        {"id": "ZoomIn", "label": "Zoom In"},
        {"id": "ZoomOut", "label": "Zoom Out"},            
        {"id": "Quality"},
        {"id": "Pause"}
    ]
}}

to map having map values as :

menu.items_0.id=open    
menu.items_1.id=OpenNew
menu.items_1.label=Open New    
menu.items_2.id=ZoomIn
menu.items_2.label=Zoom In    
menu.items_3.id=ZoomOut
menu.items_3.id=Zoom Out    
menu.items_4.id=Quality    
menu.items_5.id=Pause
5

4 Answers 4

0

For my answer you need these classes:

org.json.JSONArray;
org.json.JSONException;
org.json.JSONObject;

And I'm assuming a class like this:

public class menu{
    private String id;
    private String label;
}

To parse - I'm ignoring if it's a stream, file, etc -. However, it assumes you've manipulated your source to create a single long String object called myString.

JSONObject topLevel = new JSONObject( myString );
JSONObject itemsArray= topLevel.getJSONArray("items");

int tempID;
String tempLabel;

//Now go through all items in array.
for(int i =0; i < itemsArray.length(); i++){
    tempID = itemsArray.getJSONObject(i).getString("id");

    if(itemsArray.getJSONObject(i).has("label"))
        tempLabel = itemsArray.getJSONObject(i).getString("label");
    else
        tempLabel = null;

    //whatever action you need to take
    menu = new menu( tempId, tempLabel);
}
Sign up to request clarification or add additional context in comments.

2 Comments

I to gave a same thought earlier but I want a generic code which will functional irrespective of element names.
I worked this with a HashMap class, which I think operates in a similar fashion since it implements the Map interface. I would work it as:
0

This code here gets the job done. You can extract some methods, or refactor it a little, but it should do the trick.

public class Example {

    public static void main(String[] args) {

        String source = "{\"menu\": {\"items\": [{\"id\": \"Open\"},{\"id\": \"OpenNew\", \"label\": \"Open New\"}, " +
                "{\"id\": \"ZoomIn\", \"label\": \"Zoom In\"},"
                + "{\"id\": \"ZoomOut\", \"label\": \"Zoom Out\"},{\"id\": \"Quality\"},{\"id\": \"Pause\"}"
                + "]}}";

        JSONObject jsonObject = new JSONObject(source);

        Map<String, Object> map = jsonObject.toMap();

        Map<String, String> resultMap = new HashMap<>();

        map
                .entrySet()
                .forEach(entry -> addToResult(entry, resultMap, "", ""));

        System.out.println(resultMap);

    }

    private static void addToResult(Map.Entry<String, Object> entry, Map<String, String> resultMap, String fieldNameAcummulator, String index) {
        Object value = entry.getValue();
        if (!Map.class.isAssignableFrom(value.getClass()) && !List.class.isAssignableFrom(value.getClass())) {
            resultMap.put(addToAccumulator(entry, fieldNameAcummulator, index), (String) value);
            return;
        }

        if (Map.class.isAssignableFrom(value.getClass())) {
            Map<String, Object> nestedMap = (HashMap<String, Object>) value;
            nestedMap
                    .entrySet()
                    .forEach(nestedEntry -> addToResult(nestedEntry, resultMap, addToAccumulator(entry, fieldNameAcummulator, index), ""));
        } else {
            List<HashMap<String, Object>> hashMaps = (List<HashMap<String, Object>>) value;
            IntStream.range(0, hashMaps.size())
                    .forEach(listIndex -> {
                        HashMap<String, Object> nestedMap = hashMaps.get(listIndex);
                        nestedMap.entrySet().forEach(nestedEntry -> addToResult(nestedEntry, resultMap, addToAccumulator(entry, fieldNameAcummulator, index), String.valueOf(listIndex)));
                    });
        }
    }

    private static String addToAccumulator(Map.Entry<String, Object> entry, String fieldNameAcummulator, String index) {
        return fieldNameAcummulator.isEmpty()
                ? entry.getKey()
                : fieldNameAcummulator + getKeyValueWithIndex(entry, index);
    }

    private static String getKeyValueWithIndex(Map.Entry<String, Object> entry, String index) {
        return index.isEmpty()
                ? ".".concat(entry.getKey())
                : "_".concat(index).concat(".").concat(entry.getKey());
    }
}

Feel free to ask if you have any questions regarding the implementation.

Hope it helps!

Comments

0

I have change some logic and it works fine after that.

import com.google.gson.JsonArray;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.json.JSONArray;
import org.json.JSONObject;

public class JsonToMapConvertor {

    private static HashMap<String, Object> mapReturn = new HashMap<String, Object>();
    public static JsonParser parser = new JsonParser();

    public static void main(String[] args) throws Exception{

    String json ="{\n" +
"    \"glossary\": {\n" +
"        \"title\": \"example glossary\",\n" +
"       \"GlossDiv\": {\n" +
"            \"title\": \"S\",\n" +
"           \"GlossList\": {\n" +
"                \"GlossEntry\": {\n" +
"                    \"ID\": \"SGML\",\n" +
"                   \"SortAs\": \"SGML\",\n" +
"                   \"GlossTerm\": \"Standard Generalized Markup Language\",\n" +
"                   \"Acronym\": \"SGML\",\n" +
"                   \"Abbrev\": \"ISO 8879:1986\",\n" +
"                   \"GlossDef\": {\n" +
"                        \"para\": \"A meta-markup language, used to create markup languages such as DocBook.\",\n" +
"                       \"GlossSeeAlso\": [\"GML\", \"XML\"]\n" +
"                    },\n" +
"                   \"GlossSee\": \"markup\"\n" +
"                }\n" +
"            }\n" +
"        }\n" +
"    }\n" +
"}";

       HashMap<String, Object> map = createHashMapFromJsonString(json,""); 
        System.out.println("map size "+map.size());

        for (Map.Entry<String, Object> entry : map.entrySet()) {            
          if(!entry.getValue().toString().contains("{"))  
                System.out.println(entry.getKey()+" : "+entry.getValue());
        }

    }

public static HashMap<String, Object> createHashMapFromJsonString(String json,String prefix) throws Exception{   

    if(json.startsWith("[",0)){        
        JSONArray jsonArray = new JSONArray(json);    
            for (int i = 0; i < jsonArray.length(); i++){
                JSONObject jsonobject = jsonArray.getJSONObject(i);               
                createHashMapFromJsonString(jsonobject.toString(), prefix+"_"+i);
            }        
    }    
    else{

        JsonObject object = (JsonObject) parser.parse(json);   
        Set<Map.Entry<String, JsonElement>> set = object.entrySet();
        Iterator<Map.Entry<String, JsonElement>> iterator = set.iterator();
        while (iterator.hasNext()) {

            Map.Entry<String, JsonElement> entry = iterator.next(); 
            String key = entry.getKey();

            if(prefix.length()!=0){
                key = prefix + "."+key;
            }

            JsonElement value = entry.getValue();
            if (null != value) {            
                if (!value.isJsonPrimitive()) {
                    if (value.isJsonObject()) {                        
                        mapReturn.put(key, createHashMapFromJsonString(value.toString(),key));
                    } else if (value.isJsonArray() && value.toString().contains(":")) {

                        List<HashMap<String, Object>> list = new ArrayList<>();
                        JsonArray array = value.getAsJsonArray();
                        if (null != array) {
                            for (JsonElement element : array) {                               
                                if (!element.isJsonPrimitive()) {
                                       createHashMapFromJsonString(value.toString(),key);
                                }else{
                                    list.add(createHashMapFromJsonString(value.toString(),key));
                                    }
                                }                 
                            mapReturn.put(key, list);
                        }
                    } else if (value.isJsonArray() && !value.toString().contains(":")) {                    
                        mapReturn.put(key, value.getAsJsonArray());
                    }              
                } else {
                    mapReturn.put(key, value.getAsString());
                }
            }
        }
    }
    return mapReturn;
  }
}

Comments

0

Just another way of converting JSONObject as List of Map as Generic

public static List<Map<String, Object>> getJsonNode(String jsonContents, String nodeName)
        throws JsonProcessingException, IOException, ParseException {
    JSONParser parser = new JSONParser();
    JSONObject json = (JSONObject) parser.parse(jsonContents);

    Object o = json.get(nodeName);
    List<Map<String, Object>> results = Lists.newArrayList();

    if (o instanceof JSONObject) {
        results.add((Map<String, Object>) o);
    } else if (o instanceof JSONArray) {
        List<Map<String, Object>> hashMaps = (List<Map<String, Object>>) o;
        results.addAll((Collection<? extends Map<String, Object>>) hashMaps);
    }
    return results;
}

/**
 * Driver
 * 
 * @param args
 * @throws IOException
 * @throws ParseException
 */
public static void main(String[] args) throws IOException, ParseException {
    String jsonInputFile = "temp/input.json";
    String jsonContents = new String(Files.readAllBytes(Paths.get(jsonInputFile)));

    List<Map<String, Object>> results = getJsonNode(jsonContents, "summary");
    for (Map<String, Object> entry : results) {
        System.out.println(entry);
    }
    ///////////////////////////////////////
    results = getJsonNode(jsonContents, "payWay");
    for (Map<String, Object> entry : results) {
        System.out.println(entry);
    }
    ///////////////////////////////////////
    results = getJsonNode(jsonContents, "sellerDetails");
    for (Map<String, Object> entry : results) {
        System.out.println(entry);
    }
}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.