4

If I have

public interface Foo {
    public void oneMethod();
}

And then I have another class:

public class TestClass {

    SoftReference sr;

    public test() {
        doSomething(this::lalala);
    }

    public lalala() {

    }

    public doSomethingFoo(Foo foo) {
      sr = new SoftReference(foo);
      //can sr.get() ever return null?
    }
}

Can sr.get() ever return null?

Also interested to know the behaviour in the case where instead of a method reference we use an anonymous inner class or a non static inner class.

user1803551
  • 12,965
  • 5
  • 47
  • 74
pranahata
  • 530
  • 4
  • 18
  • 2
    You should have used a `WeakReference` instead. `SoftReference` will linger on in the Old Generation as long as there's heap to spare. – Marko Topolnik Feb 05 '15 at 11:34
  • Ok, cool, thanks, but can method references get gc if the parent is not? – pranahata Feb 05 '15 at 13:02
  • 1
    The object resulting from desugaring the method reference knows about the `this` object, but not the other way around. So as soon as you let go of that method reference in your own code, it's free for GC. – Marko Topolnik Feb 05 '15 at 13:06
  • 1
    Let me reword what @MarkoTopolnik said: if your specific application and your specific usage scenario calls for `SoftReference` to be used, that's fine, but during testing and debugging, use `WeakReference` instead, because a `SoftReference`d object will not be discarded unless you start running out of memory. – Mike Nakis Feb 05 '15 at 15:03

1 Answers1

10

The life time of an instance created for a method reference does not depend on the target of the method reference. It’s always the other way way round, if your method reference targets a particular instance, the target instance can’t get garbage collected as long as the method reference instance is reachable.

Since the Java specification leaves it open how instances for lambda expressions and method references are created and reused, it’s also unspecified, how long they will live (see A:Does a lambda expression create an object on the heap every time it's executed?).

In practice, with the current implementation, instances which do not capture any values, are remembered and reused and therefore live as long as the class which created them. In contrast, instances which capture values, and this::lalala captures the value of the this reference, are not reused and will get garbage collected as soon as they become unreachable.

Community
  • 1
  • 1
Holger
  • 285,553
  • 42
  • 434
  • 765