使用 Boost::iostreams 两用过滤器
Using Boost::iostreams dual-use filters
我试图遵循 Boost::iostreams 文档中的有限状态过滤器示例。然而,当我去 use 过滤器时,我收到一个错误,指出 ::imbue 不可访问,因为 'boost::iostreams::detail::finite_state_filter_impl' 使用 'protected' 继承自 'my_fsm' .
很沮丧,我将我的代码复制到 boost 示例中使用的测试中。测试编译并通过。我的结论是我可能误用了由以下定义的双重用途过滤器:
typedef io::finite_state_filter my_fsm_filter;
我觉得把它推到filtered_stream上可能不太合适,但我找不到遗漏的步骤。我确定一定需要包装过滤器,但我找不到示例(尽管我确定如果我深入挖掘用于测试增强代码的代码,它必须在某处)。
这里有一些示例代码:
#include <boost/mpl/vector.hpp>
#include <libs/iostreams/example/finite_state_filter.hpp>
namespace io = boost::iostreams;
struct my_fsm : io::finite_state_machine<my_fsm> {
BOOST_IOSTREAMS_FSM(my_fsm) // define skip and push.
typedef my_fsm self;
static const int beginline = 0;
static const int skipline = 1;
static const int dataline = 2;
typedef boost::mpl::vector <
row<beginline, is<'C'>, skipline, &self::skip>,
row<beginline, is_any, dataline, &self::push>,
row<skipline, is<'\n'>, beginline, &self::skip>,
row<skipline, is_any, skipline, &self::skip>,
row<dataline, is<'\n'>, beginline, &self::push>,
row<dataline, is_any, dataline, &self::push>
> transition_table;
};
typedef io::finite_state_filter<my_fsm> my_fsm_filter;
#include <iostream>
#include <string>
#include <boost/iostreams/device/file.hpp>
#include <boost/iostreams/filtering_stream.hpp>
#include <boost/iostreams/stream.hpp>
namespace io = boost::iostreams;
int main() {
io::stream<io::file_sink> out(io::file_sink("outputfile.txt"));
io::filtering_istream in;
my_fsm_filter infsm;
in.push(my_fsm_filter());
in.push(io::file_source("inputdata.txt"));
while (in) {
std::string line;
if(std::getline(in, line)) {
//std::cout << line << std::endl;
out << line << std::endl;
}
}
return 0;
}
我个人觉得样本中有一个错误 header 关于这个 imbue 调用。
但是,您可以通过将 typedef 更改为
来解决这个问题
struct my_fsm_filter : io::finite_state_filter<my_fsm> {
using io::finite_state_filter<my_fsm>::imbue;
};
这在派生类型上显式地将 imbue
方法公开为 public。我没有查看您报告的示例程序(因为您没有 link )。但他们可能使用了类似的技巧。
在我的测试中,对 finite_state_filte.hpp
L278 进行类似的编辑以添加
using base_type::imbue;
到classfinite_state_filter
效果相同
我试图遵循 Boost::iostreams 文档中的有限状态过滤器示例。然而,当我去 use 过滤器时,我收到一个错误,指出 ::imbue 不可访问,因为 'boost::iostreams::detail::finite_state_filter_impl' 使用 'protected' 继承自 'my_fsm' .
很沮丧,我将我的代码复制到 boost 示例中使用的测试中。测试编译并通过。我的结论是我可能误用了由以下定义的双重用途过滤器:
typedef io::finite_state_filter my_fsm_filter;
我觉得把它推到filtered_stream上可能不太合适,但我找不到遗漏的步骤。我确定一定需要包装过滤器,但我找不到示例(尽管我确定如果我深入挖掘用于测试增强代码的代码,它必须在某处)。
这里有一些示例代码:
#include <boost/mpl/vector.hpp>
#include <libs/iostreams/example/finite_state_filter.hpp>
namespace io = boost::iostreams;
struct my_fsm : io::finite_state_machine<my_fsm> {
BOOST_IOSTREAMS_FSM(my_fsm) // define skip and push.
typedef my_fsm self;
static const int beginline = 0;
static const int skipline = 1;
static const int dataline = 2;
typedef boost::mpl::vector <
row<beginline, is<'C'>, skipline, &self::skip>,
row<beginline, is_any, dataline, &self::push>,
row<skipline, is<'\n'>, beginline, &self::skip>,
row<skipline, is_any, skipline, &self::skip>,
row<dataline, is<'\n'>, beginline, &self::push>,
row<dataline, is_any, dataline, &self::push>
> transition_table;
};
typedef io::finite_state_filter<my_fsm> my_fsm_filter;
#include <iostream>
#include <string>
#include <boost/iostreams/device/file.hpp>
#include <boost/iostreams/filtering_stream.hpp>
#include <boost/iostreams/stream.hpp>
namespace io = boost::iostreams;
int main() {
io::stream<io::file_sink> out(io::file_sink("outputfile.txt"));
io::filtering_istream in;
my_fsm_filter infsm;
in.push(my_fsm_filter());
in.push(io::file_source("inputdata.txt"));
while (in) {
std::string line;
if(std::getline(in, line)) {
//std::cout << line << std::endl;
out << line << std::endl;
}
}
return 0;
}
我个人觉得样本中有一个错误 header 关于这个 imbue 调用。
但是,您可以通过将 typedef 更改为
来解决这个问题struct my_fsm_filter : io::finite_state_filter<my_fsm> {
using io::finite_state_filter<my_fsm>::imbue;
};
这在派生类型上显式地将 imbue
方法公开为 public。我没有查看您报告的示例程序(因为您没有 link )。但他们可能使用了类似的技巧。
在我的测试中,对 finite_state_filte.hpp
L278 进行类似的编辑以添加
using base_type::imbue;
到classfinite_state_filter
效果相同