在VB.net中将管道定界文件更改为逗号定界

时间:2018-12-21 11:09:08

标签: regex vb.net delimiter delimited

所以我有一组用管道分隔的输入,如下所示:

  

“ 787291 | 3224325523” | 37826427 | 2482472 | “ 46284729 | 46246” | 24682   | 82524 | 6846419 | 68247

我正在使用下面给出的代码将它们转换为逗号分隔:

 Dim line As String
    Dim fields As String()
    Using sw As New StreamWriter("c:\test\output.txt")
        Using tfp As New FileIO.TextFieldParser("c:\test\test.txt")
            tfp.TextFieldType = FileIO.FieldType.Delimited
            tfp.Delimiters = New String() {"|"}
            tfp.HasFieldsEnclosedInQuotes = True
            While Not tfp.EndOfData
                fields = tfp.ReadFields
                line = String.Join(",", fields)
                sw.WriteLine(line)
            End While
        End Using
    End Using

到目前为止,一切都很好。它仅考虑引号外的定界符,并将其更改为逗号定界符。但是,当我输入以下引号引起麻烦时:

  

“ 787291 | 3224325523” | 37826427 | 2482472 | “ 46284729 | 46246” | 24682   | “ 82524 | 6846419 | 68247

代码在此处提供

  

MalformeLineExcpetion

我意识到这是由于输入中的引号引起的,并且由于我就像RegEx中的一个菜鸟,所以我不能在这里使用它(或者我无法使用)。如果有人有任何想法,将不胜感激。

2 个答案:

答案 0 :(得分:1)

这是注释中描述的编码过程:

  • 读取原始输入文件的所有行,
  • 使用Regex或其他合适的方法修复错误的线路,
  • 使用TextFieldParser来解析正确的输入
  • Join()TextFieldParser使用,作为分隔符创建的输入部分
  • 将固定的,重构的输入行保存到最终输出文件中

我正在使用Wiktor Stribiżew正则表达式模式:给出问题描述后,它应该可以工作。

注意
当然,我不知道是否应该使用特定的编码。
在这里,Encoding is the default UTF-8 no-BOM 进进出出。

"FaultyInput.txt" 损坏的源文件。
"FixedInput.txt" 是包含正则表达式固定(希望)的输入行的文件。您也可以使用MemoryStream
"FixedOutput.txt" 是最终的CSV文件,其中包含逗号分隔的字段和正确的值。

这些文件都是在可执行启动路径中读取/写入的。

Dim input As List(Of String) = File.ReadAllLines("FaultyInput.txt").ToList()
For line As Integer = 0 To input.Count - 1
    input(line) = Regex.Replace(input(line), "(""\b.*?\b"")|""", "$1")
Next

File.WriteAllLines("FixedInput.txt", input)

Dim output As List(Of String) = New List(Of String)
Using tfp As New FileIO.TextFieldParser("FixedInput.txt")
    tfp.TextFieldType = FileIO.FieldType.Delimited
    tfp.Delimiters = New String() {"|"}
    tfp.HasFieldsEnclosedInQuotes = True
    While Not tfp.EndOfData
        Dim fields As String() = tfp.ReadFields
        output.Add(String.Join(",", fields))
    End While
End Using

File.WriteAllLines("FixedOutput.txt", output)
'Eventually...
'File.Delete("FixedInput.txt")

答案 1 :(得分:1)

Sub ReadMalformedCSV()
    Dim s$
    Dim pattern$ = "(?x)" + vbCrLf +
                    "\b            #word boundary" + vbCrLf +
                    "(?'num'\d+)   #any number of digits" + vbCrLf +
                    "\b            #word boundary"
    '// Use "ReadLines" as it will lazily read one line at time
    For Each line In File.ReadLines("c:\test\output.txt")
        s = String.Join(",", Regex.Matches(line, pattern).
                                   Select(Function(e) e.Groups("num").Value))
        WriteLine(s)
    Next
End Sub