VB.NET中对象的克隆 (转载+亲自实践)

来源:互联网 发布:2017淘宝现在好做吗 编辑:程序博客网 时间:2024/05/18 03:57
VB.NET中对象的克隆

侯永锋

              在3DMAX里面,做好一个物体(父物体)以后,可以选择Edit菜单中的Clone,下面有三中选项:Copy(生成一个同模样的子物体,两者的操作互不影响),Instance(父子互动,父物体的操作同样影响子物体,子物体也一样),还有一个Reference(暂不考虑)。

              在VB.NET,同样会碰到这样的问题。创建一个复杂对象(可能有很多种不同的数据类型)的实例,进行了一系列操作之后,想让一个中间变量或几个(另外的实例)保存它的状态,我们一般采取逐个变量赋值,有时候会写很长的代码:)这实际上就是上述的Copy问题。而对于Instance,很简单,新建一个实例,指向一下就可以了:

              Dim   objA     As   New   CResume     ‘Cresume是一个自定义的记录简历信息的类

然后进行初始化,比如:

              objA.Name=”AAA”

              objA.Address=”Shanghai,China”

              ……

              Dim   objB     As   New   CResume     ‘新建一个实例

              objB=objA

这样的话,objB跟objA有相同状态,值得注意的是objB改变一个Name,比如:

              objB.Name=”BBB”

而实际上,objA的Name也变为“BBB”,理由很简单。它们指向同一块内存空间。

 

下面我们重点讨论对象的Clone问题,即Copy以后的各个对象互不影响,关键是如何采用简单的方法解决我们的问题,MemoryStream和BinFormatter配合一下可以很简单的把对象克隆。

MemoryStream,我以前提到过,是支持存储区为内存的流。

BinFormatter,主要以二进制形式序列化和反序列化对象。

主要思路:

先用BinFormatter的Serialize方法,把对象存储在MemoryStream流中,(操作跟其他Stream一样),然后Deserialize反序列化,得到一个流式的数据,转化为原来对象的类型就可以了。是不是很简单?呵呵。看一下代码再说:

CResume类的代码:

 

Imports   System.IO

Imports   System.Runtime.Serialization.Formatters

<Serializable()>  Public   Class   CResume           

'注意需要引入System.IO和System.Runtime.Serialization.Formatters,否则序列化会出错
'注意类前面加上Serializable()属性,否则不可以序列化(为了下面的clone()方法)
  

        Dim   m_Name   As   String                             '姓名

        Dim   m_Address   As   String                         '地址

 

        Public   Property   Address()   As   String

                Get

                        Return   m_Address

                End   Get

                Set(ByVal   NewAddress   As   String)

                        m_Address   =   NewAddress

                End   Set

        End   Property

 

        Public   Property   Name()   As   String

                Get

                        Return   m_Name

                End   Get

                Set(ByVal   NewName   As   String)

                        m_Name   =   NewName

                End   Set

        End   Property 

  
        '其中CResume为当前类
        Public   Function   Clone()   As   CResume

                Dim   BF   As   New   Binary.BinaryFormatter()

                Dim   MS   As   New   MemoryStream()

                BF.Serialize(MS,   Me)

                MS.Position   =   0

                Return   (CType(BF.Deserialize(MS),  CResume))

        End   Function

End   Class

 

在Form里面可以这样调用

        Dim   Resume1   As   New   CResume()

          Dim   Resume2   As   New   CResume()

                Resume1.Name   =   "AAA "

                Resume1.Address   =   "Shanghai,China "

                Resume2   =   Resume1.Clone()

                Resume1.Name   =   "BBB "

                Resume1.Address   =   "Beijing,China "

                Debug.WriteLine(Resume1.Name)               ‘依然是AAA

                Debug.WriteLine(Resume1.Address)            

 

总结:主要调用了VB.NET的流和序列化技术,使得对象的克隆免去了繁琐的读写操作,也简化了代码。