vb.net使用reader读取,返回基于regex匹配的数据并将其放入数据结构中



我正试图将所有读取的数据返回到一个高效的数据结构中。阅读器正在完成它的工作,并从我的正则表达式中返回正确的值。现在我正试图将这些数据存储在内存中,稍后再进行解析。我想在一键点击事件中做到这一点。

Sub ReadFile()
Dim mapping As New Mapping()
Dim variable As New MappingVariable()
Dim P, line, startPosition, totalLength, id, name, number As String
Dim m As Match
Dim reader As New StreamReader("......FileName.myp", System.Text.Encoding.Default)
Do
line = reader.ReadLine
If line Is Nothing Then Continue Do
m = Regex.Match(line, "^[(w+)]")
P = m.Groups(1).ToString()
mapping.P = P
' Grab that code
If m.Groups.Count > 1 Then
' Read the next line after the code and get the 4 digits
line = reader.ReadLine
m = Regex.Match(line, "ID=ww(wwww)")
id = m.Groups(1).ToString()
mapping.id = ID
' Then keep reading until the next blank line
Do
line = reader.ReadLine
If line Is Nothing Then Continue Do
m = Regex.Match(line, ".*?(d+),(d+).*?""(.+?)"".*?(d+) .*")
If m.Groups.Count > 1 Then
startPosition = m.Groups(1).ToString()
variable.startPosition = startPosition
totalLength = m.Groups(2).ToString()
variable.totalLength = totalLength
name = m.Groups(3).ToString()
variable.name = Name
number = m.Groups(4).ToString()
variable.number = number
End If
Loop Until line = ""
End If
Loop Until line Is Nothing
Console.WriteLine($"{mapping.p} - P")
Console.WriteLine($"{mapping.id} - ID")
For Each variables As MappingVariable In mapping.Variables
Console.WriteLine($"{variable.startPosition} - startPosition")
Console.WriteLine($"{variable.totalLength} - totalLength")
Console.WriteLine($"{variable.name} - name")
Console.WriteLine($"{variable.number} - number")
reader.Close()
End Sub

按钮功能:

Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
'New code to return a mapping object in order to write the desired output.
Dim Test As New List(Of Mapping)
'The code used to call the reader
Dim Testing = New ReadFile
Testing.WriteToTempFile()
End Sub

从你的问题中还不清楚你到底想做什么,但我猜你想把它变成一个函数,以某种有意义且易于阅读的数据结构返回从文件中读取的所有数据。我还没有测试过它,但从文件中读取数据并用regex进行解析的算法看起来是正确的,所以如果你说它的这一部分是有效的,我相信你。问题是,您似乎在如何将数据作为对象存储在内存中遇到了问题。

第一步是设计一个类,该类声明数据将在内存中采用的结构。应该是什么样子取决于你的需求,我不知道这些是什么,所以我会做一些假设。希望我的例子至少能给你一个起点。

以下类别可用于保存每条Var=行的数据:

Public Class MappingVariable
Public Property StartPosition As String
Public Property TotalLength As String
Public Property Name As String
Public Property Number As String
End Class

下面的类可以用来存储整个映射(注意,它包括Variables属性,该属性被键入为我们的MappingVariable类的列表(:

Public Class Mapping
Public Property P As String
Public Property Id As String
Public Property Variables As New List(Of MappingVariable)()
End Class

现在,在代码中,您可以创建一个Mapping对象,并用读取的头数据填充它(在它开始读取Var=行之前(:

Dim mapping As New Mapping()
mapping.P = p
mapping.Id = id

然后,在读取每个Var=行的数据后,可以创建一个MappingVariable对象并将其添加到映射的Variables列表中:

Dim variable As New MappingVariable()
variable.StartPosition = startPosition
variable.TotalLength = totalLength 
variable.Name = name 
variable.Number = number 
mapping.Variables.Add(variable)

目前尚不清楚该文件是包含多个映射还是仅包含一个映射。如果它只包含一个,那么可以让函数返回一个Mapping对象。如果它可以包含多个,那么可以在填充它们之后将它们添加到列表中,然后让函数返回一个List(Of Mapping)对象。

在任何情况下,一旦您有了Mapping对象,您就可以这样写它所需的输出:

Console.WriteLine($"{mapping.P} - P")
Console.WriteLine($"{mapping.Id} - ID")
For Each(variable As MappingVariable in mapping.Variables)
Console.WriteLine($"{variable.StartPosition} - startPosition")
Console.WriteLine($"{variable.TotalLength} - totalLength")
Console.WriteLine($"{variable.Name} - name")
Console.WriteLine($"{variable.Number} - number")
Next

当然,这方面可以做各种各样的改进。例如,您可能至少应该将位置和长度属性类型化为整数,而不是字符串。您可能还希望将变量存储在字典中,并按其名称、编号或位置键入,以便更快地访问。但希望这足以让你朝着正确的方向前进。

更新

你正在到达那里,但你把东西放错了地方。请允许我修改您的代码:

Function ReadFile() As List(Of Mapping)  ' Note that I changed this to a function and I have it returning a list of mappings
Dim mappings As New List(Of Mapping)()
Dim P, line, startPosition, totalLength, id, name, number As String
Dim m As Match
Dim reader As New StreamReader("......FileName.myp", System.Text.Encoding.Default)
Do
Dim mapping As New Mapping()  ' Create a new mapping object for each one in the file rather than only creating it once at the top of the function
line = reader.ReadLine
If line Is Nothing Then Continue Do
m = Regex.Match(line, "^[(w+)]")
P = m.Groups(1).ToString()
mapping.P = P
' Grab that code
If m.Groups.Count > 1 Then
' Read the next line after the code and get the 4 digits
line = reader.ReadLine
m = Regex.Match(line, "ID=ww(wwww)")
id = m.Groups(1).ToString()
mapping.id = ID
' Then keep reading until the next blank line
Do
line = reader.ReadLine
If line Is Nothing Then Continue Do
m = Regex.Match(line, ".*?(d+),(d+).*?""(.+?)"".*?(d+) .*")
If m.Groups.Count > 1 Then
Dim variable As New MappingVariable()  ' Create a new variable object for each Var= line rather than just creating one at the top of the function
startPosition = m.Groups(1).ToString()
variable.startPosition = startPosition
totalLength = m.Groups(2).ToString()
variable.totalLength = totalLength
name = m.Groups(3).ToString()
variable.name = Name
number = m.Groups(4).ToString()
variable.number = number
mapping.Variables.Add(variable)  ' Add this populated variable to this mapping's list of variables
End If
Loop Until line = ""
mappings.Add(mapping)  ' Add this populated mapping to the list
End If
Loop Until line Is Nothing
reader.Close()
Return mappings  ' Return the list of mappings that were read from the file back to whatever was calling this function
End Function

Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
Dim mappings As List(Of Mapping) = ReadFile()
For Each mapping As Mapping in mappings
Console.WriteLine($"{mapping.p} - P")
Console.WriteLine($"{mapping.id} - ID")
For Each variables As MappingVariable In mapping.Variables
Console.WriteLine($"{variable.startPosition} - startPosition")
Console.WriteLine($"{variable.totalLength} - totalLength")
Console.WriteLine($"{variable.name} - name")
Console.WriteLine($"{variable.number} - number")
Next
Next
End Sub

最新更新