如何将类加载到Sub New中的当前实例中

时间:2010-08-23 13:36:22

标签: vb.net

长期潜伏者,这是第一次发布海报。

我已经编写了一个类来使用vs2008和framework 2.0来模拟vb.net中的对象。我正在将类序列化为XML文件以进行持久存储。我使用类中的方法执行此操作:

Public Sub SaveAs(ByVal filename As String)
    Dim writer As New Xml.Serialization.XmlSerializer(GetType(MyNamespace.MyClass))
    Dim file As New System.IO.StreamWriter(filename)
    writer.Serialize(file, Me)
    file.Close()
End Sub

我现在想做类似的事情,但是从文件中读取类到当前实例,如下所示:

Public Sub New(ByVal filename As String)
    Dim reader = New Xml.Serialization.XmlSerializer(GetType(MyNamespace.MyClass))
    Dim file = New System.IO.StreamReader(FullPath)
    Me = CType(reader.Deserialize(file), MyNamespace.MyClass)
End Sub

但是,我无法为“我”分配任何内容。我已经尝试创建一个临时对象来保存文件内容,然后将每个属性和字段复制到当前实例。我迭代了属性(使用Reflection),但这很快变得混乱,例如处理ReadOnly集合属性。如果我只是手动复制每个属性,我将不得不记得在将来添加属性时修改过程,这听起来像是灾难的秘诀。

我知道我可以在类外部使用单独的函数,但是许多内置的.NET类可以从文件中实例化自身,例如昏暗的bmp作为新的位图(文件名为字符串),这对我来说似乎非常直观。

那么有人可以建议如何在Sub New过程中将类加载到当前实例中吗?非常感谢任何建议。

2 个答案:

答案 0 :(得分:2)

我在类上放置了一个共享加载函数,它返回了新的反序列化对象。 e.g。

Public Class MyClass
...
Public shared Function Load(ByVal filename As String) as MyClass
    Dim reader = New Xml.Serialization.XmlSerializer(GetType(MyNamespace.MyClass)) 
    Dim file = New System.IO.StreamReader(FullPath) 
    Return CType(reader.Deserialize(file), MyNamespace.MyClass) 
End Sub 
End Class
...
Dim mine as MyClass = MyClass.Load("MyObject.Xml");

希望这有帮助

可替换地,
将您班级的数据封装在内部私人班级中 外部可见类的属性委托给内部类。 然后在内部类上进行Serialising和反序列化,然后你可以得到一个带有文件名的ctor,对内部隐藏对象进行反序列化,并将它分配给类数据存储。

答案 1 :(得分:1)

VB.Net中的“New”方法是该类的构造函数。您无法为现有实例调用它,因为该方法的整个目的是创建新实例;这不是语言的运作方式。尝试将方法命名为“ReadFrom”或“LoadFrom”。

此外,鉴于这些方法,我会尝试使用工厂模式实现它们。 ReadFrom方法将标记为Shared并返回新实例。我也会让这个方法更通用。我的主要ReadFrom()方法将接受一个开放的文本阅读器或xmlreader,甚至只是一个流,而不是文件名。然后我会有重载,将文件名转换为流进行读取并调用main方法。

当然,这假设我首先使用该模式。 .Net已经对平台内置的xml序列化提供了很好的支持。查看System.Xml.Serialization.XmlSerializer类和相关功能。