【问题标题】:Foward declaring boost::signals2::signal<void()>前向声明 boost::signals2::signal<void()>
【发布时间】:2016-02-15 18:44:16
【问题描述】:

我正在尝试转发声明boost信号,所以在不使用信号时我不需要包含头文件。

我认为这会起作用:

namespace boost
{
namespace signals2
{
  class signal<void()>;
}
}

但得到错误“信号不是模板”

有没有办法做到这一点?

编辑: 更多信息:我正在尝试做的一个例子,主要是保留 #include 在我的大部分代码库中。

#include <memory>

/// Forward declaration here:

/// .H File
class ExampleClass
{
public:
  boost::signals2::signal<void()> & GetSignal();

protected:
  std::shared_ptr<boost::signals2::signal<void()>> _signal_pointer;
};

.CPP

#include "boost/signals2.hpp"
boost::signals2::signal<void()> & ExampleClass::GetSignal()
{
  if (!_signal_pointer)
  {
    _signal_pointer.reset(new boost::signals2::signal<void()>());
  }

  return *_signal_pointer;
}

【问题讨论】:

  • 看起来有点棘手。我想要这样做的原因是,我想要一个类,当通过标题要求提供信号时,作为参考,它可以做到。否则,我不想在使用它的许多其他类上使用数千行代码来减慢我的编译时间。

标签: c++ templates boost


【解决方案1】:

如果你添加template&lt;&gt;,你可以解决这个具体的编译器错误

namespace boost
{
namespace signals2
{
  template<typename T>
  struct signal;

  template<>
  class signal<void()>;
}
}

因为之前你可以声明template的专业化, 你应该自己声明template。然后实际上你 可以写:

namespace boost
{
namespace signals2
{
  template<typename T>
  struct signal;
}
}

因为你只使用前向声明,没有实现template, 所以没有必要专门化它。

但这并不能真正帮助你。 是的,如果您无处使用boost::signals2,编译器错误就会消失, 但是如果你使用这样的包含文件,在某个地方有“真实”boost::singals2 包括在内,您会收到有关重新声明 signal 的错误,这是因为 真正的boost::signals2::signal 接受 5-7 个模板参数,不记得确切,并且大多数都有一些默认值。

【讨论】:

  • 有诸如锁定策略之类的东西。
【解决方案2】:

Signals2 不是为“pimpl”设计的。它旨在在您的公共界面中

如果您不希望这样,请将其包装在您自己的 pimpl-wrappers 中。但你应该先问自己“为什么”。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-05-15
    • 1970-01-01
    • 2011-07-06
    • 1970-01-01
    相关资源
    最近更新 更多