如何使用正则表达式匹配多个标记?

How to match multiple tokens using regular expressions?

我需要使用正则表达式来匹配特殊键和值。有个特殊情况不知道怎么办

字符串喜欢abcd/abcd。我需要匹配 / 之前的所有单词。 所以我写(.)*/,然后我发现它只匹配1个令牌(d)。更何况,即使匹配到我所需要的,我仍然不知道匹配了多少令牌。

那么正确的正则表达式应该是什么呢?实际情况比例子复杂很多,所以如果可以用正则表达式实现,我不想写tokenizer

为什么你的正则表达式不起作用

正则表达式 (.)*/ 匹配任何字符,零次或多次,后跟 /.

* 量词是 greedy,它会尽可能匹配。给定字符串"abcd/abcd",正则引擎匹配"abcd/abcd",然后匹配“/”失败,所以它回溯到"d",最后一步匹配“ /”。 () 是一个组,您只捕获最后一个字符。

如何修复

[^\/]*

这匹配任何 不是 的“/”(请注意它已转义),这正是您想要的。如果你想捕获匹配的正则表达式,你应该将它更改为 ([^\/]*),现在第一组包含你的正则表达式。

请注意,根据您使用的语言,可能有很多解决方案,不一定是正则表达式。

您正在使用的 Boost 库提供了一种将重复组捕获到 堆栈 中的方法 提供 您使用 BOOST_REGEX_MATCH_EXTRA 标志设置,否则 what 将没有名为 captures 的成员。当您使用 boost::regex_searchboost::regex_match 时,传递 boost::match_extra 标志,您将使用 (.)* 捕获所有值(匹配和捕获换行符以外的任何字符,零个或多个出现)进入堆栈,可通过 sub_match 对象的 captures 成员访问。

这是来自 official Boost site 的演示方法:

#include <boost/regex.hpp>
#include <iostream>


void print_captures(const std::string& regx, const std::string& text)
{
   boost::regex e(regx);
   boost::smatch what;
   std::cout << "Expression:  \"" << regx << "\"\n";
   std::cout << "Text:        \"" << text << "\"\n";
   if(boost::regex_match(text, what, e, boost::match_extra))
   {
      unsigned i, j;
      std::cout << "** Match found **\n   Sub-Expressions:\n";
      for(i = 0; i < what.size(); ++i)
         std::cout << "      $" << i << " = \"" << what[i] << "\"\n";
      std::cout << "   Captures:\n";
      for(i = 0; i < what.size(); ++i)
      {
         std::cout << "      $" << i << " = {";
         for(j = 0; j < what.captures(i).size(); ++j)
         {
            if(j)
               std::cout << ", ";
            else
               std::cout << " ";
            std::cout << "\"" << what.captures(i)[j] << "\"";
         }
         std::cout << " }\n";
      }
   }
   else
   {
      std::cout << "** No Match found **\n";
   }
}

int main(int , char* [])
{
   print_captures("(.*)bar|(.*)bah", "abcbar");
   return 0;
}