std :: regex构造函数抛出异常

Mar*_*som 9 c++ regex c++11

请注意,这与关于gcc的StackOverflow上的许多问题重复,我正在使用Visual Studio 2013.

这个简单的正则表达式构造抛出std::regex_error:

bool caseInsensitive = true;
char pattern[] = "\\bword\\b";
std::regex re(pattern, std::regex_constants::ECMAScript | (caseInsensitive ? std::regex_constants::icase : 0));
Run Code Online (Sandbox Code Playgroud)

what异常对象返回的实际错误不一致.通常它是一个不匹配的parethesis或支撑.为什么?

Mar*_*som 11

问题出现是因为可用的多个构造函数std::regex.跟踪构造函数显示它使用了我不想要的!

我想用这个:

explicit basic_regex(_In_z_ const _Elem *_Ptr,
    flag_type _Flags = regex_constants::ECMAScript)
Run Code Online (Sandbox Code Playgroud)

但我得到了这个:

basic_regex(_In_reads_(_Count) const _Elem *_Ptr, size_t _Count,
    flag_type _Flags = regex_constants::ECMAScript)
Run Code Online (Sandbox Code Playgroud)

标志中的三元表达式导致类型更改为int,flag_type在构造函数签名中不再匹配.因为它确实匹配,size_t所以调用构造函数.这些标志被误解为字符串的大小,当访问字符串末尾的内存时会导致未定义的行为.

问题不是Visual Studio特有的.我能够在gcc中复制它:http://ideone.com/5DjYiz

它可以通过两种方式修复.首先是参数的显式演员:

std::regex re(pattern, static_cast<std::regex::flag_type>(std::regex_constants::ECMAScript | (caseInsensitive ? std::regex_constants::icase : 0)));
Run Code Online (Sandbox Code Playgroud)

第二是避免三元表达式中的整数常量:

std::regex re(pattern, caseInsensitive ? std::regex_constants::ECMAScript | std::regex_constants::icase : std::regex_constants::ECMAScript);
Run Code Online (Sandbox Code Playgroud)


Jer*_*fin 7

我没有发现任何提议的解决方案特别引人注目或美观.我想我更喜欢这样的事情:

auto options = std::regex_constants::ECMAScript;
if (caseInsensitive) 
    options |= std::regex_constants::icase;

std::regex re(pattern, options);
Run Code Online (Sandbox Code Playgroud)

如果由于一些误导的原因,你真的坚持一行代码,我会在三元表达式中使用正确类型的值构造对象:

std::regex re(pattern, std::regex_constants::ECMAScript | (caseInsensitive ? std::regex_constants::icase : std::regex_constants::std::regex_option_type{}));
Run Code Online (Sandbox Code Playgroud)

或者,由于ECMAScript是默认值,因此您使用:

std::regex re(pattern, (caseInsensitive ? std::regex_constants::icase : std::regex_constants::ECMAScript));
Run Code Online (Sandbox Code Playgroud)

至少在我看来,第一个显然是优选的.