[Android 知识点] Gson的使用

Gson的目的:

  • 提供 toJson() and fromJson() 方法为Java实体与JSON之间相互转换

Gson的使用

Gradle:

compile 'com.google.code.gson:gson:2.6.1'

进行序列化:toJson()

进行反序列化:fromJson()

最基础的转换:

序列化
Gson gson = new Gson();
String jsonNumber = gson.toJson(100);       // 100
String jsonBoolean = gson.toJson(false);    // false
String jsonString = gson.toJson("String"); //"String"
反序列化
Gson gson = new Gson();
int i = gson.fromJson("100", int.class);              //100
double d = gson.fromJson("\"99.99\"", double.class);  //99.99
boolean b = gson.fromJson("true", boolean.class);     // true
String str = gson.fromJson("String", String.class);   // String

POJO类的转换

public class User {
    public String name;
    public int age;
    public String emailAddress;
}

生成JSON:

Gson gson = new Gson();
User user = new User("小明",24);
String jsonObject = gson.toJson(user); 

输出: {"name":"小明","age":24}

解析JSON:

Gson gson = new Gson();
String jsonString = "{\"name\":\"小明\",\"age\":24}";
User user = gson.fromJson(jsonString, User.class);

嵌套类(内部类)

public class A { 
  public String a; 

  class B { 

    public String b; 

    public B() {
      // No args constructor for B
    }
  } 
}

Gson转换嵌套类跟之前的方法一样,但要注意的是,Gson可以序列化构造函数参数为空的类,但不能反序列号。

Array数组

Gson gson = new Gson();
int[] ints = {1, 2, 3, 4, 5};
String[] strings = {"abc", "def", "ghi"};

// 序列化
gson.toJson(ints);     
输出:[1,2,3,4,5]

gson.toJson(strings);  
输出:["abc", "def", "ghi"]

// 反序列化
int[] ints2 = gson.fromJson("[1,2,3,4,5]", int[].class); 

Collections

Gson gson = new Gson();
Collection<Integer> ints = Lists.immutableList(1,2,3,4,5);

// 序列化
String json = gson.toJson(ints);  // ==> json is [1,2,3,4,5]

// 反序列化
Type collectionType = new TypeToken<Collection<Integer>>(){}.getType();
Collection<Integer> ints2 = gson.fromJson(json, collectionType);
// ==> ints2 is same as ints

泛型

class Foo<T> {
  T value;
}
Gson gson = new Gson();
Foo<Bar> foo = new Foo<Bar>();
gson.toJson(foo); // May not serialize foo.value correctly

gson.fromJson(json, foo.getClass()); 

但这样反序列化成Bar类型是失败的,你可以用下面的方法

Type fooType = new TypeToken<Foo<Bar>>() {}.getType();
gson.toJson(foo, fooType);
gson.fromJson(json, fooType);

混合类型的Collection

有时候会遇到混合类型,如:

['hello',5,{name:'GREETINGS',source:'guest'}]

对应的Collection :

Collection collection = new ArrayList();
collection.add("hello");
collection.add(5);
collection.add(new Event("GREETINGS", "guest"));

Event类:

class Event {
  private String name;
  private String source;
  private Event(String name, String source) {
    this.name = name;
    this.source = source;
  }
}

你可以用toJson(collection)就可以完成序列化工作。

可是,用fromJson(json, Collection.class)进行反序列话是不行的。

这时候,你有三种选择:

  1. 用Gson的解析API(底层流解析,或者DOM解析),去解析数组元素,然后用Gson.fromJson()解析每一个数组成员,这是推荐的方法,这里有一个例子
Gson gson = new Gson();
Collection collection = new ArrayList();
collection.add("hello");
collection.add(5);
collection.add(new Event("GREETINGS", "guest"));
String json = gson.toJson(collection);
System.out.println("Using Gson.toJson() on a raw collection: " + json);


JsonParser parser = new JsonParser();
JsonArray array = parser.parse(json).getAsJsonArray();
String message = gson.fromJson(array.get(0), String.class);
int number = gson.fromJson(array.get(1), int.class);
Event event = gson.fromJson(array.get(2), Event.class);
System.out.printf("Using Gson.fromJson() to get: %s, %d, %s", message, number, event);
  1. 官方不推荐就不介绍了
  2. 官方不推荐就不介绍了

美化Json输出打印格式

Gson gson = new GsonBuilder().setPrettyPrinting().create();
String jsonOutput = gson.toJson(someObject);

输出打印效果会相当漂亮:

{
  "analysis": "a",
  "conclusion": "is pig"
}

输出Null类型数据

Gson gson = new GsonBuilder().serializeNulls().create();

例如:

public class Foo {
  private final String s;
  private final int i;

  public Foo() {
    this(null, 5);
  }

  public Foo(String s, int i) {
    this.s = s;
    this.i = i;
  }
}

Gson gson = new GsonBuilder().serializeNulls().create();
Foo foo = new Foo();
String json = gson.toJson(foo);
System.out.println(json);

json = gson.toJson(null);
System.out.println(json);

输出结果:
{"s":null,"i":5}
null

版本化管理

提供了 @Since 和 @Until 注解方式

public class SoccerPlayer {

  private String name;

  @Since(1.2)
  private int shirtNumber;

  @Until(0.9)
  private String country;

  private String teamName;

  // Methods removed for brevity
}

下面是一个例子:

public class VersionedClass {
  @Since(1.1) private final String newerField;
  @Since(1.0) private final String newField;
  private final String field;

  public VersionedClass() {
    this.newerField = "newer";
    this.newField = "new";
    this.field = "old";
  }
}

VersionedClass versionedObject = new VersionedClass();
Gson gson = new GsonBuilder().setVersion(1.0).create();
String jsonOutput = gson.toJson(someObject);
System.out.println(jsonOutput);
System.out.println();

gson = new Gson();
jsonOutput = gson.toJson(someObject);
System.out.println(jsonOutput);

这里就包含了1.1和1.0两个版本,可以通过 @Since 注解去控制版本。

排除部分成员

使用 transient 或者 static 修饰变量

假如你要包含修饰过的成员,你可以这样做:

import java.lang.reflect.Modifier;
Gson gson = new GsonBuilder()
    .excludeFieldsWithModifiers(Modifier.STATIC)
    .create();
Gson gson = new GsonBuilder()
    .excludeFieldsWithModifiers(Modifier.STATIC, Modifier.TRANSIENT, Modifier.VOLATILE)
    .create();

或者使用@Expose注解,该注解会序列化含有该注解的成员,而没有注解的会排除在外,需进行下面的操作

new GsonBuilder().excludeFieldsWithoutExposeAnnotation().create()

@Expose注解含有2个选项deserialize 和 serialize,默认两者都为true

public class Account {

  @Expose(deserialize = false)
  private String accountNumber;

  @Expose
  private String iban;

  @Expose(serialize = false)
  private String owner;

  @Expose(serialize = false, deserialize = false)
  private String address;

  private String pin;
}
Optionalserializedeserialize
@Expose(deserialize = false)×
@Expose
@Expose(serialize = false)×
@Expose(serialize = false, deserialize = false)××

JSON域成员命名

使用 @SerializedName(“new name”) 注解重新命名,否则按变量名命名

private class SomeObject {
  @SerializedName("custom_naming") private final String someField;
  private final String someOtherField;

  public SomeObject(String a, String b) {
    this.someField = a;
    this.someOtherField = b;
  }
}

SomeObject someObject = new SomeObject("first", "second");
Gson gson = new GsonBuilder().setFieldNamingPolicy(FieldNamingPolicy.UPPER_CAMEL_CASE).create();
String jsonRepresentation = gson.toJson(someObject);
System.out.println(jsonRepresentation);


The output is:

{"custom_naming":"first","SomeOtherField":"second"}

支持流媒体

例如:

gson.toJson("Hello", System.out);
gson.toJson(123, System.out);

Writer writer = new FileWriter("Output.json");
Gson gson = new GsonBuilder().create();
gson.toJson("Hello", writer);
gson.toJson(123, writer);

writer.close();

try(Writer writer = new OutputStreamWriter(new FileOutputStream("Output.json") , "UTF-8")){
        Gson gson = new GsonBuilder().create();
        gson.toJson("Hello", writer);
        gson.toJson(123, writer);
    }

参考的文章:

http://www.importnew.com/16630.html

http://www.javacreed.com/gson-annotations-example/

http://www.jianshu.com/p/e740196225a4

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值