所有關(guān)于在視覺基礎(chǔ)上連續(xù)化的內(nèi)容

序列化是將對象轉(zhuǎn)換為稱為a"字節(jié)流"的線性字節(jié)序列的過程;反序列化只是反轉(zhuǎn)該過程。但是為什么你想把一個(gè)對象轉(zhuǎn)換成一個(gè)字節(jié)流呢?

主要原因是你可以移動物體。考慮可能性。由于"一切都是一個(gè)對象"in.NET,您可以序列化任何內(nèi)容并將其保存到文件中。所以你可以序列化圖片,數(shù)據(jù)文件,程序模塊的當(dāng)前狀態(tài)('state'就像你的程序在一個(gè)時(shí)間點(diǎn)的快照,所以你可以暫時(shí)暫停執(zhí)行并稍后再次開始)。。。無論你需要做什么。

您還可以將這些對象存儲在磁盤上的文件中,通過web將它們發(fā)送到不同的程序,保留備份副本以確保安全或安全??赡苄詫?shí)際上是無止境的。

為什么序列化是.NET和Visual Basic中的關(guān)鍵過程。以下是通過實(shí)現(xiàn)ISerializable接口并編碼aNew和aGetObjectData子例程進(jìn)行自定義序列化的部分。

作為序列化的第一個(gè)例子,讓'做一個(gè)最簡單的程序,但也是最有用的程序之一:對數(shù)據(jù)進(jìn)行序列化,然后在文件中和文件中對簡單類中的數(shù)據(jù)進(jìn)行反序列化。在這個(gè)例子中,數(shù)據(jù)不僅被序列化,而且數(shù)據(jù)的結(jié)構(gòu)也被保存。這里的結(jié)構(gòu)是在一個(gè)模塊中聲明的,以保留東西。。。好。。。結(jié)構(gòu)化的。

模塊SerializeParms
Public Class ParmExample
Public Parm1 Name As String="Parm1 Name"
Public Parm1Value As Integer=12345
Public Parm2Name As String
Public Parm2Value As Decimal
End Class
End Module

然后,可以將單個(gè)值保存到這樣的文件中:

進(jìn)口System.Runtime.Serialization.格式。二進(jìn)制
進(jìn)口系統(tǒng)
公共類Form1
私有子mySerializeè點(diǎn)擊(
ByVal發(fā)送者為系統(tǒng)。對象,
ByVal e為System.EventArgs)
手柄mySerialize。點(diǎn)擊
Dim ParmData作為新的ParmExample
ParmData.Parm2Name="Parm2名稱"
ParmData.parm2值=54321.12345
Dim s作為新文件流("ParmInfo",F(xiàn)ileMode.Create)
Dim f作為新的二進(jìn)制格式器
f.Serialize(s,ParmData)
s.Close()
End Sub
End Class

這些相同的值可以這樣檢索:

進(jìn)口System.Runtime.Serialization.格式。二進(jìn)制
進(jìn)口系統(tǒng)
Public Class Form1
Private Sub-myDeserializeèClick(U74>ByVal sender As系統(tǒng)。對象,
ByVal e為System.EventArgs)
手柄myDeserialize。點(diǎn)擊
Dim s=新文件流("ParmInfo",F(xiàn)ileMode.Open)
Dim f As New BinaryFormatter
Dim RESORTEDPARMs As New PARMEXAPLE
RESORTEDPARMs=f.Deserialize(s)
s.Close()
Console.WriteLine(RestoredParms.Parm1Name)
Console.WriteLine(RestoredParms.Parm1Value)
Console.WriteLine(RestoredParms.Parm2Name)
Console.WriteLine(RestoredParms.parm2值)
結(jié)束Sub
End Class

結(jié)構(gòu)或集合(例如ArrayList)而不是也可以以相同方式序列化到文件。

現(xiàn)小班健康知識在我們已經(jīng)完成了基本的串行化過程,讓我們看看下一頁過程的一部分的具體細(xì)節(jié)。

關(guān)于此示例,您應(yīng)該注意的第一件事是Class中的屬性。屬性只是更多可以提供的信息VB.NET關(guān)于一個(gè)對象,他們'重新用于許多不同的事情。這個(gè)代碼中的屬性告訴VB.NET要添加額外的代碼,以便以后可以序列化此類中的所有內(nèi)容。

如果y類中有特定項(xiàng)目oudon't要序列化,可以使用屬性排除它們:

Public Parm3Value As String="any"

在示例中,請注意,SerializeDeserializeBinaryFormatter對象的方法(在此示例中為f)。

f.Serialize(s,ParmData)

該對象采用FileStream對象并將該對象序列化為參數(shù)。我們'將會看到VB.NET提供了另一個(gè)允許將結(jié)果表示為XML的對象。

最后一點(diǎn)需要注意的是,如果您的對象包含其他從屬對象,它們'也將被序列化!但是由于所有序列化對象必須標(biāo)記為屬性,因此所有這些子對象都必須標(biāo)記為也是如此。

為了完全清楚您的程序中發(fā)生了什么,您可能需要在記事本中顯示名為ParmData的文件,以查看序列化數(shù)據(jù)的外觀。(如果您遵循此代碼,則應(yīng)在bin.Debug項(xiàng)目中的文件夾。)由于這是一個(gè)二進(jìn)制文件,因此大部分內(nèi)容都是't可讀文本,但您應(yīng)該能夠在序列化文件中看到任何字符串。我們'接下來做一個(gè)XML版本,你可能想比較兩者,只是為了意識到差異。

串行化為XML而不是二進(jìn)制文件需要很少的更改。XML isn't速度快,可以't捕獲一些對象信息,但它'更靈活。XML可以被**世界上任何其他軟件技術(shù)所使用。如果您想確保您的文件結(jié)構(gòu)不為't&##34;將您綁定到"Microsoft,這是一個(gè)很好的選擇。Microsoft強(qiáng)調(diào)"LINQ到XML"創(chuàng)建XML數(shù)據(jù)文件采用最新技術(shù),但許多人仍然喜歡這種方法。

XML中的'X'表示eX可伸縮。在我們的XML示例中,我們'將使用XML的這些擴(kuò)展之一,這是一種稱為SOAP的技術(shù)。這用于表示"簡單對象訪問協(xié)議"但現(xiàn)在它'只是一個(gè)名稱。(SOAP升級得太多,原始名稱不再適用了。)

我們必須在子程序中更改的主要內(nèi)容是序列化格式符的刪除。這必須在序列化對象的子程序和再次反序列化對象的子程序中進(jìn)行更改。對于默認(rèn)配置,這涉及對程序的三個(gè)更改。首先,您必須添加對該項(xiàng)目的引用。右鍵單擊該項(xiàng)目,然后選擇添加引用…。確保。。。

System.Runtime.Serialization.Formatters.Soap

... 已添加到該項(xiàng)目中。

然后更改引用它的程序中的兩個(gè)語句。

進(jìn)口System.Runtime.Serialization.Formatters.Soap

Dim f作為新的SOAPformater

這次,如果您在記事本中選中相同的ParmData文件,則可以看到整個(gè)內(nèi)容都是可讀的XML文本,例如。。。

Parm1 Name


12345


Parm2 Name


54321.12345

那里還有很多額外的XML,文件中的SOAP標(biāo)準(zhǔn)也需要'。如果要驗(yàn)證屬性的作用,可以使用該屬性添加變量并查看文件以驗(yàn)證它是否包含's。

我們剛剛編碼的示例僅對數(shù)據(jù)進(jìn)行序列化,但假設(shè)您需要控制數(shù)據(jù)的序列化方式。VB.NET也可以這樣做!

要做到這一點(diǎn),您需要更深入地了解序列化的概念。VB.NET有一個(gè)新對象可以在這里幫助:SerializationInfo。盡管您可以對自定義序列化行為進(jìn)行編碼,但它需要額外的編碼成本。

下面顯示了基本的extra代碼。請記住,使用此類代替前面示例中顯示的ParmExample類。這是一個(gè)完整的例子。目的是向您顯示自定義序列化所需的新代碼。

進(jìn)口System.Runtime.Serialization

Public Class CustomSerialization
實(shí)現(xiàn)ISerializable
'此處序列化的數(shù)據(jù)
'Public Serializable變量為Type
Public Sub New()
'創(chuàng)建類
'時(shí)的默認(rèn)生成器-自定義代碼可以
'這里也添加了
End Sub
Public Sub New(U
ByVal info As SerializationInfo,U
ByVal context As StreamingContext)
'從
'初始化您的程序變量;串行數(shù)據(jù)存儲
End Sub
Public Sub GetObjectData(U268>ByVal info As SerializationInfo,_
ByVal上下文作為精簡上下文)
實(shí)現(xiàn)ISerializable.GetObjectData
'更新序列化數(shù)據(jù)存儲
'從程序變量
End Sub
End Class

這個(gè)想法是,現(xiàn)在你可以(實(shí)際上你必須)在NewGetObjectData中的序列化數(shù)據(jù)存儲中完成所有數(shù)據(jù)的更新和讀取>子程序。您還必須包含一個(gè)通用的New生成器(無參數(shù)列表),因?yàn)槟?重新實(shí)現(xiàn)接口。

班級通常會有正式的公關(guān)以及編碼的操作和方法。。。

'通用屬性
私有NewProperty value為String
Public-Property NewProperty()為String
Get
返回newPropertyValue
End Get
Set(ByVal-value為String)
newPropertyValue=value
End Set
End-Property

'通用方法
Public-Sub-MyMethod()
'方法代碼
End Sub

生成的序列化類可以根據(jù)您提供的代碼在文件中創(chuàng)建**值。例如,房地產(chǎn)類可能會更新房屋的價(jià)值和地址,但該類也會序列化計(jì)算出的市場分類。

317>

New子例程看起來像這樣:

Public Sub-New(U327>ByVal-info為SerializationInfo,U
ByVal-context為StreamingContext)
'將程序變量初始化為
'串行數(shù)據(jù)存儲
Parm1Name=info.GetString("a")
Parm1Value=info.GetInt32("b")
'新子繼續(xù)…

當(dāng)在BinaryFormatter對象上調(diào)用Deserialize時(shí),將執(zhí)行此子并將SerializationInfo對象傳遞給New子例程。然后,New可以對序列化的數(shù)據(jù)值做任何必要的事情。例如。。。

MsgBox("這是Parm1Value乘以Pi:">&(Parm1Value*數(shù)學(xué))ToString)

當(dāng)調(diào)用Serialize時(shí)發(fā)生相反的情況,但是BinaryFormatter對象調(diào)用GetObjectData

Public Sub-GetObjectData(
ByVal info As SerializationInfo,
ByVal context As StreamingContext)
實(shí)現(xiàn)ISerializable.GetObjectData
'如果Parm2Name=",則從程序變量
更新序列化數(shù)據(jù)存儲
'測試"然后
info.AddVvalue("a","這是一個(gè)測試。")
其他
info.AddValue("a","這次沒有測試。")
如果
結(jié)束info.AddValue("b",2)

請注意,數(shù)據(jù)作為名稱/值對添加到序列化文件中。

我在撰寫本文時(shí)發(fā)現(xiàn)的許多網(wǎng)頁都有實(shí)際的工作代碼。人們想知道作者有時(shí)在撰寫文章之前是否實(shí)際執(zhí)行了任何代碼。