C++ Boost/tr1 Regex(正则表达式)快速指南
正则表达式自Boost 1.18推出,目前已经成为C++11(tr1)的标准部分。
本文以Boost 1.39正则表达式为基础,应该广泛适用于其他版本的Boost。对namespace稍加修改,即可适用tr1标准。
0、regex对象
类似于Java中的Pattern,Boost中的正则表达式对象为:
boost::regex
常见构造方法2种:
1 2 3 4 5 |
// 1. 直接使用正则表达式的字符串构造。 boost::regex reg1("\\d{18}"); // 2. 加入参数regex_constants,这里是忽略大小写case boost::regex reg2("ok", boost::regex::icase); |
1、regex_match
首先要明确match和search的区别:
- match针对整个字符串,若整个串匹配,match返回true,否则false。
- search非针对整串,若任意部分子串匹配,search返回true,否则false。
明确了这点之后,来看regex_match的三种常见用法:
(1) 使用string字符串、regex对象直接match。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
#include <boost/regex.hpp> #include <iostream> #include <string> using namespace std; int main() { // Match the whole string // regex_match(str, regex) boost::regex pat1("(\\d{4}-){3}\\d{4}"); string card_str("1234-5678-4321-8765"); cout << boost::regex_match(card_str, pat1) << endl; cout << boost::regex_match(card_str, boost::regex("\\d{12}")) << endl; cout << "----" << endl; return 0; } |
这个简单明了:若card_str全串匹配了,返回1,否则0。
输出如下:
1 2 3 |
1 0 ---- |
(2) 使用迭代器替换string,并给regex加入参数
如下所述,我们知道string的头3个、尾3个是垃圾字符,可以用迭代器指明match工作的begin和end位置。注意的是:boost中,不提供string、begin(int)、end(int)这种参数形式。
同时,在构造regex的时候,我们给定了一个参数boost::regex::icase,表示该正则对象将忽略大小写!
1 2 3 4 5 6 7 |
// Match the whole string, define string by iterator, ignore case // regex_match(begin, end, regex, flags) string card_str2("|||1234-5678-4321-8765OK|||"); boost::regex pat2("(\\d{4}-){3}\\d{4}ok", boost::regex::icase); cout << boost::regex_match(card_str2.begin()+3, card_str2.end()-3, pat2) << endl; cout << boost::regex_match(card_str2.begin()+3, card_str2.end()-3, boost::regex("(\\d{4}-){3}\\d{4}ok")) << endl; // Case wrong cout << "----" << endl; |
输出如下:
1 2 3 |
1 0 ---- |
(3) match,并返回分组的match result
我们都知道,正则中的括号表示分组,例如:
字符串和正则:
1 2 |
boost::regex pat3("(\\d{4})-(\\d{4})-(\\d{4})-(\\d{4})"); string card_str3("1234-5678-4321-8765"); |
pat3中有4个分组,则regex_match后,match result会形成5个分组,0为全串,1~4分别为1234、5678、4321、8765。
好了,看下用法吧:
1 2 3 4 5 6 7 8 9 10 11 |
// Match the whole string, return the match part boost::regex pat3("(\\d{4})-(\\d{4})-(\\d{4})-(\\d{4})"); string card_str3("1234-5678-4321-8765"); boost::smatch mat3; cout << boost::regex_match(card_str3, mat3, pat3) << endl; cout << mat3.size() << endl; for(size_t i=0; i<mat3.size(); i++) { cout << "Match " << i << ":" << mat3[i].str() << endl; } cout << "----" << endl; |
输出如下:
1 2 3 4 5 6 7 8 |
1 5 Match 0:1234-5678-4321-8765 Match 1:1234 Match 2:5678 Match 3:4321 Match 4:8765 ---- |
这里要再多解释一下,smatch是match_result的模版特例化类型,特别针对std::string的:
1 2 3 4 5 6 7 8 9 |
class match_results; typedef match_results<const char*> cmatch; typedef match_results<const wchar_t*> wcmatch; typedef match_results<string::const_iterator> smatch; typedef match_results<wstring::const_iterator> wsmatch; |
2、regex_search
下面考虑对字符串任意部分匹配的regex_search。
您可能也喜欢如下文章: