【问题标题】:C# Regex Find all string expect in debug stringC#正则表达式在调试字符串中查找所有字符串期望
【发布时间】:2012-06-14 02:53:04
【问题描述】:

首先,我只能使用 C# 正则表达式,因此建议其他语言或非正则表达式解决方案将无济于事。现在提问。

我必须找到代码中的所有字符串(几千个文件)。基本上有6种情况:

   string a = "something"; // output" "something"
   sring b = "something else" + " more"; // output: "something else" and " more"
   Print("this should match"); // output: "this should match"
   Print("So" + "should this"); // output: "So" and "should this"
   Debug("just some bebug text"); // output: this should not match
   Debug("more " + "debug text"); // output: this should not match

正则表达式应该匹配前 4 个(我只需要引号内的内容,打印也可以是任何其他函数)

到目前为止,我有这个,它返回引号中的任何内容:

 ".*?"

【问题讨论】:

  • 我建议您使用正则表达式工具来帮助您完成作业。我使用 expresso (ultrapico.com/Expresso.htm)。
  • 你能给一些示例数据吗?或者您只想排除带有"debug" 的任何行?
  • 上面的输出应该是:“something”、“something else”、“more”、“this should match”、“So”、“should this”。我不想要的是“只是一些错误文本”、“更多”和“调试文本”

标签: c# regex regex-negation


【解决方案1】:

简而言之: @"^(?!Debug\("")([^""]*""(?<Text>[^""]*)"")*.*$"

它的作用:

  • 不匹配以Debug(" 开头的字符串
  • 沿着字符串运行,直到遇到第一个",然后越过它
    • 如果没有找到 " 并且它到达了字符串的末尾,它将停止。
  • 开始“录制”到名为Text 的组中
  • 沿着字符串运行,直到遇到下一个 ",停止录制,然后越过它。
  • 返回步骤 2

结果:您在一个名为Text 的组中拥有" 之间的所有字符串。

剩下要做的事情:将其转换为多行正则表达式,并在 Debug 之前支持 whitepsaces (\s) 作为更好的过滤器。

进一步的使用示例和测试:

var regex = new Regex(@"^(?!Debug\("")([^""]*""(?<Text>[^""]*)"")*.*$");

var inputs = new[]
                 {
                     @"string a = ""something"";",
                     @"sring b = ""something else"" + "" more"";",
                     @"Print(""this should match"");",
                     @"Print(""So"" + ""should this"");",
                     @"Debug(""just some bebug text"");",
                     @"Debug(""more "" + ""debug text"");"
                 };

foreach (var input in inputs)
{
    Console.WriteLine(input);
    Console.WriteLine("=====");

    var match = regex.Match(input);

    var captures = match.Groups["Text"].Captures;

    for (var i = 0; i < captures.Count; i++)
    {
        Console.WriteLine(captures[i].Value);
    }

    Console.WriteLine("=====");
    Console.WriteLine();
}

输出:

string a = "something";
=====
something
=====

sring b = "something else" + " more";
=====
something else
 more
=====

Print("this should match");
=====
this should match
=====

Print("So" + "should this");
=====
So
should this
=====

Debug("just some bebug text");
=====
=====

Debug("more " + "debug text");
=====
=====

【讨论】:

  • 关于您的评论,我误解了这个问题,所以我将删除我的答案。关于“仅正则表达式”部分,我将建议任何比正则表达式更简单的等效好的解决方案,因为他正在用 C# 编写提取程序。
  • @nhahtdh 完全同意,但I can only use C# regex - 听起来像家庭作业 - 无事可做。这些是 OP 的需求。
  • @YoryeNathan,感谢您的帮助。它有效,但我仍然很难将其分解为您是如何到达那里的。据我了解,^(?!Debug\(") 摆脱了Debug("([^"]*"(?&lt;Text&gt;[^"]*)")* 用于实际字符串,[^"]* 删除 ",然后 .*$ 在行尾使用 );。当我写一个正则表达式时,我使用link 来测试,而上面的正则表达式在那里仍然不起作用。我认为 ruby​​ 对正则表达式有不同的规则?
  • (?!Debug(" 去掉了以Debug(" 开头的行,但并没有真正“感动读者”——只是确保它不是以它开头然后回到开头尝试匹配字符串的其余部分。 [^"]* 是传递所有非 " 字符,然后 " 是消耗 "" 字符,所以现在我们处于文本的开头。 (?&lt;Text&gt;[^"]*) 使用所有内容,直到下一个 " 进入 Text 组,然后另一个 " 使用 ",整个最后一部分放在括号中,然后 * 允许该行中有多个文本( * 是“重复零次或多次”)。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-06-28
  • 1970-01-01
  • 2011-10-02
  • 2011-06-11
相关资源
最近更新 更多