Is reference to an instance method serializable in Java 8?
java-8
Solution
Assuming that `SerializableFunction` refers to a type that extends `Serializable`, the method reference will be serializable. There is nothing special about the particular type of method reference your are asking for.
Most notably, the “reference to an instance method of an arbitrary object” is not capturing any instance of `MyClass`, hence, the fact that `MyClass` isn’t `Serializable` is not important. It would be different if you were referring to an instance method of a particular instance like `object::foo`, as in that case, the object had to be serialized as well, which will fail at runtime, if its class doesn’t implement `Serializable`.
What will not work, is to refer to a `void` method as a `Function` of return type `Void`. I don’t know how your `SerializableFunction<MyClass, Void>` is defined, but if it is equivalent to `Function<MyClass, Void>&Serializable`, it will not work.
When you have an appropriate functional interface, serializing the method reference is no problem:
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());
}
}
As said, references to a specific instance have to serialize the target instance, hence, depend on the serializability of that instance so
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();
}
}
will fail at runtime with a `java.io.NotSerializableException: MyClass`, unless you change `MyClass` to implement `Serializable`.
Problem
I want to know if reference to an instance method of an arbitrary object of a particular type is serializable or not? Example: ``` public class MyClass { public void foo() { System.out.println("Serializable"); } } ``` SerializableConsumer ``` @FunctionalInterface public interface SerializableConsumer<T> extends Consumer<T>, Serializable { } ``` and field is: ``` SerializableConsumer<MyClass> serializableMethod = MyClass::foo; ``` EDITED