2015-02-09 56 views
3

我想从包含提供字符串的成员函数的结构向量中使用karma生成逗号分隔的字符串列表。使用成员函数从结构集合中提升精神业力

虽然我可以使用phoenix :: bind生成单个字符串输出,并且我可以从一个字符串矢量生成一个csv输出,但我正在努力结合这两种方法。

在下面的例子中,第一个规则工作正常,第二个不会编译(使用VS2013,boost 1.57),给出一个phoenix错误:“不能从'std :: vector> *'转换为'foo *' “,很明显,在这种情况下,对结构的单个实例起作用的语义行为是不正确的。是使用融合适配器的唯一答案吗?

#include <iostream> 
#include <vector> 
#include <string> 
#include <boost/spirit/include/karma.hpp> 
#include <boost/spirit/include/phoenix.hpp> 

namespace karma = boost::spirit::karma; 
namespace phx = boost::phoenix; 

struct foo 
{ 
    std::string f() const { return "bar"; } 
}; 

int main() 
{ 
    std::string output; 
    typedef std::back_insert_iterator<std::string> iterator; 
    iterator it(output); 

    // this works: 
    std::vector<std::string> svec = { "foo", "bar", "baz" }; 
    karma::rule< iterator, std::vector<std::string>() > svec_rule = karma::string % ','; 
    karma::generate(it, svec_rule, svec); 
    std::cerr << output << '\n'; 

    // but this won't compile 
    std::vector<foo> vfoo(3); 
    karma::rule< iterator, std::vector<foo>&() > vfoo_rule = karma::string[karma::_1 = phx::bind(&foo::f, karma::_val)] % ','; 
    karma::generate(it, vfoo_rule, vfoo); 
    std::cerr << output << '\n'; 
} 

回答

1

_val代表了该规则的vector<foo>。你不能很好地调用矢量上的foo::f

相反,要为foo规则(或使用attr_cast<>):

karma::rule<iterator, foo()> foo_rule = karma::string [ karma::_1 = phx::bind(&foo::f, karma::_val) ]; 
karma::generate(it, foo_rule % ',', vfoo); 

std::cerr << output << '\n'; 

打印bar,bar,bar

+0

当然它中。非常感谢,如此简单的解决方案。 – nostep 2015-02-09 15:56:22