rus*_*sbi 2 c++ regex boost boost-xpressive
我刚开始使用Boost :: xpressive并发现它是一个很棒的库...我浏览了文档并尝试使用!运算符(零或一)但它不编译(VS2008).
我想匹配一个SIP地址,它可能是也可能不是以"sip"开头的:
#include <iostream>
#include <boost/xpressive/xpressive.hpp>
using namespace boost::xpressive;
using namespace std;
int main()
{
sregex re = !"sip:" >> *(_w | '.') >> '@' >> *(_w | '.');
smatch what;
for(;;)
{
string input;
cin >> input;
if(regex_match(input, what, re))
{
cout << "match!\n";
}
}
return 0;
}`
Run Code Online (Sandbox Code Playgroud)
你刚遇到一个困扰大部分DSEL的错误.
问题在于您需要调用特定的运算符,即在您的特定语言中实际定义的运算符.但是,此运算符已存在于C++中,因此适用查找和重载分辨率的常规规则.
选择右运算符是通过ADL(Argument Dependent Lookup)完成的,这意味着运算符所应用的对象中至少有一个应该是DSEL本身的一部分.
例如,请考虑以下简单的代码段:
namespace dsel
{
class MyObject;
class MyStream;
MyStream operator<<(std::ostream&, MyObject);
}
int main(int, char*[])
{
std::cout << MyObject() << "other things here";
}
Run Code Online (Sandbox Code Playgroud)
因为表达是从左到右评估的,所以存在dsel::MyObject病毒,即dsel将在这里传播.
关于Xpressive,大多数情况下它是有效的,因为你使用特殊的"标记",Xpressive类型实例像(_w)或因为病毒效应(例如"@"起作用,因为左边的表达>>是Xpressive相关的).
你用的是:
sregex re = "sip:" >> *(_w | '.') >> '@' >> *(_w | '.');
^^^^^^ ~~ ^^^^^^^^^^^
Regular Xpressive
Run Code Online (Sandbox Code Playgroud)
它会起作用,因为由于Xpressive运营商的优先规则,右侧的论点被"污染"了.
但是这里operator!有一个最高的优先权.在这种情况下,其范围仅限于:
`!"sip:"`
Run Code Online (Sandbox Code Playgroud)
并且由于"sip:"是类型char const[5],它只调用常规operator!,它将正确地推断出它所适用的表达式true,从而计算出bool值false.
通过使用as_xpr,将转换为C-字符串转换成一个Xpressive对象,并由此带来的权利operator!从Xpressive命名空间考虑,和重载决议踢适当.
| 归档时间: |
|
| 查看次数: |
358 次 |
| 最近记录: |