2013-07-22 4 views
2

List을 모두 수정 불가능한 컬렉션으로 직렬화하고자합니다.gson을 사용하여 수정 불가능한 컬렉션에 비 직렬화

public class MyClass 
{ 
    public final mylist = Collections.unmodifiablelist(new ArrayList()); 
} 

내가 역 직렬화하는 방법 : 내가 만들 필요하지 않으

MyClass inst = (new Gson()).fromJson("{mylist:[\"firstString\"]}", MyClass.class); 

모든 100 개 클래스에 대한 유형의 어댑터를 등록 여기

내가 직렬화 복원하고 내 클래스 List을 사용하므로 Gson의 해당 인스턴스에 대해 deserializable을 List으로 전역 적으로 재정의하는 방법이 있습니까?

+0

필드 'mylist'의 유형은 어디에 있습니까? – PomPom

답변

0

나도 어댑터 공장으로 이동,, 짧은 코드합니다 :

class MyAdapter implements TypeAdapterFactory { 

    @Override 
    public <T> TypeAdapter<T> create(final Gson gson, final TypeToken<T> tokenType) { 
    final TypeAdapter<T> delegate = gson.getDelegateAdapter(this, tokenType); 

    return new TypeAdapter<T>() { 
     @Override 
     public void write(JsonWriter out, T value) throws IOException { 
     delegate.write(out, value); 
     } 

     @Override 
     public T read(JsonReader arg0) throws IOException { 
     T t = delegate.read(arg0); 
     if (List.class.isAssignableFrom(tokenType.getRawType())) { 
      List<?> list = (List<?>) t; 

      return (T) Collections.unmodifiableList(list); 
     } 

     return t; 
     } 
    }; 
    } 
} 

그런 다음 평소와 같이 r 그것을 기입하십시오 :

Gson g = new GsonBuilder().registerTypeAdapterFactory(new MyAdapter()).create(); 
1

JavaBean 표준을 따르고 수정할 수없는 목록을 반환하는 이유는 무엇입니까?

Gson의 새 버전
public class MyClass { 
    private List<String> myList = new ArrayList<String>(); 

    public void setMyList(List<String> list) { 
     this.myList = list; 
    } 

    public Collection<String> getMyList() { 
     return Collections.unmodifiablelist(this.myList); 
    } 
} 
+0

...'myList' 인스턴스가 내부적으로 사용되기 때문에 ... 나는 수정할 수 없게하는 것이 정당한 이유를 선호합니다. 당신은 수정할 수 없습니다 당신의 자신의 클래스를 신뢰할 수없는 경우 – Cheetah

+0

는 이럴, 당신은 더 큰 문제 – epoch

+0

이 ... 그것은 신뢰의 일이 아니다 ... 추론 사람이 나중에 내 수업을 편집 와야 대해 대한 자세한 .. .. 수정할 수 없다면 개발자가 멈추고 왜 완료되었는지 생각할 것입니다 ... – Cheetah

0

사용자 정의 TypeAdapterFactoryList 속성을 만들 수 있습니다. 내가 간단한 구현했습니다 UnmodifiableListTypeAdapter하지만 그게 다 괜찮은지 잘 모르겠습니다. 설명서를 올바르게 구현하는 방법을 읽어보십시오. 그런

class ListTypeAdapterFactory implements TypeAdapterFactory { 

    @SuppressWarnings({ "rawtypes", "unchecked" }) 
    @Override 
    public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> typeToken) { 
     Type type = typeToken.getType(); 
     if (typeToken.getRawType() != List.class || !(type instanceof ParameterizedType)) { 
      return null; 
     } 

     Type elementType = ((ParameterizedType) type).getActualTypeArguments()[0]; 
     TypeAdapter<?> elementAdapter = gson.getAdapter(TypeToken.get(elementType)); 

     return new UnmodifiableListTypeAdapter(elementAdapter); 
    } 
} 

class UnmodifiableListTypeAdapter<E> extends TypeAdapter<List<E>> { 

    private TypeAdapter<E> elementAdapter; 

    public UnmodifiableListTypeAdapter(TypeAdapter<E> elementAdapter) { 
     this.elementAdapter = elementAdapter; 
    } 

    @Override 
    public List<E> read(JsonReader reader) throws IOException { 
     if (reader.peek() == JsonToken.NULL) { 
      reader.nextNull(); 
      return null; 
     } 

     List<E> list = new ArrayList<E>(); 
     reader.beginArray(); 
     while (reader.hasNext()) { 
      E element = elementAdapter.read(reader); 
      list.add(element); 
     } 
     reader.endArray(); 

     return Collections.unmodifiableList(list); 
    } 

    @Override 
    public void write(JsonWriter writer, List<E> list) throws IOException { 
     if (list == null) { 
      writer.nullValue(); 
      return; 
     } 

     writer.beginArray(); 
     for (E item : list) { 
      elementAdapter.write(writer, item); 
     } 
     writer.endArray(); 
    } 
} 

사용 예제 수 외모 : 프로그램의 인쇄 위

public class GsonProgram { 

    public static void main(String[] args) throws Exception { 
     GsonBuilder gsonBuilder = new GsonBuilder(); 
     gsonBuilder.registerTypeAdapterFactory(new ListTypeAdapterFactory()); 
     Gson gson = gsonBuilder.create(); 

     System.out.println(gson.fromJson("{strings:[\"firstString\"],integers:[23,34,56]}", 
       Entity.class)); 
    } 
} 

class Entity { 

    private List<String> strings; 
    private List<Integer> integers; 

    public List<String> getStrings() { 
     return strings; 
    } 

    public void setStrings(List<String> strings) { 
     this.strings = strings; 
    } 

    public List<Integer> getIntegers() { 
     return integers; 
    } 

    public void setIntegers(List<Integer> integers) { 
     this.integers = integers; 
    } 

    @Override 
    public String toString() { 
     return "Entity [strings=" + strings + ", integers=" + integers + "]"; 
    } 
} 

:

Entity [strings=[firstString], integers=[23, 34, 56]] 
관련 문제