假设SerializableFunction 指的是扩展Serializable 的类型,则方法引用将是可序列化的。您要求的特定类型的方法参考没有什么特别之处。
最值得注意的是,“对任意对象的实例方法的引用”不会捕获MyClass 的任何实例,因此MyClass 不是Serializable 的事实并不重要。如果您指的是特定实例的实例方法,例如object::foo,情况会有所不同,因为在这种情况下,对象也必须被序列化,如果它的类没有实现@987654327,这将在运行时失败@。
什么不起作用,将void 方法引用为返回类型为Void 的Function。不知道你的SerializableFunction<MyClass, Void>是怎么定义的,但是如果等价于Function<MyClass, Void>&Serializable就不行了。
当你有合适的功能接口时,序列化方法引用是没有问题的:
import java.io.*;
import java.util.function.Consumer;
public class MyClass {
public void foo() {
System.out.println("Serializable");
}
public static void main(String[] args) throws IOException, ClassNotFoundException {
Consumer<MyClass> consumer = (Consumer<MyClass>&Serializable)MyClass::foo;
byte[] serialized;
try(ByteArrayOutputStream baos=new ByteArrayOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(baos)) {
oos.writeObject(consumer);
oos.flush();
serialized=baos.toByteArray();
}
Consumer<MyClass> deserialized;
try(ByteArrayInputStream bais=new ByteArrayInputStream(serialized);
ObjectInputStream ois=new ObjectInputStream(bais)) {
deserialized = (Consumer<MyClass>)ois.readObject();
}
deserialized.accept(new MyClass());
}
}
如前所述,对特定实例的引用必须序列化目标实例,因此,取决于该实例的可序列化性
import java.io.*;
import java.util.function.Consumer;
public class MyClass {
public void foo() {
System.out.println("Serializable");
}
public static void main(String[] args) throws IOException, ClassNotFoundException {
Runnable runnable = (Runnable&Serializable)new MyClass()::foo;
byte[] serialized;
try(ByteArrayOutputStream baos=new ByteArrayOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(baos)) {
oos.writeObject(runnable);
oos.flush();
serialized=baos.toByteArray();
}
Runnable deserialized;
try(ByteArrayInputStream bais=new ByteArrayInputStream(serialized);
ObjectInputStream ois=new ObjectInputStream(bais)) {
deserialized = (Runnable)ois.readObject();
}
deserialized.run();
}
}
将在运行时以 java.io.NotSerializableException: MyClass 失败,除非您将 MyClass 更改为实现 Serializable。