最新文章专题视频专题问答1问答10问答100问答1000问答2000关键字专题1关键字专题50关键字专题500关键字专题1500TAG最新视频文章推荐1 推荐3 推荐5 推荐7 推荐9 推荐11 推荐13 推荐15 推荐17 推荐19 推荐21 推荐23 推荐25 推荐27 推荐29 推荐31 推荐33 推荐35 推荐37视频文章20视频文章30视频文章40视频文章50视频文章60 视频文章70视频文章80视频文章90视频文章100视频文章120视频文章140 视频2关键字专题关键字专题tag2tag3文章专题文章专题2文章索引1文章索引2文章索引3文章索引4文章索引5123456789101112131415文章专题3
当前位置: 首页 - 正文

使用json-lib完成json的序列化和反序列化

来源:动视网 责编:小OO 时间:2025-09-29 02:20:41
文档

使用json-lib完成json的序列化和反序列化

使用json-lib完成json的序列化和反序列化2011-07-2914:07:43分类:默认分类|标签:软件javajson.json的序列化和反序列化在现在的javaweb中特别是ajax中使用的比较频繁,现在本人就这种技术提出自己的使用心得。我的pojo对象的结构是这样的部门表和员工表1对多的关系部门对象publicclassDeptimplementsjava.io.Serializable{privateIntegerdepid;//部门IDprivateStringdepname
推荐度:
导读使用json-lib完成json的序列化和反序列化2011-07-2914:07:43分类:默认分类|标签:软件javajson.json的序列化和反序列化在现在的javaweb中特别是ajax中使用的比较频繁,现在本人就这种技术提出自己的使用心得。我的pojo对象的结构是这样的部门表和员工表1对多的关系部门对象publicclassDeptimplementsjava.io.Serializable{privateIntegerdepid;//部门IDprivateStringdepname
使用json-lib完成json的序列化和反序列化2011-07-29 14:07:43

分类: 默认分类 |  标签:软件  java  json.

json的序列化和反序列化在现在的javaweb中特别是ajax中使用的比较频繁,现在本人就这种技术提出自己的使用心得。

我的pojo对象的结构是这样的

部门表和员工表    1对多的关系

部门对象

public class Dept implements java.io.Serializable {

    private Integer depid;//部门ID

    private String depname;//部门名称

    private Set emps = new HashSet(0);//员工集合

}

员工对象

public class Emp implements java.io.Serializable {

    private Integer empid;//员工id

    private Dept dept;//部门

    private String empname;//员工名称

    private Date birthday;//生日

}

1.json字符串序列化成对象

/**

 * 通过json转换成对象

 * @author 凤生禾予

 */

public void jsonToObject(){

    Date d=new Date();

    SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd");

    StringBuffer str=new StringBuffer();

    // json字符串

    str.append("{empid:1,dept:{depid:1,depname:'开发部'},empname:'张三',birthday:'"+sdf.format(d)+"'}");

    // 使用JSONObject将json序列化对象

    JSONObject obj=JSONObject.fromObject(str.toString());

    // 将JOSNObject对象转换成pojo对象

    Emp emp=(Emp) JSONObject.toBean(obj,Emp.class);

    System.out.println(emp.getBirthday());

}

这里需要注意的是json字符串的写法以{}表示一个对象,字符串必须加引号 

2json字符串序列化成集合

/**

 * 通过json转换成集合

 * @author 凤生禾予

 */

public void jsonToArray(){

    Date d=new Date();

    SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd");

    StringBuffer str=new StringBuffer();

    //json字符串

    str.append("[");

    str.append("{empid:1,dept:{depid:1,depname:'开发部'},empname:'张三',birthday:'"+sdf.format(d)+"'}");

    str.append();

    str.append("{empid:2,dept:{depid:1,depname:'开发部'},empname:'李四',birthday:'"+sdf.format(d)+"'}");

    str.append("]");

    //将json转换成JSONArray对象

    JSONArray arr=JSONArray.fromObject(str.toString());

    //使用JSONArray转换成集合

List list=JSONArray.toList(arr,Emp.class);

    for (Emp emp : list) {

        System.out.println(emp.getEmpname());

        System.out.println(emp.getBirthday());

        System.out.println(emp.getDept().getDepname());

    }

}

这里需要注意的是json的数组用法为[]

3.对象反序列化成json

 /**

  * 通过对象转换成json

  * @author 凤生禾予

  */

public void objectToJson(){

    ClassPathXmlApplicationContext xa=new ClassPathXmlApplicationContext("applicationContext.xml");

    EmpDAO dao=(EmpDAO) xa.getBean("EmpDAO");

    //查找对象

    Emp emp=dao.findById(27);

    String s=JSONObject.fromObject(emp).toString();

    System.out.println(s);

}

这里会有2个问题

1.pojo中对象存在有死循环问题,部门类中有员工对象的集合,员工类中有部门的对象,json-lib反序列化中会进行双向转换,从而形成死循环,会报一个json-lib的经典异常:

Exception in thread "main" net.sf.json.JSONException: There is a cycle in the hierarchy!

2.日期类型转换

json-lib转换出来的日期类型格式

"birthday":{"date":1,"day":0,"hours":0,"minutes":0,"month":7,"nanos":0,"seconds":0,"time":1280592000000,"timezoneOffset":-480,"year":110}

那么我们如果想要yyyy-MM-dd HH:mm:ss 这种格式的怎么办呢?

那么解决方案有3个

都必须使用jsonConfig对象进行处理

(1)使用jsonConfig的setExcludes的方法进行过滤,将所需要过滤的字段名传入setExcludes方法

    public void objectToJson(){

        ClassPathXmlApplicationContext xa=new ClassPathXmlApplicationContext("applicationContext.xml");

        EmpDAO dao=(EmpDAO) xa.getBean("EmpDAO");

        //查找对象

        Emp emp=dao.findById(27);

        //创建jsonConfig对象

        JsonConfig config=new JsonConfig();

        //设置过滤字段

        config.setExcludes(new String[]{"dept"});

        String s=JSONObject.fromObject(emp,config).toString();

        System.out.println(s);

    }

(2)使用jsonConfig的setJsonPropertyFilter进行属性过滤,过滤器中返回true表示过滤该字段,返回false表示可以转换该字段

    public void objectToJson(){

        ClassPathXmlApplicationContext xa=new ClassPathXmlApplicationContext("applicationContext.xml");

        EmpDAO dao=(EmpDAO) xa.getBean("EmpDAO");

        //查找对象

        Emp emp=dao.findById(27);

        //创建jsonConfig对象

        JsonConfig config=new JsonConfig();

        //设置过滤字段

        config.setJsonPropertyFilter(new PropertyFilter() {

            public boolean apply(Object arg0, String arg1, Object arg2) {

                if("dept".equals(arg1)){

                    return true;

                }

                return false;

            }

        });

        String s=JSONObject.fromObject(emp,config).toString();

        System.out.println(s);

    }

上述两种解决方案可以解决部分问题,但是json-lib使用代理进行反射,所以如果想要部门表的信息,而去过滤部门表的员工对象,这样还是解决不了。这样可以使用更简单有效的方案

(3)使用jsonConfig的setCycleDetectionStrategy()方法进行忽略死循环

    使用jsonConfig的registerJsonValueProcessor()进行属性转换设置

  /**

    * 通过对象转换成json

    * @author 凤生禾予

    */

    public void objectToJson(){

        ClassPathXmlApplicationContext xa=new ClassPathXmlApplicationContext("applicationContext.xml");

        EmpDAO dao=(EmpDAO) xa.getBean("EmpDAO");

        //查找对象

        Emp emp=dao.findById(27);

        //创建jsonConfig对象

        JsonConfig config=new JsonConfig();

        //设置循环策略为忽略    解决json最头疼的问题 死循环

        config.setCycleDetectionStrategy(CycleDetectionStrategy.LENIENT);

        //设置 json转换的处理器  用来处理日期类型

        //凡是反序列化Date类型的对象,都会经过该处理器进行处理

        config.registerJsonValueProcessor(Date.class, new JsonValueProcessor() {

            //参数1 :属性名   参数2:json对象的值   参数3:jsonConfig对象

            public Object processObjectValue(String arg0, Object arg1, JsonConfig arg2) {

                SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");

                Date d=(Date) arg1;

                return sdf.format(d);

            }

            public Object processArrayValue(Object arg0, JsonConfig arg1) {

                return null;

            }

        });

        String s=JSONObject.fromObject(emp,config).toString();

        System.out.println(s);

    }

这种方案可以解决死循环问题和日期格式化的问题。

结果:

{"birthday":"2010-08-01 00:00:00","dept":{"depid":1,"depname":"开发部","emps":[{"birthday":"2009-08-01 00:00:00","dept":null,"empid":30,"empname":"田七"},null]},"empid":27,"empname":"王五"}

3.集合反序列化成json

    /**

    * 通过集合转换成json

    * @author  凤生禾予

    */

    public void arrayToJson(){

        ClassPathXmlApplicationContext xa=new ClassPathXmlApplicationContext("applicationContext.xml");

        EmpDAO dao=(EmpDAO) xa.getBean("EmpDAO");

     List emps=dao.findAll();

        JsonConfig config=new JsonConfig();

        config.setCycleDetectionStrategy(CycleDetectionStrategy.LENIENT);

        config.registerJsonValueProcessor(Date.class, new JsonValueProcessor() {

            @Override

            public Object processObjectValue(String arg0, Object arg1, JsonConfig arg2) {

                // TODO Auto-generated method stub

                SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");

                Date d=(Date) arg1;

                return sdf.format(d);

            }

            @Override

            public Object processArrayValue(Object arg0, JsonConfig arg1) {

                // TODO Auto-generated method stub

                return null;

            }

        });

        String s=JSONArray.fromObject(emps,config).toString();

        System.out.println(s);

    }

 这个和上面没有太多区别。

总结:使用json-lib进行对象的序列化和反序列化的文档比较少,在工作中进行及时总结经验是一个比较好的方式。

      json-lib对象的序列化比较简单,重要的是使用JSONObject和JSONArray两个对象,这两个对象进行序列化pojo对象之前,必须将json转换成对应的JSONObject和JSONArray对象。

     json-lib对象的反序列化相对复杂些,因为反序列时json-lib通过代理对对象进行反射操作将对象生成json,特别在Hibernate中容易产生死循环操作,而且对一些日期和其他的复杂对象的转换可能和我们的预期不一致,所以一定要对jsonConfig对象进行详细研究,其中的setExcludes,setJsonPropertyFilter,setCycleDetectionStrategy,registerJsonValueProcessor等方法相当有用。

    希望我今天的这些心得对大家有一些帮助。

文档

使用json-lib完成json的序列化和反序列化

使用json-lib完成json的序列化和反序列化2011-07-2914:07:43分类:默认分类|标签:软件javajson.json的序列化和反序列化在现在的javaweb中特别是ajax中使用的比较频繁,现在本人就这种技术提出自己的使用心得。我的pojo对象的结构是这样的部门表和员工表1对多的关系部门对象publicclassDeptimplementsjava.io.Serializable{privateIntegerdepid;//部门IDprivateStringdepname
推荐度:
  • 热门焦点

最新推荐

猜你喜欢

热门推荐

专题
Top