Java Ref

Simple rules of serialization and deserialization in Java

关于Java序列化和反序列化的原理机制和几种常见的实现方式网络上已经很多了,比如这篇 Java序列化进阶:Java内置序列化的三种方式

本文注重归纳关于序列化&反序列化的几条规则,做个简单备忘参考。

  • 一个Java对象能被序列化==当前对象或者父类实现了Serializable or Externalizable接口;
  • 某个子类是可序列化的[实现了Serializable or Externalizable,其父类是不可序列化的,那么这个父类在定义的时候必须带上一个no-argu constructor[无参构造函数],否则在运行时,readObject()方法会抛出java.io.InvalidClassException;
  • 父类[不可序列化]的无参构造函数在子类对象进行反序列化的时候会被调用,然而子类对象本身的构造函数并不会被调用;
  • Transient和Static修饰的属性不会被序列化,但对于Static来说有一个特殊情况,如果再加上final修饰符那么这个属性就是可以序列化的,这个时候这个属性就变成了一个常量;
  • 如果一个可序列化对象的成员变量引用了不可序列化的对象,那么编译能通过,但是会抛出运行时异常。

参考文献

  1. http://www.xyzws.com/Javafaq/what-are-rules-of-serialization-in-java/208
  2. https://baijiahao.baidu.com/s?id=1568611161638053&wfr=spider&for=pc

常用设计模式「Design Pattern」示例

设计模式「Design Pattern」可谓软件设计思想精髓的集中体现,是前人在大量实践中的总结和提炼,网络上相关的资料多如牛毛,好像没有炒冷饭的必要,但这不代表自己能够吸收并且在工程项目中灵活运用,还是自己总结来的比较实在。


在总结常用的设计模式之前,有必要对设计模式的几条基本原则进行充分的理解:
1. 开闭原则(Open Close Principle)
简单说就是「对修改关闭,对扩展开放」,怎么理解:在设计项目的一个模块(比如根据账户类别查询账户信息)时,假设我们已经实现根据「往来户」和「内部户」这两种账户类别查询账户信息,后续当我们新增账户类别时,我们并不希望去修改原有的业务逻辑,而是针对新增的账户类别查询子模块实现热插拔的效果。我们往往需要借助接口和抽象类来实现这样的效果。
2. 里氏代换原则(Liskov Substitution Principle)
里式代换原则是面向对象语言设计的基本原则之一,是软件功能单元复用的基础。简单的说,该原则表明了:「所有基类可以出现的地方,子类一定可以出现」。是对抽象的「开闭原则」的具体实现,在之后模式的总结中,会大量看到里式替换原则的运用。
3. 依赖倒转原则(Dependence Inversion Principle)
该原则更像是一种方法论,核心内容是:针对接口编程,依赖于抽象的接口而不是具体的实现。
4. 接口隔离原则(Interface Segregation Principle)
该原则提倡我们使用多个接口,而不是单个,以便于接口与接口之间的隔离,降低接口之间的耦合度。
5. 迪米特法则(最少知道原则)(Demeter Principle)
一个实体应当尽量少的与其他实体之间发生相互作用,使得系统功能模块相对独立。
6. 合成复用原则(Composite Reuse Principle)
尽量使用合成/聚合的方式,而不是继承。


在介绍完设计模式的六条基本原则之后,下面来具体说说常用 (更多…)

在new对象中如何使用spring容器中的bean

实际项目开发过程中可能会遇到在new出来的实例对象中使用spring容器中的bean,这个时候我们可以通过以下方法取得(方法不止这一种)。

我们通过实现ApplicationContextAware接口中的setApplicationContext方法来设置Spring容器的上下文环境,同时在VacctSpringContext实现类中增加一个get方法,使得我们有能力得到spring的上下文环境,就像下面这样:

同时在ApplicationContext.xml文件中增加一条配置:

为了在后面使用过程中更方便一点,再提供一个工厂方法,像下面这样:

在需要用到spring容器中的bean时,通过下面这条语句就能获得: