std :: match_results :: size返回什么?

时间:2015-09-24 15:39:26

标签: c++ regex c++11

我对以下C ++ 11代码感到有点困惑:

3

我希望它打印出1,但我会得到$article->getID()。我错过了什么吗?

3 个答案:

答案 0 :(得分:9)

您获得$('#attempt1') 因为regex_search仅返回1个匹配,1将返回捕获组的数量+整个匹配值。

您的size()是......:

  

此函数填充的match_results类型的对象(例如cmatch或smatch),其中包含有关匹配结果和找到的任何子匹配的信息。

     

如果[正则表达式搜索]成功,它不是空的并且包含一系列sub_match对象:第一个sub_match元素对应于整个匹配,并且,如果正则表达式包含子表达式,则匹配(即括号分隔的组),它们相应的子匹配作为连续的sub_match元素存储在match_results对象中。

这是一个可以找到多个匹配项的代码:

matches

IDEONE demo返回#include <string> #include <iostream> #include <regex> using namespace std; int main() { string str("abcdefabcghiabc"); int i = 0; regex rgx1("abc"); smatch smtch; while (regex_search(str, smtch, rgx1)) { std::cout << i << ": " << smtch[0] << std::endl; i += 1; str = smtch.suffix().str(); } return 0; } 3次。

由于此方法会破坏输入字符串,因此这是另一种基于abc的替代方法(当您的主题是std::sregex_iterator对象时应使用std::wsregex_iterator):

std::wstring

请参阅IDEONE demo,返回

int main() {
    std::regex r("ab(c)");
    std::string s = "abcdefabcghiabc";
    for(std::sregex_iterator i = std::sregex_iterator(s.begin(), s.end(), r);
                             i != std::sregex_iterator();
                             ++i)
    {
        std::smatch m = *i;
        std::cout << "Match value: " << m.str() << " at Position " << m.position() << '\n';
        std::cout << "    Capture: " << m[1].str() << " at Position " << m.position(1) << '\n';
    }
    return 0;
}

答案 1 :(得分:3)

您缺少的是matches填充了每个捕获组的一个条目(包括整个匹配的子串作为第0个捕获)。

如果你写

std::regex needle("a(b)c");

然后,您将获得matches.size()==2matches[0]=="abc"matches[1]=="b"

答案 2 :(得分:0)

@ stribizhev的解决方案具有二次最坏情况复杂度,用于理智的正则表达式。对于疯狂的(例如“y *”),它不会终止。在某些应用程序中,这些问题可能会DoS attacks等待发生。这是一个固定版本:

string str("abcdefabcghiabc");
int i = 0;
regex rgx1("abc");
smatch smtch;
auto beg = str.cbegin();
while (regex_search(beg, str.cend(), smtch, rgx1)) {
    std::cout << i << ": " << smtch[0] << std::endl;
    i += 1;
    if ( smtch.length(0) > 0 )
        std::advance(beg, smtch.length(0));
    else if ( beg != str.cend() )
        ++beg;
    else
        break;
}

根据我个人的偏好,这将在长度为n的字符串中找到空正则表达式的n + 1个匹配项。您也可以在空匹配后退出循环。

如果要将字符串的性能与数百万条匹配进行比较,请在str的定义之后添加以下行(并且不要忘记启用优化),每个版本一次:

for (int j = 0; j < 20; ++j)
    str = str + str;