You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java自定义序列化实现机制及第三方框架相关疑问咨询

Awesome questions—let's unpack each one clearly so you can get a solid grasp of how this all works.

How Custom Java Serialization Works

First, let's start with the basics: default Java serialization relies on the JVM handling the conversion of objects to bytes (and vice versa) automatically, as long as your class implements the Serializable marker interface.

Custom serialization lets you take control of this process. Here's how it works:

  1. Your class still needs to implement Serializable (it's the trigger for the JVM to consider serialization for the class).
  2. Add private methods named writeObject(ObjectOutputStream out) and readObject(ObjectInputStream in) to your class. These method signatures must be exact—no changes to return types or parameters.
  3. When serialization happens, the JVM will bypass its default logic and use reflection to call your custom writeObject method. Similarly, during deserialization, it will call your readObject method instead of the default reconstruction process.

You can use this to handle things like encrypting sensitive data before serialization, skipping unnecessary fields, or adding custom validation during deserialization. Here's a quick example:

import java.io.*;

public class User implements Serializable {
    private String username;
    private String password; // We'll encrypt this instead of serializing it raw

    public User(String username, String password) {
        this.username = username;
        this.password = password;
    }

    // Custom serialization logic
    private void writeObject(ObjectOutputStream out) throws IOException {
        out.defaultWriteObject(); // First serialize all non-custom fields normally
        // Encrypt the password before writing it to the stream
        out.writeObject(encryptPassword(password));
    }

    // Custom deserialization logic
    private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundException {
        in.defaultReadObject(); // Read the default fields first
        // Decrypt the password when reconstructing the object
        this.password = decryptPassword((String) in.readObject());
    }

    private String encryptPassword(String rawPassword) {
        // Simple example encryption (use a real library like BouncyCastle in production!)
        return new StringBuilder(rawPassword).reverse().toString();
    }

    private String decryptPassword(String encryptedPassword) {
        return new StringBuilder(encryptedPassword).reverse().toString();
    }
}

Bonus: You can also use writeReplace() and readResolve() methods to replace the object being serialized/deserialized (useful for singletons, for example, to ensure only one instance exists after deserialization).

Third-Party Serialization Frameworks (e.g., Kryo)

To answer your next questions directly:

  • No, third-party frameworks like Kryo do not rely on the JVM's built-in serialization mechanism. They handle the entire serialization/deserialization pipeline themselves.
  • Kryo's underlying work is fully managed by the framework, not the JVM. It uses low-level techniques like reflection or ASM (bytecode manipulation) to directly read and write object fields, bypassing the JVM's serialization rules entirely.
  • You do NOT need to implement Serializable when using Kryo. The framework doesn't require this marker interface—you can serialize almost any object, even if it doesn't implement Serializable.

Here's a quick Kryo example to illustrate this:

import com.esotericsoftware.kryo.Kryo;
import com.esotericsoftware.kryo.io.Input;
import com.esotericsoftware.kryo.io.Output;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;

public class KryoDemo {
    public static void main(String[] args) {
        Kryo kryo = new Kryo();
        kryo.register(User.class); // Registering classes improves performance (optional but recommended)

        // Create an object to serialize (note: User doesn't implement Serializable!)
        User user = new User("Bob", "mySecurePass123");

        // Serialize the object to bytes
        ByteArrayOutputStream bos = new ByteArrayOutputStream();
        Output output = new Output(bos);
        kryo.writeObject(output, user);
        output.close();

        // Deserialize back to an object
        ByteArrayInputStream bis = new ByteArrayInputStream(bos.toByteArray());
        Input input = new Input(bis);
        User deserializedUser = kryo.readObject(input, User.class);
        input.close();

        System.out.println(deserializedUser.getUsername()); // Prints "Bob"
    }
}

// This class has no connection to Serializable!
class User {
    private String username;
    private String password;

    // Kryo typically requires a no-arg constructor (you can configure it to use other constructors too)
    public User() {}

    public User(String username, String password) {
        this.username = username;
        this.password = password;
    }

    public String getUsername() {
        return username;
    }
}

Third-party frameworks like Kryo are popular because they're faster than JVM serialization and produce smaller byte streams—great for performance-critical applications like distributed systems or games.

内容的提问来源于stack exchange,提问作者CuriousMind

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.13 08:02:56