在我们的SQL Server数据库中,我们在text
字段记录中有哪些字符串,但是用随机节点写成xml,即
<Record id="5">
<account>
<OldValue>125025</OldValue>
<NewValue></NewValue>
</account>
<Amount>
<OldValue>001995</OldValue>
<NewValue></NewValue>
</Amount>
</Record id>
或
<Stock>
<Car>
<OldValue>035</OldValue>
<NewValue>038 </NewValue>
</Car>
</Stock>
我需要在字符串中使这些记录可读,例如:
ID: 5,
Account Old Value: 125025,
Account New Value: -
Amount Old Value: 001995,
Amount New Value: -
我不认为我可以serialize
字符串,因为我没有预定义的类来序列化它。我正在创建一个函数来读取我的随机xml节点,但我不确定我是否采用了正确的方法。更重要的是,目前我收到了错误:XMLException: 'id' is an unexpected token.
Public Shared Function XmlCustom(sValue As String)
Dim output As StringBuilder = New StringBuilder()
If Not String.IsNullOrEmpty(sValue) Then
Dim xmlString As String = sValue
Try
' Create an XmlReader
Using reader As XmlReader = XmlReader.Create(New StringReader(xmlString))
Dim ws As XmlWriterSettings = New XmlWriterSettings()
ws.Indent = True
Using writer As XmlWriter = XmlWriter.Create(output, ws)
' Parse the file and display each of the nodes.
While reader.Read()
Select Case reader.NodeType
Case XmlNodeType.Element
writer.WriteStartElement(reader.Name)
Case XmlNodeType.Text
writer.WriteString(reader.Value)
Case XmlNodeType.XmlDeclaration
Case XmlNodeType.ProcessingInstruction
writer.WriteProcessingInstruction(reader.Name, reader.Value)
Case XmlNodeType.Comment
writer.WriteComment(reader.Value)
Case XmlNodeType.Attribute
writer.WriteElementString("id", reader.Value)
Case XmlNodeType.EndElement
writer.WriteFullEndElement()
End Select
End While
End Using
End Using
Catch ex As Exception
MsgBox(output.ToString())
MessageBox.Show("XmlCustom - " & ex.ToString)
End Try
End If
End Function
有任何想法如何解决这个问题?
答案 0 :(得分:2)
如果没有架构,则无法使用序列化程序
由于大多数报告工具都支持DataTable
作为DataSource
的类型,因此您可以将数据从Xml字符串收集到DataTable
'Method which read elements and generate columns for DataTable and save values too
'Method recursively read every element and add elements names to Column name
Public Function ReadElement(el As XElement, columnName As StringBuilder) As IList(Of Tuple(Of DataColumn, String))
Dim temp As New List(Of Tuple(Of DataColumn, String))()
If el Is Nothing Then Return temp
columnName.Append(el.Name)
If el.HasElements = True Then
For Each child As XElement In el.Elements
temp.AddRange(ReadElement(child, columnName))
Next
Else
Dim column As New DataColumn(columnName.ToString(), GetType(String))
Dim value As String = el.Value
Dim item As New Tuple(Of DataColumn, String)(column, value)
temp.Add(item)
End If
Return temp
End Function
创建DataTable
Dim mainElement as XElement = XElement.Parse(yourXmlStringValue)
Dim data As New DataTable()
data.Columns.Add("Id", GetType(String))
'Generate schema for DataTable
Dim scheemaAndValues As New List(Of Tuple(Of DataColumn, String))()
For Each child As XElement In mainElement.Elements
Dim columnName As New StringBuilder()
scheemaAndValues.AddRange(ReadElement(child, columnName))
Next
'Add columns to DataTable
For Each arvo As Tuple(Of DataColumn, String) In scheemaAndValues
data.Columns.Add(arvo.Item1)
Next
'Add values to the row
Dim dr As DataRow = data.NewRow()
dr.SetField(Of String)("Id", mainElement.Attribute("id").Value)
For Each arvo As Tuple(Of DataColumn, String) In scheemaAndValues
dr.SetField(arvo.Item1.ColumnName, arvo.Item2)
Next
data.Rows.Add(dr)
答案 1 :(得分:0)
见下面的代码。我使用了XMLReader和XML Linq的组合。使用下面的代码,您可以获取每个元素名称,而无需担心对象的顺序。另一种选择是使用递归,如下面的C#项目:Recursion, parsing xml file with attributes into treeview c#。将C#代码转换为VB.Net非常简单。
Imports System.Xml
Imports System.Xml.Linq
Imports System.IO
Module Module1
Sub Main()
Dim xml As String = _
"<?xml version=""1.0"" encoding=""utf-8""?>" & _
"<Root>" & _
"<Child>" & _
"<SubNode1></SubNode1>" & _
"<SubNode2></SubNode2>" & _
"<SubNode3></SubNode3>" & _
"</Child>" & _
"<Child>" & _
"<SubNode1></SubNode1>" & _
"<SubNode2></SubNode2>" & _
"<SubNode3></SubNode3>" & _
"</Child>" & _
"<Child>" & _
"<SubNode1></SubNode1>" & _
"<SubNode2></SubNode2>" & _
"<SubNode3></SubNode3>" & _
"</Child>" & _
"</Root>"
Dim sReader As New StringReader(xml)
Dim reader As New XmlTextReader(sReader)
While Not reader.EOF
If reader.Name <> "Child" Then
reader.ReadToFollowing("Child")
End If
If Not reader.EOF Then
Dim child As XElement = XElement.ReadFrom(reader)
For Each element As XElement In child.Elements()
Dim name As String = element.Name.LocalName
Console.WriteLine(name)
Next
End If
End While
Console.ReadLine()
End Sub
End Module
答案 2 :(得分:-1)
它不能的原因是因为你必须有一个模式来提供描述XML数据结构的解析器。您的SQL记录应该在某处具有模式定义,以便解析器可以在读取数据之前预先加载它。
下面您将找到有关规则XML模式描述符的大量信息。
https://msdn.microsoft.com/en-us/library/ms256129(v=vs.110).aspx