序列化(Serialization) 是将对象的状态信息转化为可以存储或者传输的形式的过程,一般将一个对象存储到一个储存媒介,例如档案或记忆体缓冲等,在网络传输过程中,可以是字节或者XML等格式;而字节或者XML格式的可以还原成完全相等的对象,这个相反的过程又称为反序列化;
在Java中,我们可以通过多种方式来创建对象,并且只要对象没有被回收我们都可以复用此对象。但是,我们创建出来的这些对象都存在于JVM中的堆(heap)内存中,只有JVM处于运行状态的时候,这些对象才可能存在。一旦JVM停止,这些对象也就随之消失;
但是在真实的应用场景中,我们需要将这些对象持久化下来,并且在需要的时候将对象重新读取出来,Java的序列化可以帮助我们实现该功能。
对象序列化机制(object serialization)是java语言内建的一种对象持久化方式,通过对象序列化,可以将对象的状态信息保存未字节数组,并且可以在有需要的时候将这个字节数组通过反序列化的方式转换成对象,对象的序列化可以很容易的在JVM中的活动对象和字节数组(流)之间进行转换。
在JAVA中,对象的序列化和反序列化被广泛的应用到RMI(远程方法调用)及网络传输中;
Java为了方便开发人员将java对象序列化及反序列化提供了一套方便的API来支持,其中包括以下接口和类:
java.io.Serializable
java.io.Externalizable
ObjectOutput
ObjectInput
ObjectOutputStream
ObjectInputStream
Java类通过实现java.io.Serialization接口来启用序列化功能,未实现此接口的类将无法将其任何状态或者信息进行序列化或者反序列化。可序列化类的所有子类型都是可以序列化的。序列化接口没有方法或者字段,仅用于标识可序列化的语义。
当试图对一个对象进行序列化时,如果遇到一个没有实现java.io.Serialization接口的对象时,将抛出NotSerializationException异常。
如果要序列化的类有父类,要想将在父类中定义过的变量序列化下来,那么父类也应该实现java.io.Serialization接口。
public class PersonSerializableDemo {
public static void main(String[] args) throws Exception {
byte[] bytes = getPersonByte();
System.out.println(bytes);
Person person = reservePerson();
System.out.println(person);
}
public static Person getPerson() throws ParseException {
Person person = new Person();
person.setUsername("HL");
person.setUsercode("035737");
person.setAge(22);
Date birthday = new SimpleDateFormat("yyyy/MM/dd").parse("1997/08/09");
person.setBirthday(birthday);
return person;
}
//对象的序列化与反序列化
public static void reserveObject() throws Exception {
Person person = getPerson();
//序列化
ObjectOutputStream oos=new ObjectOutputStream(new FileOutputStream("template"));
oos.writeObject(person);
oos.close();
//反序列化
ObjectInputStream ois=new ObjectInputStream(new FileInputStream("template"));
Person person1 = (Person)ois.readObject();
System.out.println(person1);
}
}
//对象和byte流互相转换
//将对象转成字节流
public static byte[] getPersonByte() throws Exception {
Person person = getPerson();
ByteArrayOutputStream bo = new ByteArrayOutputStream();
ObjectOutputStream os = new ObjectOutputStream(bo);
os.writeObject(person);
return bo.toByteArray();
};
//将字节流转成对象
public static Person reservePerson() throws Exception {
byte[] bytes = getPersonByte();
ByteArrayInputStream bis = new ByteArrayInputStream(bytes);
ObjectInputStream ois = new ObjectInputStream(bis);
Person person = (Person)ois.readObject();
return person;
};
public class Send {
public static final String QUEUE_NAME="rabbitmq_queue_01";
public static void main(String[] args) throws Exception {
Connection connection = ConnectionUtils.getConnection();
Channel channel = connection.createChannel();
channel.queueDeclare(QUEUE_NAME,true,false,false,null);
for (int i = 0; i < 2; i++) {
channel.basicPublish("",QUEUE_NAME,null, PersonSerializableDemo.getPersonByte());
}
System.out.println("------send msg :success");
}
}
//将字节流转成对象
public static Object reservePerson(byte[] bs) throws Exception {
ByteArrayInputStream bis = new ByteArrayInputStream(bs);
ObjectInputStream ois = new ObjectInputStream(bis);
return ois.readObject();
};
public class Receive {
public static final String QUEUE_NAME="rabbitmq_queue_01";
public static void main(String[] args) throws Exception {
Connection connection = ConnectionUtils.getConnection();
Channel channel = connection.createChannel();
channel.queueDeclare(QUEUE_NAME,true,false,false,null);
//定义一个消费者
DefaultConsumer consumer = new DefaultConsumer(channel) {
@Override
public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
try {
Person person = (Person)PersonSerializableDemo.reservePerson(body);
System.out.println(person.toString());
} catch (Exception e) {
e.printStackTrace();
}
}
};
// 监听队列
channel.basicConsume(QUEUE_NAME,true,consumer);
}
}