deserialized list in singleton grows and grows

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

    deserialized list in singleton grows and grows

    Hello, I have a singleton settings class (.Net 2.0 framework) that I
    serialize/deserialize to XML. On my settings class is a shared list of
    integers. If I have two numbers in my list and I deserialize my class
    successive times, the count of integers in my list grows by 2 each time when
    I would expect it to remain at 2. When I run this code (below) and click the
    button multiple times, my immediate window shows the following results:

    2
    4
    6
    8
    10

    Can anyone tell me what's going on here? TIA.

    Imports System.Xml.Seri alization
    <Serializable() _
    Public Class cMySettings
    Public Shared UserIDs As List(Of Integer)
    Public Property zUserIDs() As List(Of Integer)
    Get
    Return UserIDs
    End Get
    Set(ByVal value As List(Of Integer))
    UserIDs = value
    End Set
    End Property
    End Class

    Public Class Form1
    Private Const sXML As String = _
    "<?xml version=""1.0"" encoding=""utf-16""?<cMySettin gs" & _
    "<zUserIDs><int >1</int><int>2</int></zUserIDs></cMySettings>"

    Private Sub Button1_Click(B yVal sender As System.Object, ByVal e As
    System.EventArg s) Handles Button1.Click
    Dim myStream As New System.IO.Strin gReader(sXML)
    Dim serializer As New
    System.Xml.Seri alization.XmlSe rializer(GetTyp e(cMySettings))
    serializer.Dese rialize(myStrea m)
    Debug.Print(cMy Settings.UserID s.Count)
    End Sub
    End Class


  • rowe_newsgroups

    #2
    Re: deserialized list in singleton grows and grows

    On May 12, 7:09 am, "Monty" <mo...@communit y.nospamwrote:
    Hello, I have a singleton settings class (.Net 2.0 framework) that I
    serialize/deserialize to XML. On my settings class is a shared list of
    integers. If I have two numbers in my list and I deserialize my class
    successive times, the count of integers in my list grows by 2 each time when
    I would expect it to remain at 2. When I run this code (below) and click the
    button multiple times, my immediate window shows the following results:
    >
    2
    4
    6
    8
    10
    >
    Can anyone tell me what's going on here? TIA.
    >
    Imports System.Xml.Seri alization
    <Serializable() _
    Public Class cMySettings
    Public Shared UserIDs As List(Of Integer)
    Public Property zUserIDs() As List(Of Integer)
    Get
    Return UserIDs
    End Get
    Set(ByVal value As List(Of Integer))
    UserIDs = value
    End Set
    End Property
    End Class
    >
    Public Class Form1
    Private Const sXML As String = _
    "<?xml version=""1.0"" encoding=""utf-16""?<cMySettin gs" & _
    "<zUserIDs><int >1</int><int>2</int></zUserIDs></cMySettings>"
    >
    Private Sub Button1_Click(B yVal sender As System.Object, ByVal e As
    System.EventArg s) Handles Button1.Click
    Dim myStream As New System.IO.Strin gReader(sXML)
    Dim serializer As New
    System.Xml.Seri alization.XmlSe rializer(GetTyp e(cMySettings))
    serializer.Dese rialize(myStrea m)
    Debug.Print(cMy Settings.UserID s.Count)
    End Sub
    End Class
    Quick guess here - I didn't run your code.

    You have UserIds as a shared field, so every instance you create is
    going to adds those ids to the shared field. And since the shared
    field won't "die" until the program does, you will continue to get
    higher and higher number of UserIds. You should either pull the shared
    specifier (if they don't need shared across instances) or implement
    IDisposable and clean up the shared property when the instance dies.
    Remember however that for the IDisposable strategy to work, you'll
    need to explicitly call Dispose since it's a crapshoot at best trying
    to let the GC does this for you (you'll never know when the objects
    are removed). You best best (imo) is to just pull the shared specifier
    if at all possible.

    Thanks,

    Seth Rowe [MVP]

    Comment

    • pamela fluente

      #3
      Re: deserialized list in singleton grows and grows

      On 12 Mag, 14:49, rowe_newsgroups <rowe_em...@yah oo.comwrote:
      On May 12, 7:09 am, "Monty" <mo...@communit y.nospamwrote:
      >
      >
      >
      >
      >
      Hello, I have a singleton settings class (.Net 2.0 framework) that I
      serialize/deserialize to XML. On my settings class is a shared list of
      integers. If I have two numbers in my list and I deserialize my class
      successive times, the count of integers in my list grows by 2 each time when
      I would expect it to remain at 2. When I run this code (below) and clickthe
      button multiple times, my immediate window shows the following results:
      >
      2
      4
      6
      8
      10
      >
      Can anyone tell me what's going on here? TIA.
      >
      Imports System.Xml.Seri alization
      <Serializable() _
      Public Class cMySettings
          Public Shared UserIDs As List(Of Integer)
          Public Property zUserIDs() As List(Of Integer)
              Get
                  Return UserIDs
              End Get
              Set(ByVal value As List(Of Integer))
                  UserIDs = value
              End Set
          End Property
      End Class
      >
      Public Class Form1
          Private Const sXML As String = _
              "<?xml version=""1.0"" encoding=""utf-16""?<cMySettin gs" & _
              "<zUserIDs><int >1</int><int>2</int></zUserIDs></cMySettings>"
      >
          Private Sub Button1_Click(B yVal sender As System.Object, ByVal eAs
      System.EventArg s) Handles Button1.Click
              Dim myStream As New System.IO.Strin gReader(sXML)
              Dim serializer As New
      System.Xml.Seri alization.XmlSe rializer(GetTyp e(cMySettings))
              serializer.Dese rialize(myStrea m)
              Debug.Print(cMy Settings.UserID s.Count)
          End Sub
      End Class
      >
      Quick guess here - I didn't run your code.
      >
      You have UserIds as a shared field, so every instance you create is
      going to adds those ids to the shared field. And since the shared
      field won't "die" until the program does, you will continue to get
      higher and higher number of UserIds. You should either pull the shared
      specifier (if they don't need shared across instances) or implement
      IDisposable and clean up the shared property when the instance dies.
      Remember however that for the IDisposable strategy to work, you'll
      need to explicitly call Dispose since it's a crapshoot at best trying
      to let the GC does this for you (you'll never know when the objects
      are removed). You best best (imo) is to just pull the shared specifier
      if at all possible.
      >
      Thanks,
      >
      Seth Rowe [MVP]- Nascondi testo tra virgolette -
      >
      - Mostra testo tra virgolette -
      probably, if you need the shared, you could perhaps:


      <Serializable() Public Class cMySettings

      Sub New()
      UserIDs.Clear()
      End Sub

      Public Shared UserIDs As New List(Of Integer)

      Public Property zUserIDs() As List(Of Integer)
      Get
      Return UserIDs
      End Get
      Set(ByVal value As List(Of Integer))
      UserIDs = value
      End Set
      End Property

      End Class



      -P

      Comment

      • Monty

        #4
        Re: deserialized list in singleton grows and grows

        Thanks Seth, but I guess I don't understand why it would ~add~ to the list
        rather than ~replace~ it each time I deserialize my settings? For instance,
        if I add a "Name" string property to my singleton (full code below) and
        output the name each time along with the count, I get this:

        2
        Bubba
        4
        Bubba
        6
        Bubba
        8
        Bubba

        But given the way the list behaves, why wouldn't I get this?

        2
        Bubba
        4
        BubbaBubba
        6
        BubbaBubbaBubba
        8
        BubbaBubbaBubba Bubba


        [Updated code:]

        Imports System.Xml.Seri alization
        <Serializable() _
        Public Class cMySettings
        Public Shared UserIDs As List(Of Integer)
        Public Shared Name As String
        Public Property zName() As String
        Get
        Return Name
        End Get
        Set(ByVal value As String)
        Name = value
        End Set
        End Property
        Public Property zUserIDs() As List(Of Integer)
        Get
        Return UserIDs
        End Get
        Set(ByVal value As List(Of Integer))
        UserIDs = value
        End Set
        End Property
        End Class
        Public Class cMyEmp
        Private _Name As String
        Public Property Name() As String
        Get
        Return _Name
        End Get
        Set(ByVal value As String)
        _Name = value
        End Set
        End Property
        End Class
        Public Class Form1
        Private Const sXML As String = _
        "<?xml version=""1.0"" encoding=""utf-16""?<cMySettin gs" & _
        "<zUserIDs><int >1</int><int>2</int></zUserIDs>" & _
        "<zName>Bub ba</zName>" & _
        "</cMySettings>"

        Private Sub Button1_Click(B yVal sender As System.Object, ByVal e As
        System.EventArg s) Handles Button1.Click
        Dim myStream As New System.IO.Strin gReader(sXML)
        Dim serializer As New XmlSerializer(G etType(cMySetti ngs))
        serializer.Dese rialize(myStrea m)
        Debug.Print(cMy Settings.UserID s.Count)
        Debug.Print(cMy Settings.Name)
        End Sub
        End Class


        Comment

        • Monty

          #5
          Re: deserialized list in singleton grows and grows

          That works, grazie!

          "pamela fluente" <pamelafluente@ libero.itwrote in message


          Comment

          • Steve Gerrard

            #6
            Re: deserialized list in singleton grows and grows

            Monty wrote:
            Thanks Seth, but I guess I don't understand why it would ~add~ to the
            list rather than ~replace~ it each time I deserialize my settings?
            For instance, if I add a "Name" string property to my singleton (full
            code below) and output the name each time along with the count, I get
            this:
            For a list, deserializing will *not* create a new list, then Set the list
            property. It will Get the existing list, then add the stored items to the list.
            It expects the newly created object to have inititialized a new empty list.

            For a string, which is a single value type, not a list or collection, it will
            assign the stored value to the property, not append it.


            Comment

            • rowe_newsgroups

              #7
              Re: deserialized list in singleton grows and grows

              On May 12, 9:17 am, pamela fluente <pamelaflue...@ libero.itwrote:
              On 12 Mag, 14:49, rowe_newsgroups <rowe_em...@yah oo.comwrote:
              >
              >
              >
              On May 12, 7:09 am, "Monty" <mo...@communit y.nospamwrote:
              >
              Hello, I have a singleton settings class (.Net 2.0 framework) that I
              serialize/deserialize to XML. On my settings class is a shared list of
              integers. If I have two numbers in my list and I deserialize my class
              successive times, the count of integers in my list grows by 2 each time when
              I would expect it to remain at 2. When I run this code (below) and click the
              button multiple times, my immediate window shows the following results:
              >
              2
              4
              6
              8
              10
              >
              Can anyone tell me what's going on here? TIA.
              >
              Imports System.Xml.Seri alization
              <Serializable() _
              Public Class cMySettings
              Public Shared UserIDs As List(Of Integer)
              Public Property zUserIDs() As List(Of Integer)
              Get
              Return UserIDs
              End Get
              Set(ByVal value As List(Of Integer))
              UserIDs = value
              End Set
              End Property
              End Class
              >
              Public Class Form1
              Private Const sXML As String = _
              "<?xml version=""1.0"" encoding=""utf-16""?<cMySettin gs" & _
              "<zUserIDs><int >1</int><int>2</int></zUserIDs></cMySettings>"
              >
              Private Sub Button1_Click(B yVal sender As System.Object, ByVal e As
              System.EventArg s) Handles Button1.Click
              Dim myStream As New System.IO.Strin gReader(sXML)
              Dim serializer As New
              System.Xml.Seri alization.XmlSe rializer(GetTyp e(cMySettings))
              serializer.Dese rialize(myStrea m)
              Debug.Print(cMy Settings.UserID s.Count)
              End Sub
              End Class
              >
              Quick guess here - I didn't run your code.
              >
              You have UserIds as a shared field, so every instance you create is
              going to adds those ids to the shared field. And since the shared
              field won't "die" until the program does, you will continue to get
              higher and higher number of UserIds. You should either pull the shared
              specifier (if they don't need shared across instances) or implement
              IDisposable and clean up the shared property when the instance dies.
              Remember however that for the IDisposable strategy to work, you'll
              need to explicitly call Dispose since it's a crapshoot at best trying
              to let the GC does this for you (you'll never know when the objects
              are removed). You best best (imo) is to just pull the shared specifier
              if at all possible.
              >
              Thanks,
              >
              Seth Rowe [MVP]- Nascondi testo tra virgolette -
              >
              - Mostra testo tra virgolette -
              >
              probably, if you need the shared, you could perhaps:
              >
              <Serializable() Public Class cMySettings
              >
              Sub New()
              UserIDs.Clear()
              End Sub
              >
              Public Shared UserIDs As New List(Of Integer)
              >
              Public Property zUserIDs() As List(Of Integer)
              Get
              Return UserIDs
              End Get
              Set(ByVal value As List(Of Integer))
              UserIDs = value
              End Set
              End Property
              >
              End Class
              >
              -P
              One nasty side effect of this is that if you create back to back
              cMySettings classes, both will show the most recent items, losing
              whatever was added by the first instance. You mention "singleton" in
              your subject so hopefully you just haven't added in the singleton
              pattern yet so once you do that it should take care of the problem.
              Though if you implement singleton, I don't see a reason for the shared
              variable.....

              Thanks,

              Seth Rowe [MVP]

              Comment

              Working...