Results 1 to 6 of 6

Thread: Deserialize when I don't know the class

  1. #1

    Thread Starter
    Hyperactive Member
    Join Date
    Jul 2004
    Location
    Kansas, USA
    Posts
    352

    Deserialize when I don't know the class

    I have two classes that both inherit from the same base class. I will be deserializing objects from XML text files. How do I tell what class the objected represented in the text file is so I can deserialize into the right instance of class?

    I developed the code below using the base class. I now actually have two classes that inherit the Robot class.

    Code:
            If File.Exists(fullPath) Then
                Dim rbt As New Robot
                Dim reader As New System.Xml.Serialization.XmlSerializer(GetType(Robot))
                Dim file As New System.IO.StreamReader(fullPath)
                rbt = CType(reader.Deserialize(file), Robot)
                file.Close()
                Return rbt
            Else
                Return Nothing
            End If
    Thanks,
    Eric
    --------------------------------------------------------------------------------------------------------------------
    VB.net/C# ... Visual Studio 2019
    "None of us are as smart as all of us."

  2. #2
    eXtreme Programmer .paul.'s Avatar
    Join Date
    May 2007
    Location
    Chelmsford UK
    Posts
    25,464

    Re: Deserialize when I don't know the class

    You can test the file against both classes...

    https://msdn.microsoft.com/en-us/lib...v=vs.110).aspx

  3. #3
    You don't want to know.
    Join Date
    Aug 2010
    Posts
    4,578

    Re: Deserialize when I don't know the class

    The "automatic" XML serialization doesn't have this capability. There might be some kind of event or callback you can handle that lets you manually inspect incoming XML and choose a deserialization type.

    But generally if you want to put multiple types into some serialized collection, you have to emit some information to help the deserializer understand what it's dealing with for each object. Automatic serialization is for when you're not doing that. So you usually end up writing your own serialization code for that. It's not hard, and everyone should know how to do it.

    But it's also much easier if you don't serialize non-homogenous lists. Another option you could take is to split your list into two different lists, one for each derived type, then serialize a different type with both of those lists. With a little bit of extra work, you could even preserve order.

    One thing modern software engineering might say: if two derived types are so different they can't serialize to the same information, your type hierarchy might be suspect.

    Another option: The Newtonsoft.Json NuGet package offers automatic serialization and deserialization with JSON, the format everyone but Microsoft uses for serialization. (Well, and some people who prefer YAML.) This framework can be configured to emit type information into the JSON. This makes it less likely you can hand-edit the JSON, but also means you can save mixtures of types without doing extra work.

    All in all: I'd need to see your types and be at my Windows machine to offer you more detailed help. I can't be at the windows machine until tomorrow. I don't think it's a good idea to save a list like this until I've thought about it more.
    This answer is wrong. You should be using TableAdapter and Dictionaries instead.

  4. #4

    Thread Starter
    Hyperactive Member
    Join Date
    Jul 2004
    Location
    Kansas, USA
    Posts
    352

    Re: Deserialize when I don't know the class

    My classes represent robots that have a lot in common. There are some very significant differences in that what is on the end of the arm is very different. I built a base class that describes the common features like x, y and z axis parameters. I am then inheriting the class and adding properties that describe that particular end of arm attachment.

    I am not serializing the collection, I am serializing instances of the classes into files. This is how I am persisting settings of the robots.

    I did figure one way to do this. I basically read the xml into an xml object from the file and look at the base node name. I am not in front of my computer either but will try to post the logic tomorrow.
    Thanks,
    Eric
    --------------------------------------------------------------------------------------------------------------------
    VB.net/C# ... Visual Studio 2019
    "None of us are as smart as all of us."

  5. #5

    Thread Starter
    Hyperactive Member
    Join Date
    Jul 2004
    Location
    Kansas, USA
    Posts
    352

    Re: Deserialize when I don't know the class

    Here is one way to do this. Not saying this is best practice but seems to work.

    Code:
                Dim rbt As New Object
                Dim reader As New System.Xml.Serialization.XmlSerializer(GetType(XmlDocument))
                Dim doc As New XmlDocument()
                Dim file As New System.IO.StreamReader(fullPath)
                doc = reader.Deserialize(file)
                file.Close()
    
                Select Case doc.DocumentElement.Name
                    Case "SpurGearRobot"
                        rbt = New SpurGearRobot
                        Dim serializer As New XmlSerializer(GetType(SpurGearRobot))
                        file = New System.IO.StreamReader(fullPath)
                        Using file
                            ' Call the Deserialize method to restore the object's state.
                            rbt = CType(serializer.Deserialize(file), SpurGearRobot)
                        End Using
    
                    Case "PositiveDisplacementRobot"
                        rbt = New PositiveDisplacementRobot
                        Dim serializer As New XmlSerializer(GetType(PositiveDisplacementRobot))
                        file = New System.IO.StreamReader(fullPath)
                        Using file
                            ' Call the Deserialize method to restore the object's state.
                            rbt = CType(serializer.Deserialize(file), PositiveDisplacementRobot)
                        End Using
                End Select
                file.Close()
                Return rbt
    Thanks,
    Eric
    --------------------------------------------------------------------------------------------------------------------
    VB.net/C# ... Visual Studio 2019
    "None of us are as smart as all of us."

  6. #6
    Super Moderator Shaggy Hiker's Avatar
    Join Date
    Aug 2002
    Location
    Idaho
    Posts
    38,988

    Re: Deserialize when I don't know the class

    If you don't care which type of serialization, you can do this with binary serialization. Every derived type can be used as its base type, so you could put a Serialize method in the base class and use that to serialize and derived class (or just a base class, if that applies). The Deserialize method would have to be Shared, because there can't be a specific instance, yet, but it will deserialize the class back to whatever derived type it was originally. Of course, it comes back as the base class, so you'd have to cast it back to the proper derived type, but that's easy enough.
    My usual boring signature: Nothing

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width