<p>I've created an "attached behaviour" in my WPF application which lets me handle the Enter keypress and move to the next control. I call it EnterKeyTraversal.IsEnabled, and you can see the code on my blog <a href="http://www.madprops.org/blog/enter-to-tab-as-an-attached-property/" rel="noreferrer">here</a>.</p>

<p>My main concern now is that I may have a memory leak, since I'm handling the PreviewKeyDown event on UIElements and never explicitly "unhook" the event.</p>

<p>What's the best approach to prevent this leak (if indeed there is one)? Should I keep a list of the elements I'm managing, and unhook the PreviewKeyDown event in the Application.Exit event? Has anyone had success with attached behaviours in their own WPF applications and come up with an elegant memory-management solution?</p>

[{'answer_id': 14065, 'author': 'Nick Berardi', 'author_id': 17, 'author_profile': 'https://Stackoverflow.com/users/17', 'pm_score': 0, 'selected': False, 'text': "<p>Make sure event referencing elements are with in the object they are referencing, like text boxes in the form control.  Or if that can't be prevented.  Create a static event on a global helper class and then monitor the global helper class for events.  If these two steps cannot be done try using a WeakReference, they are usually perfect for these situations, but they come with overhead.</p>\n"}, {'answer_id': 14092, 'author': 'Matt Hamilton', 'author_id': 615, 'author_profile': 'https://Stackoverflow.com/users/615', 'pm_score': 2, 'selected': False, 'text': "<p>@Nick Yeah, the thing with attached behaviours is that by definition they're not in the same object as the elements whose events you're handling.</p>\n\n<p>I think the answer lies within using WeakReference somehow, but I've not seen any simple code samples to explain it to me. :)</p>\n"}, {'answer_id': 14143, 'author': 'TheSmurf', 'author_id': 1975282, 'author_profile': 'https://Stackoverflow.com/users/1975282', 'pm_score': 0, 'selected': False, 'text': '<p>I just read your blog post and I think you got a bit of misleading advice, Matt. If there is an <em>actual</em> memory <em>leak</em> here, then that is a bug in the .NET Framework, and not something you can necessarily fix in your code. </p>\n\n<p>What I think you (and the poster on your blog) are actually talking about here is not actually a leak, but rather an ongoing consumption of memory. That\'s not the same thing. To be clear, leaked memory is memory that is reserved by a program, then abandoned (ie, a pointer is left dangling), and which subsequently cannot be freed. Since memory is managed in .NET, this is theoretically impossible. It is possible, however, for a program to reserve an ever-increasing amount of memory without allowing references to it to go out of scope (and become eligible for garbage collection); however that memory is not leaked. The GC will return it to the system once your program exits.</p>\n\n<p>So. To answer your question, I don\'t think you actually have a problem here. You certainly don\'t have a memory leak, and from your code, I don\'t think you need to worry, as far as memory consumption goes either. As long as you make sure that you are not repeatedly assigning that event handler without ever de-assigning it (ie, that you either only ever set it once, or that you remove it exactly once for each time that you assign it), which you seem to be doing, your code should be fine.</p>\n\n<p>It seems like that\'s the advice that the poster on your blog was trying to give you, but he used that alarming work "leak," which is a scary word, but which many programmers have forgotten the real meaning of in the managed world; it doesn\'t apply here.</p>\n'}, {'answer_id': 14337, 'author': 'Arcturus', 'author_id': 900, 'author_profile': 'https://Stackoverflow.com/users/900', 'pm_score': 4, 'selected': True, 'text': '<p>I do not agree DannySmurf</p>\n\n<p>Some WPF layout objects can clog up your memory and make your application really slow when they are not garbage collected. So I find the choice of words to be correct, you are leaking memory to objects you no longer use. You expect the items to be garbage collected, but they aren\'t, because there is a reference somewhere (in this case in the from an event handler).</p>\n\n<p>Now for a real answer :)</p>\n\n<p>I advise you to read this <a href="http://msdn.microsoft.com/en-us/library/bb613565.aspx" rel="nofollow noreferrer">WPF Performance article on MSDN</a></p>\n\n<blockquote>\n  <p>Not Removing Event Handlers on Objects\n  may Keep Objects Alive</p>\n  \n  <p>The delegate that an object passes to\n  its event is effectively a reference\n  to that object. Therefore, event\n  handlers can keep objects alive longer\n  than expected. When performing clean\n  up of an object that has registered to\n  listen to an object\'s event, it is\n  essential to remove that delegate\n  before releasing the object. Keeping\n  unneeded objects alive increases the\n  application\'s memory usage. This is\n  especially true when the object is the\n  root of a logical tree or a visual\n  tree.</p>\n</blockquote>\n\n<p>They advise you to look into the <a href="http://msdn.microsoft.com/en-us/library/aa970850.aspx" rel="nofollow noreferrer">Weak Event pattern</a></p>\n\n<p>Another solution would be to remove the event handlers when you are done with an object. But I know that with Attached Properties that point might not always be clear..</p>\n\n<p>Hope this helps!</p>\n'}, {'answer_id': 14343, 'author': 'Patrik Svensson', 'author_id': 936, 'author_profile': 'https://Stackoverflow.com/users/936', 'pm_score': 1, 'selected': False, 'text': '<p>Have you though of implementing the "Weak Event Pattern" instead of regular events?</p>\n\n<ol>\n<li><a href="http://shevaspace.spaces.live.com/blog/cns!FD9A0F1F8DD06954!471.entry" rel="nofollow noreferrer">Weak Event Pattern in WPF</a></li>\n<li><a href="http://msdn.microsoft.com/en-us/library/aa970850.aspx" rel="nofollow noreferrer">Weak Event Patterns (MSDN)</a></li>\n</ol>\n'}, {'answer_id': 14688, 'author': 'TheSmurf', 'author_id': 1975282, 'author_profile': 'https://Stackoverflow.com/users/1975282', 'pm_score': 0, 'selected': False, 'text': '<p>@Arcturus: </p>\n\n<blockquote>\n  <p>... clog up your memory and make your\n  application really slow when they are\n  not garbage collected.</p>\n</blockquote>\n\n<p>That\'s blindingly obvious, and I don\'t disagree. However:</p>\n\n<blockquote>\n  <p>...you  are leaking memory to object\n  that you no longer use... because\n  there is a reference to them.</p>\n</blockquote>\n\n<p>"memory is allocated to a program, and that program subsequently loses the ability to access it due to program logic flaws" (Wikipedia, "Memory leak")</p>\n\n<p>If there is an active reference to an object, which your program can access, then <em>by definition</em> it is not leaking memory. A leak means that the object is no longer accessible (to you or to the OS/Framework), and will not be freed <em>for the lifetime of the operating system\'s current session</em>. This is not the case here.</p>\n\n<p>(Sorry to be a semantic Nazi... maybe I\'m a bit old school, but leak has a very specific meaning. People tend to use "memory leak" these days to mean anything that consumes 2KB of memory more than they want...)</p>\n\n<p>But of course, if you do not release an event handler, the object it\'s attached to will not be freed until your process\' memory is reclaimed by the garbage collector at shutdown. But this behaviour is entirely expected, contrary to what you seem to imply. If you expect an object to be reclaimed, then you need to remove anything that may keep the reference alive, including event handlers.</p>\n'}, {'answer_id': 14726, 'author': 'Arcturus', 'author_id': 900, 'author_profile': 'https://Stackoverflow.com/users/900', 'pm_score': 2, 'selected': False, 'text': "<p>Yes I know that in the old days Memory Leaks are an entirely different subject. But with managed code, new meaning to the term Memory Leak might be more appropriate...</p>\n\n<p>Microsoft even acknowledges it to be a memory leak:</p>\n\n<blockquote>\n  <p>Why Implement the WeakEvent Pattern?</p>\n  \n  <p>Listening for events can lead to\n  memory leaks. The typical technique\n  for listening to an event is to use\n  the language-specific syntax that\n  attaches a handler to an event on a\n  source. For instance, in C#, that\n  syntax is: source.SomeEvent += new\n  SomeEventHandler(MyEventHandler).</p>\n  \n  <p>This technique creates a strong\n  reference from the event source to the\n  event listener. Ordinarily, attaching\n  an event handler for a listener causes\n  the listener to have an object\n  lifetime that influenced by the object\n  lifetime for the source (unless the\n  event handler is explicitly removed).\n  But in certain circumstances you might\n  want the object lifetime of the\n  listener to be controlled only by\n  other factors, such as whether it\n  currently belongs to the visual tree\n  of the application, and not by the\n  lifetime of the source. Whenever the\n  source object lifetime extends beyond\n  the object lifetime of the listener,\n  the normal event pattern leads to a\n  memory leak: the listener is kept\n  alive longer than intended.</p>\n</blockquote>\n\n<p>We use WPF for a client app with large ToolWindows that can be dragged dropped, all the nifty stuff, and all compatible with in a XBAP.. But we had the same problem with some ToolWindows that weren't garbage collected.. This was due to the fact that it was still dependent on event listeners.. Now this might not be a problem when you close your window and shut down your app. But if you are creating very large ToolWindows with a lot of commands, and all these commands gets re-evaluated over and over again, and people must use your application all day long.. I can tell you.. it really clogs up your memory and response time of your app..</p>\n\n<p>Also, I find it much easier to explain to my manager that we have a memory leak, than explaining to him that some objects are not garbage collected due to some events that needs cleaning ;)</p>\n"}, {'answer_id': 14767, 'author': 'TheSmurf', 'author_id': 1975282, 'author_profile': 'https://Stackoverflow.com/users/1975282', 'pm_score': -1, 'selected': False, 'text': '<p>Well that (the manager bit) I can certainly understand, and sympathize with.</p>\n\n<p>But whatever Microsoft calls it, I don\'t think a "new" definition is appropriate. It\'s complicated, because we don\'t live in a 100% managed world (even though Microsoft likes to pretend that we do, Microsoft itself does not live in such a world). When you say memory leak, you could mean that a program is consuming too much memory (that\'s a user\'s definition), or that a managed reference will not be freed until exit (as here), or that an unmanaged reference is not being properly cleaned up (that would be a real memory leak), or that unmanaged code called from managed code is leaking memory (another real leak).</p>\n\n<p>In this case, it\'s obvious what "memory leak" means, even though we\'re being imprecise. But it gets awfully tedious talking to some people, who call every over-consumption, or failure-to-collect a memory leak; and it\'s frustrating when these people are programmers, who supposedly know better. It\'s kind of important for technical terms to have unambiguous meanings, I think. Debugging is so much easier when they do.</p>\n\n<p>Anyway. Don\'t mean to turn this into an airy-fairy discussion about language. Just saying...</p>\n'}, {'answer_id': 14786, 'author': 'Arcturus', 'author_id': 900, 'author_profile': 'https://Stackoverflow.com/users/900', 'pm_score': 0, 'selected': False, 'text': "<p>True true,</p>\n\n<p>You are right of course.. But there is a whole new generation of programmers being born into this world that will never touch unmanaged code, and I do believe language definitions will re-invent itself over and over again. Memory leaks in WPF are in this way different than say C/Cpp.</p>\n\n<p>Or course to my managers I referred to it as a memory leaks.. to my fellow colleagues I referred to it as a performance issue!</p>\n\n<p>Referring to the Matt's problem, it might be a performance issue that you might need to tackle. If you just use a few screens and you make those screen controls singletons, you might not see this problem at all ;).</p>\n"}, {'answer_id': 6169737, 'author': 'John Fenton', 'author_id': 613519, 'author_profile': 'https://Stackoverflow.com/users/613519', 'pm_score': 3, 'selected': False, 'text': "<p>Philosophical debate aside, in looking at the OP's blog post, I don't see any leak here:</p>\n\n<pre><code>ue.PreviewKeyDown += ue_PreviewKeyDown;\n</code></pre>\n\n<p>A hard reference to <code>ue_PreviewKeyDown</code> is stored in <code>ue.PreviewKeyDown</code>.</p>\n\n<p><code>ue_PreviewKeyDown</code> is a <code>STATIC</code> method and can't be <code>GCed</code>.</p>\n\n<p>No hard reference to <code>ue</code> is being stored, so nothing is preventing it from being <code>GCed</code>.</p>\n\n<p>So... Where is the leak?  </p>\n"}, {'answer_id': 28239309, 'author': 'Daniel Bişar', 'author_id': 613320, 'author_profile': 'https://Stackoverflow.com/users/613320', 'pm_score': 2, 'selected': False, 'text': '<p>To explain my comment on John Fenton post here is my answer. Lets see the following example:</p>\n\n<pre><code>class Program\n{\n    static void Main(string[] args)\n    {\n        var a = new A();\n        var b = new B();\n\n        a.Clicked += b.HandleClicked;\n        //a.Clicked += B.StaticHandleClicked;\n        //A.StaticClicked += b.HandleClicked;\n\n        var weakA = new WeakReference(a);\n        var weakB = new WeakReference(b);\n\n        a = null;\n        //b = null;\n\n        GC.Collect();\n        GC.WaitForPendingFinalizers();\n        GC.Collect();\n\n        Console.WriteLine("a is alive: " + weakA.IsAlive);\n        Console.WriteLine("b is alive: " + weakB.IsAlive);\n        Console.ReadKey();\n    }\n\n\n}\n\nclass A\n{\n    public event EventHandler Clicked;\n    public static event EventHandler StaticClicked;\n}\n\nclass B\n{\n    public void HandleClicked(object sender, EventArgs e)\n    {\n    }\n\n    public static void StaticHandleClicked(object sender, EventArgs e)\n    {\n    }\n}\n</code></pre>\n\n<p>If you have </p>\n\n<pre><code>a.Clicked += b.HandleClicked;\n</code></pre>\n\n<p>and set only b to null both references weakA and weakB stay alive! If you set only a to null b stays alive but not a (which proves that John Fenton is wrong stating that a hard reference is stored in the event provider - in this case a).</p>\n\n<p>This lead me to the WRONG conclusion that </p>\n\n<pre><code>a.Clicked += B.StaticHandleClicked;\n</code></pre>\n\n<p>would lead to a leak because i though the instance of a would be kept by the static handler. This is not the case (test my program). In the case of static event handler or events it is the other way around. If you write</p>\n\n<pre><code>A.StaticClicked += b.HandleClicked;\n</code></pre>\n\n<p>a reference will be kept to b.</p>\n'}]
['https://Stackoverflow.com/questions/14061', 'https://Stackoverflow.com', 'https://Stackoverflow.com/users/615/']