Garbage collector question

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • DoB

    #1

    Garbage collector question

    Hi,

    Suppose a situation where some object goes out of scope and its reference
    is not kept anywhere, but a reference to some delegate (that references
    one of the object's methods) is kept as a value in some map.

    Is there a possibility that the object is disposed and the delegate will
    be invalid?

    Yours DoB

    --
    Using Opera's revolutionary e-mail client: http://www.opera.com/mail/
  • Jon Skeet [C# MVP]

    #2
    Re: Garbage collector question

    On Dec 11, 12:58 pm, DoB <D...@dob.comwr ote:
    Suppose a situation where some object goes out of scope and its reference
    is not kept anywhere, but a reference to some delegate (that references
    one of the object's methods) is kept as a value in some map.
    >
    Is there a possibility that the object is disposed and the delegate will
    be invalid?
    Well, it might be disposed - but it certainly won't be garbage
    collected.

    The "a reference to a delegate that references one of the object's
    methods" is directly contradictory to "its reference is not kept
    anywhere". The reference *is* kept in the delegate - provided it's an
    instance method, of course.

    Jon

    Comment

    • DoB

      #3
      Re: Garbage collector question

      The "a reference to a delegate that references one of the object's
      methods" is directly contradictory to "its reference is not kept
      anywhere". The reference *is* kept in the delegate - provided it's an
      instance method, of course.
      Yes, it will be an instance method.

      So...
      as long as the reference to the delegate is kept, the referenced method
      might be safely invoked, is that right?

      DoB


      Comment

      • Marc Gravell

        #4
        Re: Garbage collector question

        Define "safely" ;-p

        The delegate will prevent the object being garbage collected, but if
        the object itself has been deliberately closed/disposed/whatever (by
        code that thinks the object is no longer needed) then the method will
        probably throw an exception when invoked.

        This type of delegate (to an otherwise unreferenced object) is fine by
        itself, but be aware that if used inappropriately this type of hanging
        reference (especially events) is a common cause of memory issues -
        i.e. event subscriptions keeping thousands of objects from being
        collected. For example:


        Marc

        Comment

        • Rene

          #5
          Re: Garbage collector question

          If you look at the Delegate definition, you will see that it contains a
          "Target" and a "Method" properties.

          public object Target { get; }
          public MethodInfo Method { get; }

          This "Target" property is used by the delegate to hold a reference to the
          object that contains the "Method" that should be called when the delegate is
          invoked.

          Having said that, as long as the "Target" property is pointing to the object
          (call this object XYZ), the object XYZ will never be garaged collected
          because there *is* a reference to this object (XYZ) in the delegate
          instance.

          It may look like there is no way to get a hold of the XYZ object but you
          could do so by using the "GetInvocationL ist()" method of the delegate.



          "DoB" <DoB@dob.comwro te in message
          news:op.t258zfi pmqfnmo@dwroble wski.hq.abg.com .pl...
          Hi,
          >
          Suppose a situation where some object goes out of scope and its reference
          is not kept anywhere, but a reference to some delegate (that references
          one of the object's methods) is kept as a value in some map.
          >
          Is there a possibility that the object is disposed and the delegate will
          be invalid?
          >
          Yours DoB
          >
          --
          Using Opera's revolutionary e-mail client: http://www.opera.com/mail/

          Comment

          • DoB

            #6
            Re: Garbage collector question

            Define "safely" ;-p

            :-)))

            In principle I assumed that whenever we explicitly make the object unusable
            (closed/disposed... whatever), we will also explicitly remove the delegates
            from the map in question.
            I was not sure about what would happen in implicit cases, specifically
            including the case when the object in question goes out of scope. I could
            also think of such situations like power management issues, etc. i.e.
            situations not caused directly via our code.

            This type of delegate (to an otherwise unreferenced object) is fine by
            itself, but be aware that if used inappropriately this type of hanging
            reference (especially events) is a common cause of memory issues -
            i.e. event subscriptions keeping thousands of objects from being
            collected. For example:
            http://www.codeproject.com/KB/showca...SProfiler.aspx
            In fact we also want to implement an event subscription mechanism ;-), so we
            take the same risk. Of course we assume that all event subscriptions will be
            deleted each time we explicitly make the subscribed object unusable. It
            would be nice to automatise it somehow, so that the programmer does not have
            to think too much about it every time the object gets explicitly disposed.
            The problem is that I do not know how to use inheritance for this, because
            the objects' classes are going to inherit various other business logic
            classes...

            If you possibly know about a description of some nice event subscription
            mechanism, please let me know ;-)

            Yours
            DoB.


            Comment

            • Jon Skeet [C# MVP]

              #7
              Re: Garbage collector question

              On Dec 12, 10:38 am, "DoB" <D...@dob.comwr ote:
              Define "safely" ;-p
              >
              :-)))
              >
              In principle I assumed that whenever we explicitly make the object unusable
              (closed/disposed... whatever), we will also explicitly remove the delegates
              from the map in question.
              I was not sure about what would happen in implicit cases, specifically
              including the case when the object in question goes out of scope. I could
              also think of such situations like power management issues, etc. i.e.
              situations not caused directly via our code.
              If you keep track of what you've subscribed to, you could make the
              Dispose method unsubscribe as well. It's a bit icky though - I'd
              prefer to design round it usually.

              Jon

              Comment

              • DoB

                #8
                Re: Garbage collector question

                If you keep track of what you've subscribed to, you could make the
                Dispose method unsubscribe as well.
                What I've actually coded is a typical mediator pattern - various objects
                subscribe as listeners to varoius events to a mediator (a singleton).
                The mediator can unsubscribe all subscriptions made by a particular object
                in a single method call.
                The problem arises if this method is not called after an object is no longer
                needed - either because of programmer forgot to call it, or because of some
                unpredicted execution path.

                It's a bit icky though - I'd
                prefer to design round it usually.
                What do you mean?

                Yours
                DoB


                Comment

                • Jon Skeet [C# MVP]

                  #9
                  Re: Garbage collector question

                  On Dec 13, 12:58 pm, "DoB" <D...@dob.comwr ote:
                  If you keep track of what you've subscribed to, you could make the
                  Dispose method unsubscribe as well.
                  >
                  What I've actually coded is a typical mediator pattern - various objects
                  subscribe as listeners to varoius events to a mediator (a singleton).
                  The mediator can unsubscribe all subscriptions made by a particular object
                  in a single method call.
                  The problem arises if this method is not called after an object is no longer
                  needed - either because of programmer forgot to call it, or because of some
                  unpredicted execution path.
                  Well, you *could* use a finalizer to unregister; alternatively, use
                  WeakReference in the mediator. Either way, you should certainly log
                  the situation where you've failed to unsubscribe when you should have
                  done.
                  It's a bit icky though - I'd
                  prefer to design round it usually.
                  >
                  What do you mean?
                  There are often design choices which allow the relationship to be
                  reversed somehow, but that may not be the case in your situation - or
                  there may be oteher undesirable consequences.

                  Jon

                  Comment

                  • Scott Roberts

                    #10
                    Re: Garbage collector question

                    >If you keep track of what you've subscribed to, you could make the
                    >Dispose method unsubscribe as well.
                    >
                    What I've actually coded is a typical mediator pattern - various objects
                    subscribe as listeners to varoius events to a mediator (a singleton).
                    The mediator can unsubscribe all subscriptions made by a particular object
                    in a single method call.
                    The problem arises if this method is not called after an object is no
                    longer needed - either because of programmer forgot to call it, or because
                    of some unpredicted execution path.
                    I only caught the tail end of this thread, so sorry if this has already been
                    mentioned.

                    It looks like you're having trouble with memory leaks resulting from event
                    delegates. If so, this link may be useful:


                    Comment

                    • Martin Carpella

                      #11
                      Re: Garbage collector question

                      Hi,

                      "Jon Skeet [C# MVP]" <skeet@pobox.co mwrites:
                      Well, you *could* use a finalizer to unregister;
                      How does the finalizer come into play here? The subscriber won't be
                      finalized as there are still references to it from the event source.
                      And if the event source is garbage collected, its references to the
                      subscriber don't exist any more.

                      Could you elaborate on this?

                      Best regards,
                      Martin

                      Comment

                      • Jon Skeet [C# MVP]

                        #12
                        Re: Garbage collector question

                        Martin Carpella <martin.carpell a@gmx.netwrote:
                        "Jon Skeet [C# MVP]" <skeet@pobox.co mwrites:
                        >
                        Well, you *could* use a finalizer to unregister;
                        >
                        How does the finalizer come into play here? The subscriber won't be
                        finalized as there are still references to it from the event source.
                        And if the event source is garbage collected, its references to the
                        subscriber don't exist any more.
                        >
                        Could you elaborate on this?
                        Yes, of course you're absolutely right - I can't immediately say what I
                        was thinking of...

                        --
                        Jon Skeet - <skeet@pobox.co m>
                        http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
                        World class .NET training in the UK: http://iterativetraining.co.uk

                        Comment

                        Working...