boost :: regex_replace中两个参数格式函数的问题

时间:2011-01-30 03:25:08

标签: c++ regex templates boost-regex

我在boost::regex_replace中遇到格式化功能问题。我可以调用它的一个参数版本,但不能调用两个参数:

e = "(^|>)([^<>]+)";
h_str = regex_replace(h_str, e, repl_quot, boost::match_default);

repl_quot定义为

std::string const &repl_quot(boost::smatch const &what) {
    boost::regex e("\"");
    std::string  repl("&#34;");
    static std::string;
    str = regex_replace(what[0].str(), e, repl, boost::match_default);
    return str;
}

上面的工作,但我真的不想使用那个静态变量,所以我尝试了我认为是可接受的两个参数的替代版本:

std::string const &repl_quot2(boost::smatch const &what, std::string &out) {
    boost::regex e("\"");
    std::string  repl("&#34;");
    out = regex_replace(what[0].str(), e, repl, boost::match_default);
    return out;
}

但是regex_replace不接受这个(一个错综复杂的编译器错误)。我正在尝试使用基于Boost::Regex文档中的以下两个参数版本:

  

模板basic_string   regex_replace(常量   basic_string的&安培; S,                                     const basic_regex&amp; E,                                     格式化程序fmt,                                     match_flag_type flags =   了match_default);

     

需要Formatter类型必须是   或者......一元,二元或三元函子   从a计算替换字符串   函数调用:fmt(what)哪个   必须返回char_type的容器   用作替换文本,或   fmt(what,out)或fmt(what,   out,flags),两者都写   替换文本到* out,然后   返回新的OutputIterator   位置。在每种情况下是什么   match_results表示的对象   找到了匹配。

已经多次请求编译器错误消息,所以这里(小心你要求的):

  

c:\ boost \ boost \ regex \ v4 \ regex_format.hpp在成员函数`OutputIter boost :: re_detail :: format_functor_container :: operator()(const Match&amp;,OutputIter,boost :: regex_constants :: match_flag_type,const Traits&amp;)[with OutputIter = boost :: re_detail :: string_out_iterator,std :: allocator&gt; &gt;,Container = const std :: string&amp;(*)(const boost :: smatch&amp;,std :: string&amp;),Match = boost :: match_results&lt; __ gnu_cxx :: __ normal_iterator,std :: allocator&gt; &gt;,std :: allocator,std :: allocator&gt; &GT; &GT; &GT; &gt;,Traits = boost :: regex_traits_wrapper&gt; &GT;]':

     

356 c:\ boost \ boost \ regex \ v4 \ match_results.hpp从`OutputIterator boost :: match_results :: format(OutputIterator,Functor,boost :: regex_constants :: match_flag_type,const RegexT&amp;)const [与OutputIterator]实例化= boost :: re_detail :: string_out_iterator,std :: allocator&gt; &gt;,Functor = const std :: string&amp;(*)(const boost :: smatch&amp;,std :: string&amp;),RegexT = boost :: basic_regex&gt; &gt;,BidiIterator = __gnu_cxx :: __ normal_iterator,std :: allocator&gt; &gt;,Allocator = std :: allocator,std :: allocator&gt; &GT; &GT; &GT;]'

     

60 c:\ boost \ boost \ regex \ v4 \ regex_replace.hpp从`OutputIterator boost :: regex_replace(OutputIterator,BidirectionalIterator,BidirectionalIterator,const boost :: basic_regex&amp;,Formatter,boost :: regex_constants :: match_flag_type)实例化[使用OutputIterator = boost :: re_detail :: string_out_iterator,std :: allocator&gt; &gt;,BidirectionalIterator = __gnu_cxx :: __ normal_iterator,std :: allocator&gt; &gt;,traits = boost :: regex_traits&gt;,charT = char,Formatter = const std :: string&amp;(*)(const boost :: smatch&amp;,std :: string&amp;)]'

     

80 c:\ boost \ boost \ regex \ v4 \ regex_replace.hpp从`std :: basic_string,std :: allocator&lt; _T2&gt;实例化&GT; boost :: regex_replace(const std :: basic_string,std :: allocator&lt; _T2&gt;&gt;&amp;,const boost :: basic_regex&amp;,Formatter,boost :: regex_constants :: match_flag_type)[with traits = boost :: regex_traits&gt; ,charT = char,Formatter = const std :: string&amp;(*)(const boost :: smatch&amp;,std :: string&amp;)]'

     

327 C:\ Dev-Cpp \ Examples \ wordrad \ xhtml_open.cpp从这里实例化

     

1064 c:\ boost \ boost \ regex \ v4 \ regex_format.hpp请求成员begin' in((boost :: re_detail :: format_functor_container,std :: allocator&gt;&gt;,std :: allocator, std :: allocator&gt;&gt;&gt;&gt;&gt;,boost :: regex_traits_wrapper&gt;&gt;&gt; *)this) - &gt; boost :: re_detail :: format_functor_container,std :: allocator&gt; &gt;,std :: allocator,std :: allocator&gt; &GT; &GT; &GT; &gt;,boost :: regex_traits_wrapper&gt; &GT; &gt; :: func',它是非类型的`const std :: string&amp;(* const)(const boost :: smatch&amp;,std :: string&amp;)'

     

1064 c:\ boost \ boost \ regex \ v4 \ regex_format.hpp请求成员end' in((boost :: re_detail :: format_functor_container,std :: allocator&gt;&gt;,std :: allocator, std :: allocator&gt;&gt;&gt;&gt;&gt;,boost :: regex_traits_wrapper&gt;&gt;&gt; *)this) - &gt; boost :: re_detail :: format_functor_container,std :: allocator&gt; &gt;,std :: allocator,std :: allocator&gt; &GT; &GT; &GT; &gt;,boost :: regex_traits_wrapper&gt; &GT; &gt; :: func',它是非类型的`const std :: string&amp;(* const)(const boost :: smatch&amp;,std :: string&amp;)'

1 个答案:

答案 0 :(得分:1)

好的,这就是我必须写的repl_quot2:

struct formatter
{       
  template<typename Out>
  Out operator()(boost::smatch const &what, Out out) const {
    boost::regex e("\"");    
    std::string  repl("&#34;");
    std::string str
      = regex_replace(what[0].str(), e, repl, boost::match_default);
    out = std::copy(str.begin(), str.end(), out);
    return out;
  }

};

然后从regex_replace调用它时:

  e = "(^|>)[^<>]+";
  formatter repl_quot2;
  h_str = regex_replace(h_str, e, repl_quot2, boost::match_default);

这与http://boost-sandbox.sourceforge.net/libs/xpressive/doc/html/boost_xpressive/user_s_guide/string_substitutions.html上的文档相对应。

目前令我困惑的是,如果调用了两个参数版本,它需要一个仿函数(带有()运算符的类而不是函数,但是对于一个参数版本不需要仿函数(repl_quot)在OP)。无论如何,没有得到新的两个parm版本作为一个直接的功能。但主要的问题是out我必须传递并作为模板参数返回,如图所示,而不是像在OP中那样使它成为std :: string。它应该是一个OutputIterator - 但实际上并不知道它是什么。

顺便说一下,所有这个正则表达式都是用html实体版本替换双引号, \&安培;#34;在html中的任何文本中都不是标记的一部分。

另外,我想替换原始函数repl_quot的原因是我必须将返回值存储在repl_quot中的静态局部变量中。它只能返回一个普通的局部变量,因为它甚至可以在被使用之前被解除分配(并导致崩溃)。 repl_quot正在工作 - 我的静态问题是它不是线程安全的,并且不知道Boost :: RegEx是否是多线程的。我想我把它编译为多线程,但静态var似乎没有引起问题。但是使用repl_quot2我将返回值写入输出参数。