programing

JSON을 기존 개체로 역직렬화(Java)

javamemo 2023. 3. 1. 08:47
반응형

JSON을 기존 개체로 역직렬화(Java)

Jackson JSON 라이브러리가 JSON을 기존 객체로 역직렬화하도록 하는 방법을 알고 싶습니다.이 방법을 찾으려고 노력했지만 수업을 듣고 인스턴스화만 할 수 있는 것 같습니다.

또는 가능하지 않다면 Java JSON 역직렬화 라이브러리가 가능한지 알고 싶습니다.

이것은 C#: JSON 문자열에서 기존 객체인스턴스로 데이터를 오버레이 하는 경우의 대응 질문인 것 같습니다.JSON 같아요.NET에는 Populate Object(string, object)가 있습니다.

잭슨을 사용하여 이 작업을 수행할 수 있습니다.

mapper.readerForUpdating(object).readValue(json);

Jackson을 사용하여 두 JSON 문서 병합을 참조하십시오.

잭슨 대신 다른 도서관을 사용할 수 있다면 Genson http://owlike.github.io/genson/에 접속할 수 있습니다.기타 뛰어난 기능(주석 없이 비어 있지 않은 컨스트럭터를 사용하여 역직렬화, 폴리모픽 타입으로 역직렬화 등) 외에 JavaBean을 기존 인스턴스로 역직렬화 할 수 있습니다.다음은 예를 제시하겠습니다.

BeanDescriptorProvider provider = new Genson().getBeanDescriptorFactory();
BeanDescriptor<MyClass> descriptor = provider.provide(MyClass.class, genson);
ObjectReader reader = new JsonReader(jsonString);
MyClass existingObject = descriptor.deserialize(existingObject, reader, new Context(genson));

질문이 있으시면 주저하지 마시고 메일링 리스트 http://groups.google.com/group/genson을 이용하세요.

스프링 프레임워크를 사용하는 경우 이 작업에 BeanUtils 라이브러리를 사용할 수 있습니다.먼저 json String을 정상적으로 역직렬화한 다음 BeanUtils를 사용하여 이 개체를 상위 개체 내에 설정하십시오.또한 개체의 변수 이름이 상위 개체 내에 설정될 것으로 예상합니다.코드 스니펫은 다음과 같습니다.

childObject = gson.fromJson("your json string",class.forName(argType))
BeanUtils.setProperty(mainObject, "childObjectName", childObject);

하나의 솔루션은 새로운 오브젝트 그래프/트리를 해석한 후 기존 오브젝트 그래프/트리에 통합 복사하는 것입니다.그러나 이는 물론 효율이 떨어지고 작업량이 늘어납니다. 특히 유형 정보의 가용성이 낮아 구체적인 유형이 다를 경우 더욱 그렇습니다.(그래서 정답은 아닙니다.다른 사람이 이런 식으로 대답하지 않도록 더 좋은 답변이 있기를 바랍니다.)

flexJson도 같은 작업을 수행할 수 있습니다.

다음은 FlexJson Doc에서 복사한 예입니다.

역직렬화Into 함수는 문자열과 기존 개체를 참조합니다.

 Person charlie = new Person("Charlie", "Hubbard", cal.getTime(), home, work );
 Person charlieClone = new Person( "Chauncy", "Beauregard", null, null, null );
 Phone fakePhone = new Phone( PhoneNumberType.MOBILE, "303 555 1234");
 charlieClone.getPhones().add( fakePhone ); 
 String json = new JSONSerializer().include("hobbies").exclude("firstname", "lastname").serialize( charlie ); 
 Person p = new JSONDeserializer<Person>().deserializeInto(json, charlieClone);

p에서 반환되는 참조는 업데이트된 값만 있는 charlieClone과 동일합니다.

Jackson + Spring의 Data Binder를 사용하여 이와 같은 작업을 수행했습니다.이 코드는 어레이를 처리하지만 중첩된 개체는 처리하지 않습니다.

private void bindJSONToObject(Object obj, String json) throws IOException, JsonProcessingException {
    MutablePropertyValues mpv = new MutablePropertyValues();
    JsonNode rootNode = new ObjectMapper().readTree(json);
    for (Iterator<Entry<String, JsonNode>> iter = rootNode.getFields(); iter.hasNext(); ) {
        Entry<String, JsonNode> entry = iter.next();
        String name = entry.getKey();
        JsonNode node = entry.getValue();
        if (node.isArray()) {
            List<String> values = new ArrayList<String>();
            for (JsonNode elem : node) {
                values.add(elem.getTextValue());
            }
            mpv.addPropertyValue(name, values);
            if (logger.isDebugEnabled()) {
                logger.debug(name + "=" + ArrayUtils.toString(values));
            }
        }
        else {
            mpv.addPropertyValue(name, node.getTextValue());
            if (logger.isDebugEnabled()) {
                logger.debug(name + "=" + node.getTextValue());
            }
        } 
    }
    DataBinder dataBinder = new DataBinder(obj);
    dataBinder.bind(mpv);
}

는 항상 더미 객체에 로드하여 반사를 사용하여 데이터를 전송할 수 있습니다.gson만 사용하기로 마음먹었다면

예: 이 코드가 데이터를 복사하려는 개체에 있다고 가정합니다.

    public void loadObject(){
Gson gson = new Gson();
//make temp object
YourObject tempStorage = (YourObject) gson.fromJson(new FileReader(theJsonFile), YourObject.class);
//get the fields for that class
ArrayList<Field> tempFields = new ArrayList<Field>();
ArrayList<Field> ourFields = new ArrayList<Field>();
getAllFields(tempFields, tempStorage.getClass());
getAllFields(thisObjectsFields, this.getClass());
for(Field f1 : tempFields){
    for(Field f2 : thisObjectsFields){
        //find matching fields
        if(f1.getName().equals(f2.getName()) && f1.getType().equals(f2.getType())){
            //transient and statics dont get serialized and deserialized.
            if(!Modifier.isTransient(f1.getModifiers())&&!Modifier.isStatic(f1.getModifiers())){
                //make sure its a loadable thing
                f2.set(this, f1.get(tempStorage));
            }
        }
    }
}

}

public static List<Field> getAllFields(List<Field> fields, Class<?> type) {
    for (Field field : type.getDeclaredFields()) {
        fields.add(field);
    }
    if (type.getSuperclass() != null) {
        fields = getAllFields(fields, type.getSuperclass());
    }
    return fields;
}

언급URL : https://stackoverflow.com/questions/12518618/deserialize-json-into-existing-object-java

반응형