在引号中查找管道忽略误报

时间:2019-07-02 15:00:38

标签: c# regex

我正在尝试将引号内的竖线分隔字符替换为空格。问题是由于一些字符串为空,我得到了很多误报。我只想替换引号之间的文本。我正在使用的regex模式来自另一个stackoverflow帖子,因为我缺少regex技能。

数据示例:

"Hello"|"Green | Blue"|123.45|""|""|""|5|45

代码我正在使用:

internal class Program
{
    public static void Main()
    {
        string pattern = @"(?: (?<= "")|\G(?!^))(\s*[^"" |\s]+(?:\s +[^ 
        ""|\s]+)*)\s*\|\s*(?=[^""] * "")";
        string substitution = @"\1 \2";
        string input = @"""20190430|""Test  Text""|""""|""""|""Manual""|""""|""Machine""|""""|""""|10.00|""""|0.00|||0.00||5600.00||||""A+""|""""|40.00||""""|""Vision Service |Troubleshoot""|57|""Y""|838|""Yellow Maroon""|850||""FL""||||0.00|||||||||||""""||""""||""""|||""""||||||""""||""""|""""||""""|""""||||||""""|""""|""""||||||||1||""";
        RegexOptions options = RegexOptions.Multiline;
        Regex regex = new Regex(pattern, options);
        string result = regex.Replace(input, substitution);
        Console.WriteLine("Result:" + result);
        Console.ReadKey();
    }
}

它可以很好地替换“蓝绿色”管道。但是,稍后它还会替换引号之间的管道,这会在删除列时破坏文件。

使用正在处理的文件的实际示例更新了代码。正则表达式找到了它,但没有替换管道。缺少东西。

2 个答案:

答案 0 :(得分:3)

如果双引号之间应有文本,且文本应在管道的两侧,则可以使用:

(?<=")(\s*[^"\s|]+)\s*\|\s*([^\s"|]+\s*)(?=")

在替换中,使用$1 $2

说明

  • (?<=")向后看,断言左侧是"
  • (\s*[^"\s|]+)在组1中捕获,匹配0+次空白字符,而不是"|或空白字符1次以上
  • \s*\|\s*在0+次空白字符之间匹配|
  • ([^\s"|]+\s*)在组2中捕获匹配1次以上而不是"|或空白字符,并匹配0次以上一个空白字符
  • (?=")正向前进,断言右边是"

.NET Regex demo

enter image description here

修改

如果您想用双引号之间的空格替换多个管道,则可以使用\G锚点在上一个匹配项的末尾声明位置。

在替换中,使用第一个捕获组,后跟一个空格$1

(?:(?<=")|\G(?!^))(\s*[^"|\s]+(?:\s+[^"|\s]+)*)\s*\|\s*(?=[^"]*")

说明

  • (?:非捕获组
    • (?<=")断言左侧是"
    • |
    • \G(?!^)在上一场比赛结束时声明位置
  • )关闭非捕获组
  • (第1组
    • \s*[^"|\s]+匹配0+次空白字符,然后匹配1+次非|或空白字符
    • (?:\s+[^"|\s]+)*重复0+次匹配1+个空白字符,然后再加上1+次而不是|或空白字符
  • )关闭捕获组1
  • \s*\|\s*在0+次空白字符之间匹配|
  • (?=[^"]*")断言右边是"

查看其他.NET regex demo

enter image description here

答案 1 :(得分:0)

我的猜测是,我们可能还希望在文本和该表达式中仅保留一个空格,

"([^"]+?)\s+\|\s+([^"]+?)"
替换为$1 $2

可能有效。

Demo

示例

using System;
using System.Text.RegularExpressions;

public class Example
{
    public static void Main()
    {
        string pattern = @"""([^""]+?)\s+\|\s+([^""]+?)""";
        string substitution = @"\1 \2";
        string input = @"""Hello""|""Green | Blue""|123.45|""""|""""|""""|5|45";
        RegexOptions options = RegexOptions.Multiline;

        Regex regex = new Regex(pattern, options);
        string result = regex.Replace(input, substitution);
    }
}