Gson을 사용하여 JSON을 HashMap으로 변환하려면 어떻게 해야 합니까?
데이터를 JSON 형식으로 반환하는 서버에 데이터를 요청합니다.요청을 할 때 HashMap을 JSON에 삽입하는 것은 전혀 어렵지 않지만, 그 반대는 조금 어려운 것 같습니다.JSON 응답은 다음과 같습니다.
{
"header" : {
"alerts" : [
{
"AlertID" : "2",
"TSExpires" : null,
"Target" : "1",
"Text" : "woot",
"Type" : "1"
},
{
"AlertID" : "3",
"TSExpires" : null,
"Target" : "1",
"Text" : "woot",
"Type" : "1"
}
],
"session" : "0bc8d0835f93ac3ebbf11560b2c5be9a"
},
"result" : "4be26bc400d3c"
}
이 데이터에 가장 쉽게 접근할 수 있는 방법은 무엇입니까?GSON 모듈을 사용하고 있습니다.
여기 있습니다.
import java.lang.reflect.Type;
import com.google.gson.reflect.TypeToken;
Type type = new TypeToken<Map<String, String>>(){}.getType();
Map<String, String> myMap = gson.fromJson("{'k1':'apple','k2':'orange'}", type);
이 코드는 동작합니다.
Gson gson = new Gson();
String json = "{\"k1\":\"v1\",\"k2\":\"v2\"}";
Map<String,Object> map = new HashMap<String,Object>();
map = (Map<String,Object>) gson.fromJson(json, map.getClass());
질문인 , JSON을 으로 asonsonsonsonsonsonsonsonsonsonsonsonsonsonsonsonsonsonsonJSON으로 솔루션을 .Map<String, Object>
못했습니다
으로 yaml deserializer로 되어 있습니다.Map<String, Object>
유형을 지정하지 않았지만 gson은 이 작업을 수행하지 않는 것 같습니다.운 좋게도 당신은 맞춤 탈시리얼라이저로 그것을 달성할 수 있다.
과 같은 하여 모든 것을 로 디세리얼라이저는 디세리얼라이저입니다.JsonObject
~ ~까지Map<String, Object>
★★★★★★★★★★★★★★★★★」JsonArray
~ ~까지Object[]
모든 가 유사하게 . 이치노
private static class NaturalDeserializer implements JsonDeserializer<Object> {
public Object deserialize(JsonElement json, Type typeOfT,
JsonDeserializationContext context) {
if(json.isJsonNull()) return null;
else if(json.isJsonPrimitive()) return handlePrimitive(json.getAsJsonPrimitive());
else if(json.isJsonArray()) return handleArray(json.getAsJsonArray(), context);
else return handleObject(json.getAsJsonObject(), context);
}
private Object handlePrimitive(JsonPrimitive json) {
if(json.isBoolean())
return json.getAsBoolean();
else if(json.isString())
return json.getAsString();
else {
BigDecimal bigDec = json.getAsBigDecimal();
// Find out if it is an int type
try {
bigDec.toBigIntegerExact();
try { return bigDec.intValueExact(); }
catch(ArithmeticException e) {}
return bigDec.longValue();
} catch(ArithmeticException e) {}
// Just return it as a double
return bigDec.doubleValue();
}
}
private Object handleArray(JsonArray json, JsonDeserializationContext context) {
Object[] array = new Object[json.size()];
for(int i = 0; i < array.length; i++)
array[i] = context.deserialize(json.get(i), Object.class);
return array;
}
private Object handleObject(JsonObject json, JsonDeserializationContext context) {
Map<String, Object> map = new HashMap<String, Object>();
for(Map.Entry<String, JsonElement> entry : json.entrySet())
map.put(entry.getKey(), context.deserialize(entry.getValue(), Object.class));
return map;
}
}
handlePrimitive
또 double double또또또 integer만만만만만만만만만만만만만만만만만만만만만만만만만만만만.기본값으로 Big Decimals를 사용할 수 있다면 더 낫거나 최소한 단순화할 수 있습니다.
이 어댑터는 다음과 같이 등록할 수 있습니다.
GsonBuilder gsonBuilder = new GsonBuilder();
gsonBuilder.registerTypeAdapter(Object.class, new NaturalDeserializer());
Gson gson = gsonBuilder.create();
그리고 이렇게 부르세요.
Object natural = gson.fromJson(source, Object.class);
대부분의 다른 반구조화 시리얼라이제이션라이브러리에 있기 때문에 이것이 gson의 디폴트 동작이 아닌 이유는 잘 모르겠습니다.
Google의 Gson 2.7(아마도 이전 버전이지만 현재 버전 2.7로 테스트했습니다)에서는 다음과 같이 간단합니다.
Gson gson = new Gson();
Map map = gson.fromJson(jsonString, Map.class);
'A'가 됩니다.Map
입입 of com.google.gson.internal.LinkedTreeMap
네스트된 객체, 어레이 등에서 재귀적으로 동작합니다.
다음과 같이 OP 예를 실행했습니다(단순히 이중 따옴표로 대체하고 공백을 삭제).
String jsonString = "{'header': {'alerts': [{'AlertID': '2', 'TSExpires': null, 'Target': '1', 'Text': 'woot', 'Type': '1'}, {'AlertID': '3', 'TSExpires': null, 'Target': '1', 'Text': 'woot', 'Type': '1'}], 'session': '0bc8d0835f93ac3ebbf11560b2c5be9a'}, 'result': '4be26bc400d3c'}";
Map map = gson.fromJson(jsonString, Map.class);
System.out.println(map.getClass().toString());
System.out.println(map);
그리고 다음과 같은 결과를 얻었습니다.
class com.google.gson.internal.LinkedTreeMap
{header={alerts=[{AlertID=2, TSExpires=null, Target=1, Text=woot, Type=1}, {AlertID=3, TSExpires=null, Target=1, Text=woot, Type=1}], session=0bc8d0835f93ac3ebbf11560b2c5be9a}, result=4be26bc400d3c}
lib : Gson lib 업데이트:
할 수 Json을 "" Map"으로 하려고 할 하십시오.Map<String, Object>
라고 입력합니다.하려면 , 「는 「알겠습니다」라고 .LinkedTreeMap
예를 들면 과 같습니다.음음:
String nestedJSON = "{\"id\":\"1\",\"message\":\"web_didload\",\"content\":{\"success\":1}}";
Gson gson = new Gson();
LinkedTreeMap result = gson.fromJson(nestedJSON , LinkedTreeMap.class);
저도 똑같은 질문을 받고 여기까지 왔습니다.저는 훨씬 단순해 보이는 다른 접근 방식을 가지고 있었습니다(아마도 새로운 버전의 gson?).
Gson gson = new Gson();
Map jsonObject = (Map) gson.fromJson(data, Object.class);
다음 json과 함께
{
"map-00": {
"array-00": [
"entry-00",
"entry-01"
],
"value": "entry-02"
}
}
이하와 같다
Map map00 = (Map) jsonObject.get("map-00");
List array00 = (List) map00.get("array-00");
String value = (String) map00.get("value");
for (int i = 0; i < array00.size(); i++) {
System.out.println("map-00.array-00[" + i + "]= " + array00.get(i));
}
System.out.println("map-00.value = " + value);
출력
map-00.array-00[0]= entry-00
map-00.array-00[1]= entry-01
map-00.value = entry-02
jsonObject를 탐색할 때 instance of를 사용하여 동적으로 확인할 수 있습니다.뭐랄까
Map json = gson.fromJson(data, Object.class);
if(json.get("field") instanceof Map) {
Map field = (Map)json.get("field");
} else if (json.get("field") instanceof List) {
List field = (List)json.get("field");
} ...
저는 효과가 있기 때문에, 당신에게 효과가 있을 것입니다;-)
아래는 gson 2.8.0 이후 지원되고 있습니다.
public static Type getMapType(Class keyType, Class valueType){
return TypeToken.getParameterized(HashMap.class, keyType, valueType).getType();
}
public static <K,V> HashMap<K,V> fromMap(String json, Class<K> keyType, Class<V> valueType){
return gson.fromJson(json, getMapType(keyType,valueType));
}
이거 먹어봐, 효과가 있을 거야.해시테이블에 썼어
public static Hashtable<Integer, KioskStatusResource> parseModifued(String json) {
JsonObject object = (JsonObject) new com.google.gson.JsonParser().parse(json);
Set<Map.Entry<String, JsonElement>> set = object.entrySet();
Iterator<Map.Entry<String, JsonElement>> iterator = set.iterator();
Hashtable<Integer, KioskStatusResource> map = new Hashtable<Integer, KioskStatusResource>();
while (iterator.hasNext()) {
Map.Entry<String, JsonElement> entry = iterator.next();
Integer key = Integer.parseInt(entry.getKey());
KioskStatusResource value = new Gson().fromJson(entry.getValue(), KioskStatusResource.class);
if (value != null) {
map.put(key, value);
}
}
return map;
}
KioskStatusResource를 클래스로, Integer를 키 클래스로 바꿉니다.
사용하고 있는 것은 다음과 같습니다.
public static HashMap<String, Object> parse(String json) {
JsonObject object = (JsonObject) parser.parse(json);
Set<Map.Entry<String, JsonElement>> set = object.entrySet();
Iterator<Map.Entry<String, JsonElement>> iterator = set.iterator();
HashMap<String, Object> map = new HashMap<String, Object>();
while (iterator.hasNext()) {
Map.Entry<String, JsonElement> entry = iterator.next();
String key = entry.getKey();
JsonElement value = entry.getValue();
if (!value.isJsonPrimitive()) {
map.put(key, parse(value.toString()));
} else {
map.put(key, value.getAsString());
}
}
return map;
}
여기 그것을 할 수 있는 원라이너가 있습니다.
HashMap<String, Object> myMap =
gson.fromJson(yourJson, new TypeToken<HashMap<String, Object>>(){}.getType());
Custom JsonDeSerializer에서도 비슷한 문제를 해결했습니다.나는 그것을 좀 일반적이게 하려고 노력했지만 여전히 충분하지 않다.그것은 내 요구에 맞는 해결책이다.
우선 맵 오브젝트용으로 새로운 JsonDeserializer를 구현해야 합니다.
public class MapDeserializer<T, U> implements JsonDeserializer<Map<T, U>>
역직렬화 방법은 다음과 같습니다.
public Map<T, U> deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context)
throws JsonParseException {
if (!json.isJsonObject()) {
return null;
}
JsonObject jsonObject = json.getAsJsonObject();
Set<Entry<String, JsonElement>> jsonEntrySet = jsonObject.entrySet();
Map<T, U> deserializedMap = new HashMap<T, U>();
for (Entry<java.lang.String, JsonElement> entry : jsonEntrySet) {
try {
U value = context.deserialize(entry.getValue(), getMyType());
deserializedMap.put((T) entry.getKey(), value);
} catch (Exception ex) {
logger.info("Could not deserialize map.", ex);
}
}
return deserializedMap;
}
이 솔루션의 단점은 맵의 키가 항상 "String" 유형이라는 것입니다.그러나 몇 가지 사항을 변경함으로써 이를 일반화할 수 있습니다.또한 값의 클래스는 컨스트럭터로 전달되어야 합니다.그래서 방법은getMyType()
my code는 생성자에 전달된 Map 값의 유형을 반환합니다.
이 투고를 참조할 수 있습니다.Gson용 커스텀 JSON 디시리얼라이저를 작성하려면 어떻게 해야 합니까?커스텀 디시리얼라이저에 대해 자세히 알아보려면 , 를 참조해 주세요.
대신 이 클래스를 사용할 수 있습니다:). (짝수 목록, 중첩 목록 및 json을 처리합니다.)
public class Utility {
public static Map<String, Object> jsonToMap(Object json) throws JSONException {
if(json instanceof JSONObject)
return _jsonToMap_((JSONObject)json) ;
else if (json instanceof String)
{
JSONObject jsonObject = new JSONObject((String)json) ;
return _jsonToMap_(jsonObject) ;
}
return null ;
}
private static Map<String, Object> _jsonToMap_(JSONObject json) throws JSONException {
Map<String, Object> retMap = new HashMap<String, Object>();
if(json != JSONObject.NULL) {
retMap = toMap(json);
}
return retMap;
}
private static Map<String, Object> toMap(JSONObject object) throws JSONException {
Map<String, Object> map = new HashMap<String, Object>();
Iterator<String> keysItr = object.keys();
while(keysItr.hasNext()) {
String key = keysItr.next();
Object value = object.get(key);
if(value instanceof JSONArray) {
value = toList((JSONArray) value);
}
else if(value instanceof JSONObject) {
value = toMap((JSONObject) value);
}
map.put(key, value);
}
return map;
}
public static List<Object> toList(JSONArray array) throws JSONException {
List<Object> list = new ArrayList<Object>();
for(int i = 0; i < array.length(); i++) {
Object value = array.get(i);
if(value instanceof JSONArray) {
value = toList((JSONArray) value);
}
else if(value instanceof JSONObject) {
value = toMap((JSONObject) value);
}
list.add(value);
}
return list;
}
}
JSON 문자열을 해시맵으로 변환하려면 다음 명령을 사용합니다.
HashMap<String, Object> hashMap = new HashMap<>(Utility.jsonToMap(response)) ;
이것은 완전한 답변이라기보다 케빈 돌란의 답변의 부록에 가깝지만, 저는 Number에서 활자를 추출하는 데 어려움을 겪고 있었습니다.제 솔루션은 다음과 같습니다.
private Object handlePrimitive(JsonPrimitive json) {
if(json.isBoolean()) {
return json.getAsBoolean();
} else if(json.isString())
return json.getAsString();
}
Number num = element.getAsNumber();
if(num instanceof Integer){
map.put(fieldName, num.intValue());
} else if(num instanceof Long){
map.put(fieldName, num.longValue());
} else if(num instanceof Float){
map.put(fieldName, num.floatValue());
} else { // Double
map.put(fieldName, num.doubleValue());
}
}
HashMap<String, String> jsonToMap(String JsonDetectionString) throws JSONException {
HashMap<String, String> map = new HashMap<String, String>();
Gson gson = new Gson();
map = (HashMap<String, String>) gson.fromJson(JsonDetectionString, map.getClass());
return map;
}
JSONObject는 일반적으로HashMap
데이터를 저장할 수 있습니다.따라서 코드에서 Map으로 사용할 수 있습니다.
예,
JSONObject obj = JSONObject.fromObject(strRepresentation);
Iterator i = obj.entrySet().iterator();
while (i.hasNext()) {
Map.Entry e = (Map.Entry)i.next();
System.out.println("Key: " + e.getKey());
System.out.println("Value: " + e.getValue());
}
이 코드를 사용했습니다.
Gson gson = new Gson();
HashMap<String, Object> fields = gson.fromJson(json, HashMap.class);
언급URL : https://stackoverflow.com/questions/2779251/how-can-i-convert-json-to-a-hashmap-using-gson
'source' 카테고리의 다른 글
java.sql에서 열 이름을 검색합니다.결과 세트 (0) | 2022.09.04 |
---|---|
Java 객체(빈)를 키와 값의 쌍으로 변환하는 방법(또는 그 반대) (0) | 2022.09.04 |
Mysql 만들기 삽입 절차 문이 불완전합니다. (0) | 2022.09.04 |
python 쉘이 32비트인지 64비트인지 확인하려면 어떻게 해야 하나요? (0) | 2022.09.04 |
Python에서 날짜 범위 만들기 (0) | 2022.09.04 |