可变参数模板参数和策略

时间:2014-01-26 18:05:50

标签: templates c++11 policy

我正在编写基于策略的日志记录系统,同时学习一些C ++作为业余爱好。似乎是一个非常经典的练习。但是我遇到了一个我无法解决的问题。

我正在使用一个可变参数模板在Sink构造中传递writerPolicy中的任何参数,因为某些策略需要一个参数。

template <class FilterPolicy, class FormatterPolicy ,class WriterPolicy, class ...Ts>
class Sink
    {
    public:
    Sink(Ts ... p_args) : m_filter(), m_formatter(), m_writer(p_args...){}

    virtual void ProcessLogEntry(const Log::LogEntry &data) ;
    private:
    FilterPolicy m_filter;
    FormatterPolicy m_formatter;
    WriterPolicy m_writer;
    }; 

当我意识到其他策略也可能需要在sink的构造函数中传递给它们的零个或多个参数时,头痛就开始了。

显然我们不能写:

Sink(T1s ... v1s, T2s ... v2s, T3s ... v3s) : m_filter(v1s...), m_formatter(v2...), m_writer(v3s...){}

但我不能理解这个模板的事情,并想出一个很好的解决方案,让Sink模板找出哪些参数与女巫政策有关。

我的目标是能够写

Sink<FilterOnLogLevelPolicy,HTMLFormatPolicy,FileWriterPolicy>(log::DEBUG,"log.html");

并让Sink将第一个参数传递给FilerOnLogLevelPolicy(在其构造函数中接受一个参数),没有传递给不带参数的HTMLFormatPolicy,第二个参数传递给构造函数中需要文件名的FileWriterPolicy。

如何吗

1 个答案:

答案 0 :(得分:3)

为什么不将建筑“外包”给客户,无论如何都是她的类型,所以她知道如何建造它们(见Dependency Injection)。

template <class FilterPolicy, class FormatterPolicy, class WriterPolicy>
class Sink
{
public:
    Sink(FilterPolicy filter,
         FormatterPolicy formatter,
         WriterPolicy writer) :
      m_filter(std::move(filter)),
      m_formatter(std::move(formatter)),
      m_writer(std::move(writer)) {}

    virtual void ProcessLogEntry(const Log::LogEntry &data);

private:
    FilterPolicy m_filter;
    FormatterPolicy m_formatter;
    WriterPolicy m_writer;
};

这会产生声明语法:

Sink<FilterOnLogLevelPolicy,HTMLFormatPolicy,FileWriterPolicy> sink(
  {log::DEBUG}, {}, {"log.html"}
);

允许用户执行她喜欢的复杂或简单的初始化。