【发布时间】:2023-04-03 07:39:01
【问题描述】:
我是 Boost 库的新手,遇到了一个对我来说有点复杂的问题。 我试图用上一个问题中找到的一个例子来重新表述它,这可能很适合我的问题。 (上一题是here)
#include <boost/bind.hpp>
#include <iostream>
#include <map>
#include <set>
#include <algorithm>
#include <boost/noncopyable.hpp>
#include <boost/shared_ptr.hpp>
#include <boost/enable_shared_from_this.hpp>
class Base
: public boost::enable_shared_from_this<Base>,
private boost::noncopyable
{
public:
virtual void test() = 0;
protected:
virtual void foo(int i) = 0;
};
class Derived
: public Base
{
protected:
void foo(int i)
{ std::cout << "Base: " << i << std::endl; }
std::map<int, int> data;
public:
Derived()
{
data[0] = 5;
data[1] = 6;
data[2] = 7;
}
void test()
{
std::for_each(data.begin(), data.end(),
boost::bind(&Derived::foo, shared_from_this(),
boost::bind(&std::map<int, int>::value_type::second, _1)));
}
};
typedef boost::shared_ptr<Base> Base_ptr;
int main(int, const char**)
{
std::set<Base_ptr> Bases_;
Base_ptr derived(new Derived());
Bases_.insert(derived);
derived->test();
return 0;
}
我有一个包含在集合中的基础对象和不同的派生对象(在这个例子中,只有一个)。 派生对象应该使用 boost::bind 调用他自己的受保护方法。 在真正的问题中,boost::bind 为异步操作生成了一个回调方法,这就是为什么(我认为)我需要一个 shared_ptr。 否则,使用指针 this 而不是 shared_from_this() 解决问题。
当我编译这段代码时,我收到了一个很长的错误消息(我认为这是最重要的部分):
bind_test.cpp:43:78: instantiated from here
/usr/include/boost/bind/mem_fn_template.hpp:156:53: error: pointer to member type ‘void (Derived::)(int)’ incompatible with object type ‘Base’
/usr/include/boost/bind/mem_fn_template.hpp:156:53: error: return-statement with a value, in function returning 'void'
我尝试从 enable_shared_from_this 和一些静态转换来管理更多继承:
#include <boost/bind.hpp>
#include <iostream>
#include <map>
#include <set>
#include <algorithm>
#include <boost/noncopyable.hpp>
#include <boost/shared_ptr.hpp>
#include <boost/enable_shared_from_this.hpp>
class Base
: public boost::enable_shared_from_this<Base>,
private boost::noncopyable
{
public:
virtual void test() = 0;
protected:
virtual void foo(int i) = 0;
};
class Derived
: public boost::enable_shared_from_this<Derived>,
public Base
{
protected:
void foo(int i)
{ std::cout << "Base: " << i << std::endl; }
std::map<int, int> data;
public:
Derived()
{
data[0] = 5;
data[1] = 6;
data[2] = 7;
}
void test()
{
std::for_each(data.begin(), data.end(),
boost::bind(&Derived::foo, boost::enable_shared_from_this<Derived>::shared_from_this(),
boost::bind(&std::map<int, int>::value_type::second, _1)));
}
};
typedef boost::shared_ptr<Base> Base_ptr;
int main(int, const char**)
{
std::set<Base_ptr> Bases_;
Base_ptr derived(new Derived());
Bases_.insert(derived);
derived->test();
return 0;
}
但我在运行时遇到错误:
terminate called after throwing an instance of 'boost::exception_detail::clone_impl<boost::exception_detail::error_info_injector<boost::bad_weak_ptr> >'
what(): tr1::bad_weak_ptr
可能有人知道如何管理它? 谢谢。
艾蒂安。
【问题讨论】:
-
bind声明在多个方面毫无意义。最引人注目的是,你不能像那样轻易地接触到这对的第二个成员。可以重写foo()的函数签名吗? -
从 base 和 derived 中的 enable_shared_from_this 继承可能会导致问题。我会避开那条路线。 stackoverflow.com/questions/657155/…
-
@Kerrek SB,其实这个例子真的比真正的问题还要简单。实际上,我使用 boost::bind 为名为 socket_ 的套接字上的异步操作生成回调函数: void derived::test() { socket_.async_read_some(boost::asio::buffer(buffer_), boost::bind(&Derived ::foo, shared_from_this(), boost::asio::placeholders::error, boost::asio::placeholders::bytes_transferred)); } foo 是我的回调,实际上被称为 handle_read 或 handle_write。
-
@Tom K,由于这种双重继承,我遇到了一些问题。这就是为什么我需要指定 : boost::enable_shared_from_this
::shared_from_this() 而不是 : shared_from_this() -
@Etienne:尽管如此,但这仍然不能让您不必处理地图的值为
pair<int,int>。你要么写一个小投影函数,要么让接收者接受这对……
标签: c++ inheritance boost shared-ptr boost-bind