`

java中的IO整理(6)

    博客分类:
  • java
 
阅读更多

对象的序列化

 

对象序列化就是把一个对象变为二进制数据流的一种方法。

 

一个类要想被序列化,就行必须实现java.io.Serializable接口。虽然这个接口中没有任何方法,就如同之前的cloneable接口一样。实现了这个接口之后,就表示这个类具有被序列化的能力。

 

先让我们实现一个具有序列化能力的类吧:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
import java.io.*;
/**
 * 实现具有序列化能力的类
 * */
public class SerializableDemo implements Serializable{
    public SerializableDemo(){
         
    }
    public SerializableDemo(String name, int age){
        this.name=name;
        this.age=age;
    }
    @Override
    public String toString(){
        return "姓名:"+name+"  年龄:"+age;
    }
    private String name;
    private int age;
}

 

这个类就具有实现序列化能力,

 

在继续将序列化之前,先将一下ObjectInputStreamObjectOutputStream这两个类

 

先给一个ObjectOutputStream的例子吧:

 

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
import java.io.Serializable;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectOutputStream;
 
/**
 * 实现具有序列化能力的类
 * */
public class Person implements Serializable{
    public Person(){
 
    }
 
    public Person(String name, int age){
        this.name = name;
        this.age = age;
    }
 
    @Override
    public String toString(){
        return "姓名:" + name + "  年龄:" + age;
    }
 
    private String name;
    private int age;
}
/**
 * 示范ObjectOutputStream
 * */
public class ObjectOutputStreamDemo{
    public static void main(String[] args) throws IOException{
        File file = new File("d:" + File.separator + "hello.txt");
        ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream(
                file));
        oos.writeObject(new Person("rollen", 20));
        oos.close();
    }
}

 

 

【运行结果】:

 

当我们查看产生的hello.txt的时候,看到的是乱码,呵呵。因为是二进制文件。

 

虽然我们不能直接查看里面的内容,但是我们可以使用ObjectInputStream类查看:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import java.io.File;
import java.io.FileInputStream;
import java.io.ObjectInputStream;
 
/**
 * ObjectInputStream示范
 * */
public class ObjectInputStreamDemo{
    public static void main(String[] args) throws Exception{
        File file = new File("d:" + File.separator + "hello.txt");
        ObjectInputStream input = new ObjectInputStream(new FileInputStream(
                file));
        Object obj = input.readObject();
        input.close();
        System.out.println(obj);
    }
}

 

【运行结果】

 

姓名:rollen  年龄:20

 

 

 

到底序列化什么内容呢?

 

其实只有属性会被序列化。

 

Externalizable接口

 

Serializable接口声明的类的对象的属性都将被序列化,但是如果想自定义序列化的内容的时候,就需要实现Externalizable接口。

 

当一个类要使用Externalizable这个接口的时候,这个类中必须要有一个无参的构造函数,如果没有的话,在构造的时候会产生异常,这是因为在反序列话的时候会默认调用无参的构造函数。

 

现在我们来演示一下序列化和反序列话:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
package IO;
 
import java.io.Externalizable;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInput;
import java.io.ObjectInputStream;
import java.io.ObjectOutput;
import java.io.ObjectOutputStream;
 
/**
 * 序列化和反序列化的操作
 * */
public class ExternalizableDemo{
    public static void main(String[] args) throws Exception{
        ser(); // 序列化
        dser(); // 反序列话
    }
 
    public static void ser() throws Exception{
        File file = new File("d:" + File.separator + "hello.txt");
        ObjectOutputStream out = new ObjectOutputStream(new FileOutputStream(
                file));
        out.writeObject(new Person("rollen", 20));
        out.close();
    }
 
    public static void dser() throws Exception{
        File file = new File("d:" + File.separator + "hello.txt");
        ObjectInputStream input = new ObjectInputStream(new FileInputStream(
                file));
        Object obj = input.readObject();
        input.close();
        System.out.println(obj);
    }
}
 
class Person implements Externalizable{
    public Person(){
 
    }
 
    public Person(String name, int age){
        this.name = name;
        this.age = age;
    }
 
    @Override
    public String toString(){
        return "姓名:" + name + "  年龄:" + age;
    }
 
    // 复写这个方法,根据需要可以保存的属性或者具体内容,在序列化的时候使用
    @Override
    public void writeExternal(ObjectOutput out) throws IOException{
        out.writeObject(this.name);
        out.writeInt(age);
    }
 
    // 复写这个方法,根据需要读取内容 反序列话的时候需要
    @Override
    public void readExternal(ObjectInput in) throws IOException,
            ClassNotFoundException{
        this.name = (String) in.readObject();
        this.age = in.readInt();
    }
 
    private String name;
    private int age;
}

 

【运行结果】:

 

姓名:rollen  年龄:20

 

本例中,我们将全部的属性都保留了下来,

 

Serializable接口实现的操作其实是吧一个对象中的全部属性进行序列化,当然也可以使用我们上使用是Externalizable接口以实现部分属性的序列化,但是这样的操作比较麻烦,

 

当我们使用Serializable接口实现序列化操作的时候,如果一个对象的某一个属性不想被序列化保存下来,那么我们可以使用transient关键字进行说明:

 

下面举一个例子:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
package IO;
 
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
 
/**
 * 序列化和反序列化的操作
 * */
public class serDemo{
    public static void main(String[] args) throws Exception{
        ser(); // 序列化
        dser(); // 反序列话
    }
 
    public static void ser() throws Exception{
        File file = new File("d:" + File.separator + "hello.txt");
        ObjectOutputStream out = new ObjectOutputStream(new FileOutputStream(
                file));
        out.writeObject(new Person1("rollen", 20));
        out.close();
    }
 
    public static void dser() throws Exception{
        File file = new File("d:" + File.separator + "hello.txt");
        ObjectInputStream input = new ObjectInputStream(new FileInputStream(
                file));
        Object obj = input.readObject();
        input.close();
        System.out.println(obj);
    }
}
 
class Person1 implements Serializable{
    public Person1(){
 
    }
 
    public Person1(String name, int age){
        this.name = name;
        this.age = age;
    }
 
    @Override
    public String toString(){
        return "姓名:" + name + "  年龄:" + age;
    }
 
    // 注意这里
    private transient String name;
    private int age;
}

 

【运行结果】:

 

姓名:null  年龄:20

 

最后在给一个序列化一组对象的例子吧:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
 
/**
 * 序列化一组对象
 * */
public class SerDemo1{
    public static void main(String[] args) throws Exception{
        Student[] stu = { new Student("hello", 20), new Student("world", 30),
                new Student("rollen", 40) };
        ser(stu);
        Object[] obj = dser();
        for(int i = 0; i < obj.length; ++i){
            Student s = (Student) obj[i];
            System.out.println(s);
        }
    }
 
    // 序列化
    public static void ser(Object[] obj) throws Exception{
        File file = new File("d:" + File.separator + "hello.txt");
        ObjectOutputStream out = new ObjectOutputStream(new FileOutputStream(
                file));
        out.writeObject(obj);
        out.close();
    }
 
    // 反序列化
    public static Object[] dser() throws Exception{
        File file = new File("d:" + File.separator + "hello.txt");
        ObjectInputStream input = new ObjectInputStream(new FileInputStream(
                file));
        Object[] obj = (Object[]) input.readObject();
        input.close();
        return obj;
    }
}
 
class Student implements Serializable{
    public Student(){
 
    }
 
    public Student(String name, int age){
        this.name = name;
        this.age = age;
    }
 
    @Override
    public String toString(){
        return "姓名:  " + name + "  年龄:" + age;
    }
 
    private String name;
    private int age;
}

 

【运行结果】:

 

姓名:  hello  年龄:20

 

姓名:  world  年龄:30

 

姓名:  rollen  年龄:40

 

 

 

写在最后:本文章没有涉及java.nio,等我有时间,我自会补上的,欢迎大家关注我的博客,大家一起交流学习。

 

转自:http://www.cnblogs.com/rollenholt/archive/2011/09/11/2173787.html

分享到:
评论

相关推荐

    java中的IO整理完整版

    java中的IO整理完整版

    Java中IO系统总结[整理].pdf

    Java中IO系统总结[整理].pdf

    java中的IO流整理

    此文档是对JAVA 中的 IO 流的整理,其中有大多实用 而平时可以接触到的 IO 基础,对开发工作者有很大的帮助

    Java中的IO整理完整版

    Java中的IO整理完整版

    JAVA_IO流整理思维导图.emmx

    JAVA_IO流整理思维导图.

    java IO全面整理

    java IO全面整理,整理了一下关于java 的IO操作,我是直接在测试的时候将关键的测试代码放上去了,并配以简洁的注解,适合有一定基础的朋友!

    javaIO流整理.txt

    javaIO流整理.txt

    java基础 IO流

    此文档属于本人当初学习java基础之IO流,所整理的文档。里面有字节流与字符流的比较,也有总结使用不同方式读取文档的demo。希望对你的学习有帮助,谢谢!

    Java中IO流简介_动力节点Java学院整理

    Java io系统的设计初衷,就是为了实现“文件、控制台、网络设备”这些io设置的通信。例如,对于一个文件,我们...而到了java 1.1,为了与国际化进行接轨,在java io中添加了许多以字符(Unicode)为单位进行操作的类。

    javaIO流思维导图

    自己整理了一下javaIO流的相关知识点 用xmind软件做了一下

    Java IO流.xmind

    Java IO流思维导图,主要摘录整理的是java.io.*包下的所有IO对象,其中对应备注里包含各个IO对象的构造方法

    Java IO复用_动力节点Java学院整理

    对于服务器的并发处理能力,我们需要的是:每一毫秒服务器都能及时处理这一毫秒内收到的数百个不同TCP连接上的报文,与此同时,可能服务器上还有数以十万计的最近几秒没有收发任何报文的相对不活跃连接。...

    Java多线程.drawio

    Java多线程.drawio

    Java基础篇:IO流.pdf

    该文档主要整理了Java IO流的相关信息,主要包括IO流的按照不同维度的分类、节点流、处理流、输入输出流的处理过程、抽象基类的使用等细节内容

    scalable-io-in-java-中文.pdf

    网上都是不带书签,并且有些地方翻译有歧义。 所以我整理了一个。 特点:带书签 Scalable io in java 中文版,并且对有歧义的语义进行了修改。

    IO流体系继承结构图_动力节点Java学院整理

    Java IO体系结构看似庞大复杂,其实有规律可循,要弄清楚其结构,需要明白两点: 1. 其对称性质:InputStream 与 OutputStream, Reader 与 Writer,他们分别是一套字节输入-输出,字符输入-输出体系 2. 原始处理器(适配器)...

    Java线程和IO总结[整理].pdf

    Java线程和IO总结[整理].pdf

    JAVA高级知识点整理.rar

    Java高级技术整理,包含多线程、虚拟机、JAVA IO/NIO 、Java集合 等高级进阶知识点

    Java中的IO与NIO-jiava求职面试-15题,答案

    最新整理的Java中的IO与NIO相关面试题目总结,java求职面试题,共15题,含答案解析,希望能帮到有需求的同学

    java核心知识点整理

    java详细的知识点整理,包括:jvm原理、IO、类加载过程、集合、线程、反射、泛型等java基础,spring原理、特点,微服务架构、数据库引擎、消息组件、算法、数据结构等。偏理论的知识较多,主要用于面试。

Global site tag (gtag.js) - Google Analytics