在c ++和库中使用regex_search <regex> </regex>

时间:2013-12-19 09:36:15

标签: c++ regex

我想在c ++ 11中使用regex_search成员函数。

但是,我找不到给定正则表达式的正确答案。

示例如下:

目标字符串:“abcd cd abefcd ababcddecd”

给定正则表达式:“ab。* cd” - 这个正则表达式基于POSIX扩展的gramer。

预期结果:abcd,abcd cd,abcd cd abefcd,abcd cd abefcd ababcd,abcd cd abefcd ababcddecd,                  abefcd,abefcd ababcd,abefcd ababcddecd,ababcd,ababcddecd

图书馆对我来说并不熟悉。

所以,我不知道如何在上面的例子中获得预期的结果。

源代码:

#include <regex>
#include <iostream>
using namespace std;

int main(void){
    regex re("ab.*cd", regex::extended);
    smatch m;
    string s = "abcd cd abefcd ababcddecd";

    // TO DO??

    /*
    while(regex_search(s, m, re)){
        for(auto x:m) cout << x << " ";
        cout << endl;
        s = m.suffix().str();
    }
    */
    return 0;
}

3 个答案:

答案 0 :(得分:0)

#include <regex>
#include <iostream>
using namespace std;

int main(void){
    regex e("(a.*cd)", regex::extended);
    string s = R"(abcd cd abefcd ababcddecd)";
    string match = "";
    size_t i = 0;
    while (s.size() > i)
    {
        smatch m;
        string ss = s.substr(0, i);

        regex_search(ss, m, e);
        if (m.size() > 1 && m[1] != match) {
            cout << m[1] << endl; 
            match = m[1];
        }
        i++;
    }
        cin.get();

    return 0;
}

答案 1 :(得分:0)

正则表达式中的*操作是贪婪:它会在不打破其余匹配的情况下吃掉所有可能的操作。因此,当您使用"abxxxabyyyab"搜索ab.*ab时,正则表达式与整个字符串匹配; .*匹配"xxxabyyy"。您正在寻找的是非贪婪搜索,其中*使用不会破坏匹配的最短子字符串。为此,请使用*?。当您使用"abxxxabyyyab"搜索ab.*?ab时,正则表达式与"abxxxab"匹配,.*?匹配"xxx"

答案 2 :(得分:0)

我想这个问题会导致C ++ 11中的库。

我使用库实现上述原始问题中描述的示例的短代码。

然而,我无法得到正确答案。 regex_search只返回0。

因此。我在Boost库中使用它来实现这个例子。

#include <string>
#include <map>
#include <boost/regex.hpp>
#include <iostream>
using namespace std;

int main(void){
    boost::regex e("ab.*cd", boost::regex::extended);
    std::string s("abcd cd abefcd ababcddecd");
    boost::smatch m;
    std::map<std::string, int> mm;
    // I use a map for prevent redundant duplication of matched string

    for(int i = 0; i < s.size(); i++){
        for(int j = 1; j <= (s.size() - i); j++){
            std::string ss = s.substr(i, j);
            boost::smatch m;
            if(boost::regex_search(ss, m, e)){
                int temp = mm[m[0]];
                if(temp == 0){
                    mm[m[0]] = 1; 
                    cout << "Match string: " << m[0] << endl;
                }
            }
        }
    }
}

Makefile如下:

CC = g++   

FLAG = -g
FLAG_I = -I/usr/include
FLAG_L = -L/usr/lib -lboost_regex    

OBJECTS = main.o
TARGET = main

$(Target) : $(OBJECTS)
$(CC) -o $(TARGET) $(OBJECTS) $(FLAG_L)
main.o : main.cpp
    $(CC) $(FLAG) -c main.cpp $(FLAG_I)

我在linux机器上使用这个代码得到了正确的答案,例如带有Boost库的fedora 19。

[user@localhost test]#make
g++ -g -c main.cpp -I/usr/include
g++ -o main main.o -L/usr/lib -lboost_regex
[user@localhost test]#./main
Match string: abcd
Match string: abcd cd
Match string: abcd cd abefcd
Match string: abcd cd abefcd ababcd
Match string: abcd cd abefcd ababcddecd
Match string: abefcd
Match string: abefcd ababcd
Match string: abefcd ababcddecd
Match string: ababcd
Match string: ababcddecd
Match string: abcddecd
[user@localhost test]#

末端 -