我正在尝试使用My.Settings保存经过身份验证的服务器及其信息列表,但我无法确定如何制作自定义类型。
我现在有一个名为SqlServer的类,它有以下三个字段:
Public ServerName As String
Public UserName As String
Public Password As String
每次使用SQL身份验证连接到SQL服务器时,我都希望保存该服务器和登录信息。这意味着我需要一个自定义类型,它是My.Settings中SqlServer的集合。
这是我到目前为止的代码:
Public Class SQLServerList
Inherits List(Of SQLServer)
Implements IComparable(Of SQLServer)
Public Function CompareTo(ByVal SqlServerInfo As SQLServer) As Integer Implements IComparable(Of MyProjectName.SQLServer).CompareTo
...
End Function
End Class
我是否通过继承List在正确的轨道上?我需要什么样的属性/字段才能让这个东西按照我想要的方式运行?谢谢。
答案 0 :(得分:3)
给定一个集合类,很容易让它自己序列化内容。
Imports System.IO
Imports System.Runtime.Serialization.Formatters.Binary
<Serializable>
Public Class Server
Public Property Name As String
Public Property UserName As String
Public Property Password As String
End Class
一个简单的集合类:
<Serializable>
Public Class Servers
Private myList As List(Of Server)
Public Sub New()
myList = New List(Of Server)
End Sub
Public Sub Add(svr As Server)
myList.Add(svr)
End Sub
' no reason it cant also create server objects for you
Public Sub Add(sname As String, uname As String, pw As String)
myList.Add(New Server With {.Name = sname, .UserName = uname, .Password = pw})
End Sub
'toDo Contains, Count, Item etc as needed
Public Sub Save(mypath As String)
Using fs As New FileStream(mypath, FileMode.OpenOrCreate)
Dim bf As New BinaryFormatter
bf.Serialize(fs, myList)
End Using
End Sub
Public Function Load(mypath As String) As Int32
'ToDo: check if file exists
Using fs As New FileStream(mypath, FileMode.Open)
Dim bf As New BinaryFormatter
myList = CType(bf.Deserialize(fs), List(Of Server))
End Using
If myList IsNot Nothing Then
Return myList.Count
Else
Return 0
End If
End Function
End Class
<Serializable>
需要BinaryFormatter
属性。不同的序列化器(json,ProtoBuf-NET)可能有自己的。
“魔法”位于Save
和Load
方法中,用于序列化或反序列化内部对象列表。只需几行代码即可加载/保存1或1000个项目。它是数据库中少数数据的绝佳替代品。
测试往返次数:
Dim svrs As New Servers
svrs.Add("SqlSS1", "ziggy", "foo")
svrs.Add("SqlSS2", "zacky", "bar")
svrs.Add("SqlSS3", "zoey", "baz")
svrs.Save("C:\Temp\SSvrs.bin")
' now load to a new Servers collection
' to test the round trip
Dim svrs2 As New Servers
Dim sCount = svrs2.Load("C:\Temp\SSvrs.bin")
For n = 0 To sCount - 1
Console.WriteLine("{0} {1} {2} ", svrs2(n).Name, svrs2(n).UserName, svrs2(n).Password)
Next
输出:
SqlSS1 ziggy foo
SqlSS2 zacky吧
SqlSS3 zoey baz
我使用了BinaryFormatter(没有实际原因),但ProtoBuf-NET或XMLSerializer也可以使用。由于数据都是字符串,因此您可能需要加密它们(将文件流包装在cryptuffream中)。
答案 1 :(得分:1)
如果要将您定义的某些类保存到My.Settings中,则基本上需要满足与任何XML可序列化类相同的要求。
答案 2 :(得分:0)
基准测试,将对象序列化为二进制文件,XML文件和XML字符串:
很惊讶地看到编写二进制文件比XML文件花费更长的时间。我希望.Net只是将内存转储到文件而不进行任何处理和转换。也许有比使用的更好的二进制序列化器?
虽然预计会更小。 XML文件“仅”具有100%的开销。
同样令人惊讶的是,编写XML文件比写入内存中的字符串要快。
我确定我的代码可以优化,因为它非常奇怪,随意贡献: - )
要序列化的对象:
<Serializable> _
Public Class oNames
Public Shared cNames As New List(Of oName)
<Serializable> _
Public Class oName
Public Property Firstname As String
Public Property Lastname As String
Sub New()
End Sub
End Class
Sub New()
End Sub
End Class
使用 500.000 对象填充列表:
oNames.cNames.Clear()
For i As Integer = 1 To 500000
oNames.cNames.Add(New oNames.oName With {.Firstname = "MyFirstName" & i.ToString, .Lastname = "MyLastName" & i.ToString})
Next
写入二进制文件(使用我自己的序列化程序类):
WCC.BinSerialization.ToFile(oNames.cNames, "c:\temp\ObjToBin.bin", IO.FileMode.Append)
写入XML文件(使用我自己的序列化程序类):
WCC.XMLSerialization.Obj_To_XMLFile(oNames.cNames, "c:\temp\ObjToXML.xml")
写入XML字符串(使用我自己的序列化程序类):
Dim XMLStr As String
XMLStr = WCC.XMLSerialization.Obj_To_XLMStr(oNames.cNames)
我的序列化程序类:
Public Class WCC
Public Class XMLSerialization
Public Shared Function Obj_To_XLMStr(Obj As Object) As String
Using SW As New System.IO.StringWriter
Dim X As New System.Xml.Serialization.XmlSerializer(Obj.GetType)
X.Serialize(SW, Obj)
Return SW.ToString
End Using
End Function
Public Shared Sub XMLStr_To_Obj(XMLString As String, ByRef ListObj As Object)
Using SR As New System.IO.StringReader(XMLString)
Dim X As New System.Xml.Serialization.XmlSerializer(ListObj.GetType)
ListObj = X.Deserialize(SR)
End Using
End Sub
Public Shared Sub Obj_To_XMLFile(Obj As Object, Path As String)
Dim XWS As New System.Xml.XmlWriterSettings
XWS.Indent = True
XWS.IndentChars = vbTab
Using XW As System.Xml.XmlWriter = System.Xml.XmlWriter.Create(Path, XWS)
Dim X As New System.Xml.Serialization.XmlSerializer(Obj.GetType)
X.Serialize(XW, Obj)
End Using
End Sub
End Class
Public Class BinSerialization
Public Shared Sub ToFile(Obj As Object, Path As String, FileMode As IO.FileMode)
Using fs As New System.IO.FileStream(Path, FileMode)
Dim bf As New System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
bf.Serialize(fs, Obj)
End Using
End Sub
End Class
End Class