<div dir="ltr"><div dir="ltr">On Sat, Sep 30, 2023 at 12:55 AM David Alayachew <<a href="mailto:davidalayachew@gmail.com">davidalayachew@gmail.com</a>> wrote:</div><div class="gmail_quote"><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex"><div dir="ltr">package Paint;<div style="font-family:monospace"><br>import javax.swing.*;<br><br>public class GUI<br>{<br><br>   private final JFrame frame;<br><br>   public GUI()<br>   {<br>   <br>      this.frame = new JFrame();<br>   <br>      this.frame.add(this.createBottomPanel());<br>   <br>   }<br><br>   private final JPanel createBottomPanel()<br>   {<br>   <br>      final JButton save = new JButton();<br>   <br>      save<br>         .addActionListener<br>         (<br>            actionEvent -><br>            {<br>            <br>               this.toString();<br>            <br>            }<br>            <br>         )<br>         ;<br>   <br>      return null;<br>   <br>   }<br><br>}<br></div><div style="font-family:monospace">```</div><div style="font-family:monospace">Can someone help me understand the what, why, and how of this warning? I don't understand it at all.</div></div></blockquote><div><br></div><div>First note there is really only one warning, even though the compiler says "2 warnings". It's just trying to show you the full "stack trace" where the leak occurs.</div><div><br></div></div><div class="gmail_quote">Here's the sequence of events that the compiler is fretting about:</div><div class="gmail_quote"><ol><li>GUI constructor invokes this.createBottomPanel() </li><li>createBottomPanel() creates a lambda that, if/when it ever gets invoked, could invoke this.toString()</li><li>createBottomPanel() passes this lambda to save.addActionListener()</li><li>save.addActionListener() (which the compiler does NOT inspect) might possibly invoke the lambda</li><li>the lambda invokes GUI.toString()</li></ol><div>Since your class GUI is public and non-final, it could be subclassed, and since GUI.toString() is not final, that subclass could override toString().</div><div><br></div><div>So in summary the compiler is deducing that it's *possible* (in theory) that a subclass could unwittingly operate on an incompletely initialized object - i.e., a 'this' escape.<br></div><div><br></div><div>Note that the compiler only looks at the one file you are compiling. It does not try to inspect JButton to see what addActionListener() actually does. So for step 4 it just assumes the worst case, which is that addActionListener() immediately invokes the lamba. Of course you and I know this is not actually how it behaves.<br></div><div><br></div><div>So is this a "false positive"?</div><div><br></div><div>Yes in the sense that we "know" JButton.addActionListener() doesn't immediately invoke the lambda. But in general the compiler can't make assumptions about the behavior of other classes, even those that are part of the current compilation, because you could swap out class files at runtime and change that behavior.</div><div><br></div><div>So all inferences are made based only on what can be deduced from the one file you are currently compiling. In that sense, this warning is not a false positive.<br></div><div><br></div><div>-Archie<br></div></div><br><span class="gmail_signature_prefix">-- </span><br><div dir="ltr" class="gmail_signature">Archie L. Cobbs<br></div></div>