java中序列化和反序列化是什么?

在 Java 中,序列化和反序列化是两个重要的概念,主要用于对象的持久化存储和网络传输等场景1。

序列化

  • 定义:指将 Java 对象转换为字节序列的过程1。
  • 作用
    • 数据持久化:可以把对象的状态保存到文件中,比如将程序运行过程中的一些重要对象状态保存到磁盘上,以便在程序下次启动时能够恢复这些对象的状态。例如,游戏中的存档功能,把玩家的游戏进度(包含玩家角色的各种属性、游戏场景等信息的对象)序列化后保存到文件,下次玩家打开游戏时,再通过反序列化读取文件中的数据来恢复游戏进度。
    • 网络传输:在网络通信中,需要将对象转换为字节流进行传输。比如在分布式系统中,不同的节点之间要传递对象,就可以先将对象序列化,然后在接收方将字节流反序列化为对象,实现跨网络的对象传递。

反序列化

  • 定义:是序列化的逆过程,即把字节序列恢复为 Java 对象1。
  • 作用:根据字节流中保存的对象状态及描述信息,重建对象,恢复对象状态。

要在 Java 中实现序列化和反序列化,需要满足以下条件1:

  • 类必须实现 java.io.Serializable 接口或 java.io.Externalizable 接口。
    • Serializable 接口是一个标记接口,没有任何方法,仅用于标识类可以被序列化。实现该接口的类的对象可以被序列化和反序列化。如果一个类没有实现 Serializable 接口,在进行序列化操作时会抛出 NotSerializableException
    • Externalizable 接口继承自 Serializable 接口,该接口中定义了两个抽象方法:writeExternal(ObjectOutput out) 与 readExternal(ObjectInput in)。实现 Externalizable 接口的类需要提供这两个方法的具体实现,来控制对象的序列化和反序列化过程。与 Serializable 接口的默认序列化机制相比,Externalizable 接口提供了更细粒度的控制,可以自定义序列化和反序列化的具体行为,但实现起来相对复杂一些。

Java 提供了相关的 API 来支持序列化和反序列化操作,如 java.io.ObjectOutputStream 和 java.io.ObjectInputStream1。ObjectOutputStream 的 writeObject(Object obj) 方法用于将对象序列化并写入输出流,ObjectInputStream 的 readObject() 方法用于从输入流中读取字节序列并反序列化为对象1。

以下是一个简单的 Java 序列化和反序列化的示例代码1:

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;

class Person implements Serializable {
    private String name;
    private int age;

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public int getAge() {
        return age;
    }

    @Override
    public String toString() {
        return "Person{" +
                "name='" + name + '\'' +
                ", age=" + age +
                '}';
    }
}

public class SerializationExample {
    public static void main(String[] args) {
        // 创建一个 Person 对象
        Person person = new Person("John", 25);

        // 序列化对象到文件
        serializeObject(person, "person.ser");

        // 从文件中反序列化对象
        Person deserializedPerson = (Person) deserializeObject("person.ser");

        // 打印反序列化后的对象
        System.out.println(deserializedPerson);
    }

    private static void serializeObject(Object object, String filename) {
        try (FileOutputStream fileOut = new FileOutputStream(filename);
             ObjectOutputStream objectOut = new ObjectOutputStream(fileOut)) {
            objectOut.writeObject(object);
            System.out.println("Object serialized successfully.");
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    private static Object deserializeObject(String filename) {
        try (FileInputStream fileIn = new FileInputStream(filename);
             ObjectInputStream objectIn = new ObjectInputStream(fileIn)) {
            Object object = objectIn.readObject();
            System.out.println("Object deserialized successfully.");
            return object;
        } catch (IOException | ClassNotFoundException e) {
            e.printStackTrace();
            return null;
        }
    }
}

  • 2
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
Java序列化反序列化是将对象转换为字节流以便存储或传输,并在需要时将字节流重新转换为对象的过程[^1]。序列化可以将对象保存到文件或通过网络传输,而反序列化则可以从文件或网络读取字节流并重新构建对象。 序列化的主要作用是实现对象的持久化存储和跨网络传输。当需要将对象保存到磁盘或数据库,或者在不同的Java虚拟机之间传输对象时,就需要使用序列化。通过序列化,可以将对象转换为字节流,然后再将字节流写入文件或通过网络传输。反序列化则是将字节流重新转换为对象,以便在需要时重新使用对象。 在Java,可以通过实现Serializable接口来使一个类可序列化。Serializable接口是一个标记接口,没有任何方法需要实现。只要一个类实现了Serializable接口,就可以将该类的对象序列化反序列化。需要注意的是,被序列化的类的所有成员变量都会被序列化,包括私有成员变量。但是,被声明为static和transient的成员变量不能被序列化。static成员变量是描述类级别的属性,而transient关键字表示临时数据,不需要被序列化Java提供了ObjectOutputStream和ObjectInputStream类来实现序列化反序列化。通过ObjectOutputStream的writeObject()方法可以将对象序列化为字节流,而通过ObjectInputStream的readObject()方法可以将字节流反序列化为对象。 范例: ```java import java.io.*; public class SerializationDemo { public static void main(String[] args) { // 序列化对象 try { // 创建一个Person对象 Person person = new Person("Alice", 25); // 创建一个ObjectOutputStream对象 ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream("person.ser")); // 将person对象写入文件 oos.writeObject(person); // 关闭ObjectOutputStream oos.close(); System.out.println("Person对象已序列化"); } catch (IOException e) { e.printStackTrace(); } // 反序列化对象 try { // 创建一个ObjectInputStream对象 ObjectInputStream ois = new ObjectInputStream(new FileInputStream("person.ser")); // 从文件读取对象 Person person = (Person) ois.readObject(); // 关闭ObjectInputStream ois.close(); System.out.println("反序列化得到的Person对象:"); System.out.println("姓名:" + person.getName()); System.out.println("年龄:" + person.getAge()); } catch (IOException | ClassNotFoundException e) { e.printStackTrace(); } } } class Person implements Serializable { private String name; private int age; public Person(String name, int age) { this.name = name; this.age = age; } public String getName() { return name; } public int getAge() { return age; } } ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

浪仙545

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值