【问题标题】:Regex lookahead or lookbehind正则表达式前瞻或后视
【发布时间】:2013-11-15 19:06:49
【问题描述】:

我正在学习如何使用正则表达式前瞻和后瞻。

我想像这样从文本中提取json值

{"html":"\n\t\t\t\t<table class=\"table\">"} 

我正在像这样在 C# 上使用正则表达式

 Regex.Match(text, "\"html\":\"([^(?<!\\\\)\"]*)").Groups[1].Value

或者

 Regex.Match(text, "\"html\":\"((?<!\\\\$)[^\"]*)").Groups[1].Value

但它根本不起作用。我可以使用 C# regex 获得这个值吗?

【问题讨论】:

  • 为什么不使用JavaScriptSerializer?为什么是正则表达式?
  • @Amadan 因为我正在学习正则表达式前瞻和后瞻。
  • lookahead 和lookbehind 被称为零长度断言。这意味着他们返回是否找到匹配项,但不返回匹配项。 regular-expressions.info/lookaround.html
  • @MikeCheel 没错!我想确保 [^"]* 不以“\”字符结尾

标签: c# regex


【解决方案1】:

有一个完全适合您的tool,这正是在这种解析 JSON 对象的情况下您所需要的。

好的,如果您正在学习 Regex,以下是您检索 JSON 数据的示例:

class Program
{
    static void Main(string[] args)
    {
        // {"html":"\n\t\t\t\t<table class=\"table\">"} 
        var s = "{\"html\":\"\n\t\t\t\t<table class=\\\"table\\\">\"}";
        Console.WriteLine("\"{0}\"", ParseJson("html", s).First());
        // You might wanna do Trim() on the string because of those \t\t\t etc.
    }
    static private IEnumerable<string> ParseJson(string key, string input)
    {
        Regex r = new Regex(@"\{\""" + key + "\""\:\""(.*?)(?<!\\)\""\}", RegexOptions.Singleline);
        return r.Matches(input).Cast<Match>().Select(T => T.Groups[1].Value);
    }
}

几点说明:

  1. 使用(?&lt;!\\) 作为否定的后向查找(来自here),用于前面没有反斜杠的双引号。
  2. 使用 RegexOptions.Singleline 作为点 (.) 字符以匹配换行符 (\r & \n)。
  3. Do not parse HTML with regex :)

【讨论】:

  • 他正在尝试学习正则表达式,但不一定要解析 JSON。
【解决方案2】:
/"html":"(?:[^"]*(\\"[^"]*(?<!\\)))*"/

        -                              opening quote
            -----    -----         -     then any number of non-quotes
                 ----              -     ... separated by an escaped quote
                          -------        ... where the non-quote string doesn't
                                              end in a backslash
                                    -    closing quote   

对于这种情况应该是一个足够好的近似值。

(我已经用标准的正则表达式方式编写了它;记得为 C# 字符串文字转义反斜杠和引号。)

【讨论】:

  • 其实我的json值很大。而且这段代码在那里不起作用。我刚刚在这里发布了 json 的开头。
  • 正如我所说,适用于这种情况。我可以想象,如果您在未转义的引号之前有一个转义的反斜杠,或者非字符串值,或者其键不是"html" 的值,它就不会起作用。这就是为什么对于真实数据,您使用比常规自动机具有更多状态的解析器,并且最好是已经编写和测试过的东西(如JavaScriptSerializer)。或者至少使用具有强大“正则表达式”的语言,例如 Perl,它实现了递归,因此不再是“常规”。
猜你喜欢
  • 1970-01-01
  • 2015-09-13
  • 2014-07-05
  • 2013-12-24
  • 1970-01-01
  • 1970-01-01
  • 2021-10-11
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多