【问题标题】:c++ regex extract all substrings using regex_search()c++ 正则表达式使用 regex_search() 提取所有子字符串
【发布时间】:2017-05-15 20:48:27
【问题描述】:

我是 C++ 正则表达式的新手。我有一个字符串“{1,2,3}”,我想提取数字 1 2 3。我想我应该使用 regex_search 但它失败了。

#include<iostream>
#include<regex>
#include<string>
using namespace std;
int main()
{
        string s1("{1,2,3}");
        string s2("{}");
        smatch sm;
        regex e(R"(\d+)");
        cout << s1 << endl;
        if (regex_search(s1,sm,e)){
                cout << "size: " << sm.size() << endl;
                for (int i = 0 ; i < sm.size(); ++i){
                        cout << "the " << i+1 << "th match" <<": "<< sm[i] <<  endl;
                }
        }
}

结果:

{1,2,3}
size: 1
the 1th match: 1

【问题讨论】:

  • 您可能希望将regex_match() 与描述此格式的适当表达式一起使用。

标签: c++ regex


【解决方案1】:

std::regex_search 仅在找到第一个匹配项后返回。

std::smatch 为您提供的是正则表达式中的所有匹配组。您的正则表达式仅包含一组,因此 std::smatch 中仅包含一项。

如果您想查找所有匹配项,您需要使用std::sregex_iterator

int main()
{
    std::string s1("{1,2,3}");
    std::regex e(R"(\d+)");

    std::cout << s1 << std::endl;

    std::sregex_iterator iter(s1.begin(), s1.end(), e);
    std::sregex_iterator end;

    while(iter != end)
    {
        std::cout << "size: " << iter->size() << std::endl;

        for(unsigned i = 0; i < iter->size(); ++i)
        {
            std::cout << "the " << i + 1 << "th match" << ": " << (*iter)[i] << std::endl;
        }
        ++iter;
    }
}

输出:

{1,2,3}
size: 1
the 1th match: 1
size: 1
the 1th match: 2
size: 1
the 1th match: 3

end 迭代器是按设计默认构造的,因此当iter 匹配不足时,它等于iter。注意在循环的底部我做++iter。这会将iter 移动到下一场比赛。当没有更多匹配时,iter 与默认构造的end 具有相同的值。

另一个显示子匹配(捕获组)的示例:

int main()
{
    std::string s1("{1,2,3}{4,5,6}{7,8,9}");
    std::regex e(R"~((\d+),(\d+),(\d+))~");

    std::cout << s1 << std::endl;

    std::sregex_iterator iter(s1.begin(), s1.end(), e);
    std::sregex_iterator end;

    while(iter != end)
    {
        std::cout << "size: " << iter->size() << std::endl;

        std::cout << "expression match #" << 0 << ": " << (*iter)[0] << std::endl;
        for(unsigned i = 1; i < iter->size(); ++i)
        {
            std::cout << "capture submatch #" << i << ": " << (*iter)[i] << std::endl;
        }
        ++iter;
    }
}

输出:

{1,2,3}{4,5,6}{7,8,9}
size: 4
expression match #0: 1,2,3
capture submatch #1: 1
capture submatch #2: 2
capture submatch #3: 3
size: 4
expression match #0: 4,5,6
capture submatch #1: 4
capture submatch #2: 5
capture submatch #3: 6
size: 4
expression match #0: 7,8,9
capture submatch #1: 7
capture submatch #2: 8
capture submatch #3: 9

【讨论】:

  • 谢谢。我能问一下“结束”是为了什么吗?看起来你没有初始化它。 std::sregex_iterator 结束;
  • @daydayup end 迭代器是由设计默认构造的,因此当iter 匹配不足时,它等于iter。注意在循环的底部我做++iter。这会将iter 移动到下一场比赛。当没有更多匹配时,iter 与默认构造的end 具有相同的值。我添加了另一个示例来显示子匹配。
猜你喜欢
  • 1970-01-01
  • 2023-04-06
  • 1970-01-01
  • 1970-01-01
  • 2017-11-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-12-29
相关资源
最近更新 更多