【游戏服务器开发-准备篇】对象Json序列化工具类

前言

对象的序列化和反序列化在网络应用通信过程中十分重要,而Json通常是其中最常用的一种传输格式。

就个人接触项目的序列化部分,主要分为两类。一类是十分严谨的,每个Json串都有与之映射的Java对象,通过对象进行序列化和反序列化。第二类较为灵活,通过类库手动拼写Json串。

目前正在用的服务架构中,使用第一类,通过fast-json类库,每次对需要返回的数据手动拼写json字符串。这样的做法有好也有坏。

优点在于
1. 拼凑的数据格式较为灵活,可以根据每个接口的实际需求,灵活的调整数据。
2. 不需为每个接口的返回值创建一个与之对应的java对象进行管理,可以极大减少一些重复代码的出现。
缺点在于
1. 手工拼写,很容易出现格式和语法错误。且代码中有大量的与业务逻辑无关的代码。使代码结构混乱,影响代码整洁度,出现问题很难排查。
2. 没有统一的对象进行映射,很难进行统一的管理。

个人更加喜欢第一种较为严谨的方式。即便代码可能膨胀,但通过继承等方式可以尽量避免,同时能够减少语法和格式等低级错误的出现。


一、常用Json序列化类库对比

目前市面上比较常用的集中Json序列化类库有,Jackson、Gson、FastJson。各种类库的API接口说明都很详细,且大同小异。使用上三者基本都没有难度。
主要考虑三者序列化和反序列化的效率问题。博客上都说FastJson是最快的类库。没有亲自测试,主要参考了这篇博客:
http://blog.csdn.net/accountwcx/article/details/50252657 FastJSON、Gson和Jackson性能对比
结论

  1. FastJSON和GsonJSON序列化的速度差不多,Jackson是最快的(用时Gson少大约600毫秒)
  2. 三个类库在反序列化上性能比较接近,Gson稍微差一些。

考虑系统以后的主体构成是SpringMVC + Netty 因此,大量的反序列化可能由springMVC实现,系统中更多的是使用序列化。因此,选择自己较为熟悉的Jackson。


二、代码实现

代码逻辑十分简单,类加载时初始化Jackson的相关配置。
序列化和反序列化都通过Jackson的objectMapper提供的接口实现。

/**
 * Json序列化与反序列化工具
 * @author 毅成
 * @since 2017年7月22日 上午10:25:22
 * @version MARK 0.0.1
 */
public class JsonConvertUtil {

    private static ObjectMapper objectMapper = new ObjectMapper();

    //设置objectMapper
    static {
        // 反序列化未知属性不会失败
        objectMapper.disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES);
        // 序列化的字段包含
        objectMapper.setSerializationInclusion(Include.NON_NULL);
        objectMapper.setSerializationInclusion(Include.NON_EMPTY);
    }

    /**
     * 序列化对象
     * @author 毅成
     * @since 2017年7月22日 上午10:25:59
     * @version MARK 0.0.1
     */
    public static String serializeObj(Object t){
        String jsonStr = null;
        try {
            jsonStr = objectMapper.writeValueAsString(t);
        } catch (JsonProcessingException e) {
            e.printStackTrace();
        }
        return jsonStr;
    }

    /**
     * 反序列化
     * @author 毅成
     * @since 2017年7月22日 上午10:37:45
     * @version MARK 0.0.1
     */
    public static <T> T deserializeJson(String jsonStr, Class<T> type){
        T obj = null;
        try {
            obj = objectMapper.readValue(jsonStr, type);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return obj;
    }

    public static void main(String[] args) {
        int[] array = {1,2,3,4,5,6,7};
        String arrStr = serializeObj(array);
        System.out.println(arrStr);
        int[] arrayo = deserializeJson(arrStr, int[].class);
        System.out.println(arrayo);
    }
}

三、关于对象序列化的补充

对象序列化在项目中很普通但也很常用。在项目运行中我们通常需要观察一些关键对象的属性和值,通过日志将其打印出来。
但是通常而言,打印会直接调用Object的toString方法打印出对象的hashCode。这样很难查询对象的详细信息。
因此,通常在代码中,也会使一些对象统一继承一个基类,重写其toString方法。实现序列化输出。
个人常用的方式是common-lang包的toStringBuilder类实现,较为简单。具体如下

@Override
public String toString() {
    return ToStringBuilder.reflectionToString(this);
}

该工具类的API还提供了一些序列化的风格。如

ToStringStyle.JSON_STYLE //Json风格

可以根据参照API根据自己的需求实现

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值