java 那些鲜为人知的序列化(debug)
来源:互联网 发布:2014年网络炒作事件 编辑:程序博客网 时间:2024/06/07 12:34
一:起因
Java提供一种机制叫做序列化,其实就是把实体类的对象(Bean对象)以二进制的形式就行存储和传输(读取),多有需要序列化的对象对应的类需要继承 接口 Serializable。
(1)通过有序的格式或者字节序列持久化java对象,其中包含对象的数据,还有对象的类型,和保存在对象中的数据类型。所以,如果我们已经序列化了一个对象,那么它可以被读取并通过对象的类型和其他信息进行反序列化,并最终获取对象的原型。
(2)ObjectInputStream 和 ObjectOutputStream对象是高级别的流对象,包含序列化和反序列化的方法。ObjectOutputStream 拥有很多序列化对象的方法.
(2-2) 我们可以通过序列化来保存一个对象的状态(实例变量)到文件中,也可以从这个格式化的文件中很容易地读取对象的状态从而可以恢复我们保存的对象;用来实现序列化的类都在java.io包中,我们常用的类或接口有:ObjectOutputStream:提供序列化对象并把其写入流的方法ObjectInputStream:读取流并反序列化对象 ;Serializable:一个对象想要被序列化,那么它的类就要实现 此接口
(3)那么哪里会需要序列化呢?序列化通常在需要通过网络传输数据,或者保存对象到文件的场合使用。这里说的数据是对象而不是文本。
现在的问题是,我们的网络架构和硬盘都只能识别二进制和字节,而不能识别Java对象。序列化就是把Java对象中的value/states翻译为字节,以便通过网络传输或者保存。另外,反序列化就是通过读取字节码,并把它翻译回java对象
二:示例
(1)员工实体类(Employee.java 是一个bean,内含get set方法)
import java.io.Serializable;public class Employee implements Serializable{ int employeeId; String employeeName; String department; public int getEmployeeId() { return employeeId; } public void setEmployeeId(int employeeId) { this.employeeId = employeeId; } public String getEmployeeName() { return employeeName; } public void setEmployeeName(String employeeName) { this.employeeName = employeeName; } public String getDepartment() { return department; } public void setDepartment(String department) { this.department = department; }}(2)这里以存储在外部文件为例子,外部文件命名为employee.out (文件的读写以employee类的对象进行)
import java.io.FileOutputStream;import java.io.IOException;import java.io.ObjectOutputStream;import java.util.ArrayList; public class SerializeMain { /** * @author zyp */ public static void main(String[] args) { Employee emp = new Employee(); emp.setEmployeeId(101); emp.setEmployeeName("zyp 张燕鹏"); emp.setDepartment("com.CS"); Employee emp2 = new Employee(); emp2.setEmployeeId(102); emp2.setEmployeeName("xqz 徐勤柱"); emp2.setDepartment("中国海洋大学"); ArrayList<Employee> emps = new ArrayList<Employee>(); emps.add(emp); emps.add(emp2); // 以上两个用于测试的 try { FileOutputStream fileOut = new FileOutputStream("employee.out",true); // employee.ser 这可是文件名称的,相当于序列化的文件名的内的内容的,无法用普通的文本查看器查看的 ObjectOutputStream outStream = new ObjectOutputStream(fileOut); for(int i=0;i<emps.size();i++){ outStream.writeObject(emps.get(i)); System.out.println(emps.get(i)); } outStream.writeObject(null);// 非常关键的哦,否则报错的peekByte错误的,用于读取的时候判空的 outStream.close(); fileOut.close(); }catch(IOException i) { i.printStackTrace(); } }}(3)读取(2)存储的文件
import java.io.FileInputStream;import java.io.IOException;import java.io.ObjectInputStream;import java.util.ArrayList; public class DeserializeMain { /** * @author zyp */ public static void main(String[] args) { ArrayList<Employee> emps = new ArrayList<Employee>(); Employee emp = null; try { FileInputStream fis =new FileInputStream("employee.out"); //employee.ser 这可是之前保存的文件名称的,相当于读取序列化的文件名的内的内容的,无法用普通的文本查看器查看的 ObjectInputStream ois = new ObjectInputStream(fis); emp = (Employee) ois.readObject();// while(emp!=null){ emps.add(emp); emp = (Employee)ois.readObject(); } ois.close(); fis.close(); }catch(IOException i) { i.printStackTrace(); return; }catch(ClassNotFoundException c) { System.out.println("Employee class not found"); c.printStackTrace(); return; } for(int i=0;i<emps.size();i++){ emp = emps.get(i); System.out.println("Deserialized Employee..."); System.out.println("Emp id: " + emp.getEmployeeId()); System.out.println("Name: " + emp.getEmployeeName()); System.out.println("Department: " + emp.getDepartment()); System.out.println(emp); } }}(4)注意事项:
outStream.writeObject(null); (2)中的这一句话,非常关键的哦,否则报错的peekByte错误的,这是用于读取的时候判空的,否者到了文件末尾EOF还在读取employee对象,肯定报错的,错误如下(如果没有这句代码的话)
错误提示
(5)employee.out文件是以16进制进行数据存储的,一般的notepad++文本文件打不开的,UE可以打开的查看16进制代码
(6)eclipse 调试说明:首先打开debug模式(视图)开启,之后设置断点(设置多个断点)
- java 那些鲜为人知的序列化(debug)
- java 那些鲜为人知的保留字
- Activity鲜为人知的那些事(一)
- 创业者那些鲜为人知的事情
- TextView 那些鲜为人知的方法
- 那些鲜为人知的JavaScript 技巧
- Java序列化的那些事
- windows下那些鲜为人知的ftp命令
- linux那些鲜为人知的小秘密
- Pascal中那些鲜为人知的技巧
- RocketMQ捐赠给Apache那些鲜为人知的故事
- Java序列化机制要序列化那些内容
- java 对象序列化要序列化那些内容
- Java序列化机制要序列化那些内容
- codeblocks debug 的那些事
- Java研究:this 之鲜为人知的一面
- Chrome DevTools(2):那些debug的技巧
- JAVA 序列化 和 反序列化 (Externalizable Serializable) 那些事
- linux基本命令-实用工具
- 团队软件开发进阶
- 用GDB调试程序
- 通过Android manifest中的sharedUserId属性的设置来实现apk之间的资源共享
- mysql在linux下的my.cnf文件在哪里!
- java 那些鲜为人知的序列化(debug)
- 修改Android解锁界面
- ActiveMQ优化 客户端优化 预取限制
- 南美洲地图
- SpringMVC和Struts2的异同
- cms.pod around line 457: Expected text after =item, not a number 的解决方法
- leveldb源码阅读-memtable
- 10.2.1 用尾递归避免栈溢出(续!)
- 自动匹配文本框--AutCompleteTextView概述,