Gson解析json
GSON:谷歌的一款开源项目,主要用于解析json数据,有很多很友好的个性化设置
思想:把json字符串与java对象相关联
序列化:把java对象转换成json字符串
反序列化:把json字符串转换成java对象
使用springMVC获取web前端传送过来的数据
Gson处理简单数据(key对应的value是简单的String类型/或者number)
Gson的使用前提:导入jar包 gson-2.2.4.jar
主要的方法:
Gson fromJson(String jsonStr,Type) //用于把json字符串转换成type类型的java对象
String toJson(Object obj) //把obj对象变成json字符串
例如:
前端传送如下json字符串:
{
"username":"kylin",
"password":"123456"
}
//那么controller中就可以有如下的操作(User类的内容就不导入)
@RequestMapping(value = "/LOGIN",method = RequestMethod.POST) public String LOGIN(@RequestBody String jsonStr){ //使用gson来获取数据并且进行操作 Gson gson=new Gson(); //序列化 User user=gson.fromJson(jsonStr,User.class); String username=user.getUsername(); String password=user.getPassword(); System.out.println(username+" "+password); return "welcome"; }
Gson处理复杂数据(key对应的value可能是数组/对象)
处理方式:
如果是对象的话,那么对应的javabean类,需要设置一个公有的内部类对象,如果是数组的话,那么对应的javabean类中可以把对应的字段设置为list集合/set集合
例如:
前端传送数据如下:
{ "name":"kylin", "age":20, "major":["English","Chinese","math"], "grade":{ "course":"computer", "score":"100", "level":"good" } }
对应的Student类:
Student.java
package com.kylin.JavaBean;
import java.util.List;
public class Student {
private String name; //名字
private int age; //年纪
private List<String> major; //主修课程
private Grade grade; //某科目
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public List<String> getMajor() {
return major;
}
public void setMajor(List<String> major) {
this.major = major;
}
public Grade getGrade() {
return grade;
}
public void setGrade(Grade grade) {
this.grade = grade;
}
//注意:内部类应该被设置为public
public class Grade {
private String course;
private String score;
private String level;
public String getCourse() {
return course;
}
public void setCourse(String course) {
this.course = course;
}
public String getScore() {
return score;
}
public void setScore(String score) {
this.score = score;
}
public String getLevel() {
return level;
}
public void setLevel(String level) {
this.level = level;
}
}
}
Controller中请求处理方法:
@RequestMapping(value = "/Student",method = RequestMethod.POST) public String Student_Login(@RequestBody String jsonStr){ //jsonstr获取数据 /* { "name":"kylin", "age":20, "major":["English","Chinese","math"], "grade":{ "course":"computer", "score":"100", "level":"good" } } * */ //因为本地已经有想匹配的javabean对象,所有直接当成简单的数据获取就 Gson gson=new Gson(); Student student=gson.fromJson(jsonStr,Student.class); //成功获取数组里面的内容 List<String> major=student.getMajor(); for (String i:major){ System.out.println(i); } //接下来就是解析内部类中的内容 /* Outter outter = new Outter(); Outter.Inner inner = outter.new Inner(); //必须通过Outter对象来创建*/ //成功获取grade对象 Student.Grade grade=student.new Grade(); grade=student.getGrade(); String gradeCourse=grade.getCourse(); String gradeLevel=grade.getLevel(); String gradeScore=grade.getScore(); System.out.println("内部的东西"+gradeScore+gradeCourse+gradeLevel); return "welcome"; //welcome是一个jsp文件,配置了视图解析器的,不需要过多的纠结 }
以上是从web前端获取json数据----简单数据,复杂数据(含有数组/对象)的处理方式;下面将介绍如何从web后端传送符合规范的json字符串给前端。
后端返回简单数据给前端------过于简单这里就不介绍了,主要介绍后端返回复杂json数据给前端的方法
后端返回复杂json字符串给前端
方式:使用javabean/使用map集合
使用javabean方式
@RequestMapping(value = "/DataBackByJavaBean",method = RequestMethod.POST)
@ResponseBody
public String DataBack(@RequestParam String id){
//本来是需要获取前端传过来的id,然后进行数据库查询 然后再返回结果 这里就随便的进行一次获取吧
System.out.println("前端传过来的id:"+id);
//设置需要传送的数据
Student student=new Student();
student.setName("kylin");
student.setAge(11);
List<String> major=new ArrayList<>();
major.add("Chinese");
major.add("Math");
student.setMajor(major);
Student.Grade grade=student.new Grade();
grade.setCourse("XXX");
grade.setScore("111");
grade.setLevel("good");
student.setGrade(grade);
//数据设置完毕 进行gson操作-----变成json字符串
//使用GsonBuilder创建的gson对象会更加的强大,可以有更多的个性化操作
GsonBuilder gsonBuilder=new GsonBuilder();
Gson gson=gsonBuilder.create();
String jsonStr=gson.toJson(student);
System.out.println(jsonStr);
return jsonStr;
}
使用map集合方式(优点:对于需要返回的数据可以任意设置,不用局限于只能使用javabean的属性)
@RequestMapping(value = "/DataBackByMap",method = RequestMethod.POST)
@ResponseBody
public String DataBackByMap(@RequestParam String id){
System.out.println(id);
//使用map方式来处理
Map<String,Object>params=new HashMap<>();
params.put("status","200");
params.put("name","kylin");
List<String> major=new LinkedList<>();
major.add("XXX");
major.add("YYY");
params.put("major",major);
Student student=new Student();
Student.Grade grade=student.new Grade();
grade.setLevel("GOOD");
grade.setScore("1111");
grade.setCourse("xxxxxxssss");
params.put("grade",grade);
//转换成jsonStr字符串
GsonBuilder gsonBuilder = new GsonBuilder();
gsonBuilder.setFieldNamingStrategy(new FieldNamingStrategy() {
@Override
public String translateName(Field field) {
if (field.getName().equals("name")){
return "NAME";
}
return field.getName();
}
});
Gson gson = gsonBuilder.create();
gson.toJson()
String jsonStr=gson.toJson(params);
System.out.println(params);
return jsonStr;
}
以上主要介绍了如何从web前端获取json数据并且如何从web后端传送数据给web前端(如果对@RequestBody和@ResponseBody不理解的朋友,可以自行百度)
下面主要扩展性的讲解一下Gson的一些其他特性:
1.修改javaBean中的属性在json转换中的名字
有两种方式,分别是:
1.@SerializedName 注解的使用(在定义javaBean类的时候,对属性进行注解)
2.GsonBuilder的 setFieldNamingStrategy 方法 ,FieldNamingStrategy 自定义规则
比如需要的数据是:
{
"id":"123",
"name":"kylin",
"author":{
"id":"222",
"name":"kkkk"
}
}
而实际类对应的数据是:
{
"id":"123",
"name":"kylin",
"user":{
"id":"222",
"name":"kkkk"
}
}
方式一:
在对应的javaBean类中;在user属性上添加注解@SerializedName
@SerializedName("author")
private User user;
例如:
@SerializedName(value = "user_password", alternate = {"userName", "username"})//value是默认字段名称、alternate是备选字段名称 private String userPassword;
缺点:这种方式会使得以后所有涉及到该属性的json在转换的过程中,user都会变成author;而且其权限相对较大,会覆盖其他的对该属性的操作,比如我在另外一个地方使用方式2来
对属性的名字进行修改,但最终还是会被其@SerializedName覆盖
方式二:(推荐)
GsonBuilder的 setFieldNamingStrategy 方法 ,FieldNamingStrategy 自定义规则
GsonBuilder gsonBuilder = new GsonBuilder();
gsonBuilder.setFieldNamingStrategy(new FieldNamingStrategy() {
@Override
public String translateName(Field field) {
if (field.getName().equals("name")){
//相当于遍历一遍,如果找到名字为name的就把他变成NAME
return "NAME"
}
return field.getName();
}
});
Gson gson = gsonBuilder.create();
FieldNamingStrategy中还有很多其他的规则,如果有兴趣可以自己去了解一下~
下面贴一些GsonBuilder中比较常见的方法和注解
//序列化null serializeNulls() // 设置日期时间格式,另有2个重载方法 // 在序列化和反序化时均生效 setDateFormat("yyyy-MM-dd") // 禁此序列化内部类 disableInnerClassSerialization() //生成不可执行的Json(多了 )]}' 这4个字符) generateNonExecutableJson() //禁止转义html标签 disableHtmlEscaping() //格式化输出 setPrettyPrinting() create()
@Expose(serialize=true,deserialize=false)
private String name;//序列化是忽略,反序列化时参与。