C++ 如何使用通用函数/插槽连接到boost::signal?

C++ 如何使用通用函数/插槽连接到boost::signal?,c++,boost,boost-bind,boost-signals2,C++,Boost,Boost Bind,Boost Signals2,是否可以将具有不同签名的函数连接到需要特定签名的Boost::Signal 我有很多信号(不同的特征),从模块外部我希望能够观察到信号,而不必关心信号的特征。有可能吗 例如: float sum(float x, float y) { return x + y; } void signal_monitor(void) { //Do something } boost::signal<float (float, float)> sig; sig.connect(&

是否可以将具有不同签名的函数连接到需要特定签名的Boost::Signal

我有很多信号(不同的特征),从模块外部我希望能够观察到信号,而不必关心信号的特征。有可能吗

例如:

float sum(float x, float y)
{
  return x + y;
}

void signal_monitor(void)
{
  //Do something
}

boost::signal<float (float, float)> sig;

sig.connect(&print_sum);
sig.connect(/* How to connect to signal_monitor ?  */);

sig(5, 3);
我得到以下错误:

opt/include/boost/function/function_template.hpp: In static member function ‘static R boost::detail::function::function_obj_invoker2<FunctionObj, R, T0, T1>::invoke(boost::detail::function::function_buffer&, T0, T1) [with FunctionObj = float, R = float, T0 = float, T1 = float]’:
opt/include/boost/function/function_template.hpp:913:60:   instantiated from ‘void boost::function2<R, T1, T2>::assign_to(Functor) [with Functor = float, R = float, T0 = float, T1 = float]’
opt/include/boost/function/function_template.hpp:722:7:   instantiated from ‘boost::function2<R, T1, T2>::function2(Functor, typename boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value, int>::type) [with Functor = float, R = float, T0 = float, T1 = float, typename boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value, int>::type = int]’
opt/include/boost/function/function_template.hpp:1064:16:   instantiated from ‘boost::function<R(T0, T1)>::function(Functor, typename boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value, int>::type) [with Functor = float, R = float, T0 = float, T1 = float, typename boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value, int>::type = int]’
opt/include/boost/function/function_template.hpp:1105:5:   instantiated from ‘typename boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value, boost::function<R(T0, T1)>&>::type boost::function<R(T0, T1)>::operator=(Functor) [with Functor = float, R = float, T0 = float, T1 = float, typename boost::enable_if_c<boost::type_traits::ice_not<boost::is_integral<Functor>::value>::value, boost::function<R(T0, T1)>&>::type = boost::function<float(float, float)>&]’
opt/include/boost/signals2/detail/slot_template.hpp:156:9:   instantiated from ‘void boost::signals2::slot2<R, T1, T2, SlotFunction>::init_slot_function(const F&) [with F = float, R = float, T1 = float, T2 = float, SlotFunction = boost::function<float(float, float)>]’
opt/include/boost/signals2/detail/slot_template.hpp:81:9:   instantiated from ‘boost::signals2::slot2<R, T1, T2, SlotFunction>::slot2(const F&) [with F = float, R = float, T1 = float, T2 = float, SlotFunction = boost::function<float(float, float)>]’
../../../example/example.cpp:200:61:   instantiated from here
opt/include/boost/function/function_template.hpp:132:42: error: ‘* f’ cannot be used as a function
opt/include/boost/function/function_template.hpp:133:9: error: control reaches end of non-void function [-Werror=return-type]
cc1plus: all warnings being treated as errors
make[1]: *** [example.o] Error 1
opt/include/boost/function/function_template.hpp:在静态成员函数“static R boost::detail::function::function_obj_invoker2::invoke(boost::detail::function::function_buffer&,T0,T1)[其中FunctionObj=float,R=float,T0=float,T1=float]:
opt/include/boost/function/function_模板。hpp:913:60:从“void boost::function2::assign_to(Functor)[其中Functor=float,R=float,T0=float,T1=float]实例化”
opt/include/boost/function/function_template.hpp:722:7:从“boost::function2::function2(Functor,typename boost::enable_if_c::type)[使用Functor=float,R=float,T0=float,T1=float,typename boost::enable_if_c::type=int]'
opt/include/boost/function/function_template.hpp:1064:16:从“boost::function::function(Functor,typename boost::enable_if_c::type)[使用Functor=float,R=float,T0=float,T1=float,typename boost::enable_if_c::type=int]”实例化
opt/include/boost/function/function_template.hpp:1105:5:实例化自“typename boost::enable_if_c::type boost::function::operator=(Functor)[其中Functor=float,R=float,T0=float,T1=float,typename boost::enable_if_c::type=boost::function&]
opt/include/boost/signals2/detail/slot_模板。hpp:156:9:从“void boost::signals2::slot2::init_slot_函数(const F&)实例化[其中F=float,R=float,T1=float,T2=float,SlotFunction=boost::function]'
opt/include/boost/signals2/detail/slot_template.hpp:81:9:从“boost::signals2::slot2::slot2(const F&)[其中F=float,R=float,T1=float,T2=float,SlotFunction=boost::function]”实例化
../../../example/example.cpp:200:61:从此处实例化
opt/include/boost/function/function_模板。hpp:132:42:错误:“*f”不能用作函数
opt/include/boost/function/function_template.hpp:133:9:错误:控制到达非无效函数的末尾[-Werror=返回类型]
cc1plus:所有警告都被视为错误
生成[1]:***[example.o]错误1
非常感谢各位。

是的:

sig.connect( boost::bind( &signal_monitor ) );
Bind根本不会提出这些论点

编辑:正如Luc所提到的,由于绑定表达式不返回任何内容,这将不起作用,也许有一种不同的解决方案使用boost bind,但另一种解决方案是推出大炮,
boost::phoenix
#包括“boost/phoenix.hpp”
):

请注意额外的
()
,否则您仍将参数传递给
connect

是:

sig.connect( boost::bind( &signal_monitor ) );
Bind根本不会提出这些论点

编辑:正如Luc所提到的,由于绑定表达式不返回任何内容,这将不起作用,也许有一种不同的解决方案使用boost bind,但另一种解决方案是推出大炮,
boost::phoenix
#包括“boost/phoenix.hpp”
):


请注意额外的
()
,否则您仍然将参数传递给
connect

我希望禁止使用返回void的函数来代替返回float的函数;因为如果返回值实际用于某个对象,那么该值将是未定义的,因此程序的行为可能是不可预测的

所以我很确定,你要做的唯一方法就是创建一个具有正确签名的新函数,然后让该函数调用你的void函数并返回0。在C++11中,我认为这将起作用:

sig.connect([](float, float)->float { signal_monitor(); return 0.0f; });

我希望禁止使用返回void的函数代替返回float的函数;因为如果返回值实际用于某个对象,那么该值将是未定义的,因此程序的行为可能是不可预测的

所以我很确定,你要做的唯一方法就是创建一个具有正确签名的新函数,然后让该函数调用你的void函数并返回0。在C++11中,我认为这将起作用:

sig.connect([](float, float)->float { signal_monitor(); return 0.0f; });

还有返回类型和值的问题。感谢您的快速响应,如果我调用sig.connect((boost::phoenix::bind(&signal_monitor),1.f));//返回1.f,所有错误都是scriptic(与往常一样;)“boost/function/function_template.hpp:132:42:错误:'*f'不能用作函数”@user1574205提供的示例可以正常工作,因此需要提供更多信息。例如,一个指向错误输出和您正在使用的Boost版本的链接会有很大帮助。@LucDanton将错误添加为问题的一部分,我是这个网站的新手,因此,如果我在论坛发布etequette时破坏了任何协议,我深表歉意。@LucDanton尝试了boost::lambda::bind,它似乎编译正常。返回类型和值有问题。感谢您的快速响应,如果我调用sig.connect((boost::phoenix::bind(&signal_monitor),1.f))//返回1.f,所有错误都是scriptic(与往常一样;)“boost/function/function_template.hpp:132:42:错误:'*f'不能用作函数”@user1574205提供的示例可以正常工作,因此需要提供更多信息。例如,一个指向错误输出和您正在使用的Boost版本的链接会有很大帮助。@LucDanton将此错误添加为问题的一部分,我是这个网站的新手,因此,如果我在论坛发布etequette时违反了任何协议,我深表歉意。@LucDanton尝试了Boost::lambda::bind,它似乎编译正常。