Boost 共享指针 C++ :共享指针无法在释放时释放资源

发布于 2024-12-09 13:32:13 字数 1017 浏览 2 评论 0原文

我遇到了一个问题,我无法摆脱最后一个共享指针,而我实际上有点需要它。

所以我拥有的是一个管理器和一些工作线程。管理器保存指向不同资源的共享指针的集合。工作人员可以向管理器请求指向资源的共享指针。总会有 1 个或多个工作线程拥有指向资源的共享指针。我的最终目标是,当所有工作人员都完成资源的使用时,资源将被删除。然而,在这个方案中,管理器始终维护一个指向资源的共享指针,因此即使没有工作人员挂在共享指针上,资源也不会被删除,因为引用计数应始终至少为 1,因为经理正在抓紧它。我需要管理器保留指向引用的共享指针,以便如果任何工作人员请求共享指针,管理器将能够提供它。


编辑:创建资源时,工作人员已经拥有它。因此,在其创建时,其引用计数应该为 2(管理器拥有它,单个工作人员拥有它)。当引用计数达到 1 时(只有经理拥有),我希望将其删除。如果资源已经被删除并且工作人员来寻找它,则应重新创建该资源。


编辑2:一些代码:

SomeSharedPointer Manager::getResource(String unique_id) 
{ // if unique id exists, return its mapped shared pointer, if unique id doesn't exist, create the resource, assign it a shared pointer, and stick it in the map 
}


class Worker
{
    SomeSharedPointer my_sp;

    Worker()
    {
       String someUniqueId = "http://blah.com"
       my_sp = Manager::getResource(someUniqueId);
       // do some work on the resource
    }

    ~Worker()
    {
        my_sp.reset(); // done with resource
    }
}

I'm running into a problem where I can't get rid of the last shared pointer and I kinda need it actually.

So what I have is a manager and some worker threads. The manager keeps a collection of shared pointers to different resources. A worker may ask the manager for a shared pointer to a resource. There will always be 1 or more workers with a shared pointer to the resource. My end goal is that when all workers are done with the resource, the resource is deleted. However, in this scheme, the manager always maintains a shared pointer to the resource so even when no workers are hanging on to the shared pointer, the resource won't get deleted b/c the ref count should always be at least 1 since the manager is hanging onto it. I need the manager to hang on to a shared pointer to the reference so that if any worker comes asking for a shared pointer, the manager will be able to provide it one.


edit: When the resource is created a worker already has it. So at its creation its ref count should be two (manager has it, and a single worker has it). When the ref count hits one (only the manager has it), I would like it to be deleted. If the resource had already been deleted and a worker comes looking for it, the resource shall be recreated.


edit2: some code:

SomeSharedPointer Manager::getResource(String unique_id) 
{ // if unique id exists, return its mapped shared pointer, if unique id doesn't exist, create the resource, assign it a shared pointer, and stick it in the map 
}


class Worker
{
    SomeSharedPointer my_sp;

    Worker()
    {
       String someUniqueId = "http://blah.com"
       my_sp = Manager::getResource(someUniqueId);
       // do some work on the resource
    }

    ~Worker()
    {
        my_sp.reset(); // done with resource
    }
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

指尖上得阳光 2024-12-16 13:32:13

如果管理器不需要保留控制权,只需将其传递下去,为什么管理器要持有对象的 shared_ptr (强引用)?没有看到您的代码,看起来就像让经理持有一个 weak_ptr ,然后将其传递给工作人员,工作人员将其锁定到自己的 shared_ptr 中。这将允许经理传递推荐人而不拥有自己的推荐人。

class Worker
{
    SomeSharedPointer my_sp;

    Worker()
    {
        String someUniqueId = "http://blah.com"
        weak_ptr wp = Manager::getResource(someUniqueId);
        my_sp = wp.lock();

        // do some work on the resource
    }

    ~Worker()
    {
        //my_sp.reset(); // handled automatically, as part of how shared pointers work
    }
}

如果工作人员完成并释放资源,该资源将被销毁,并且管理器将无法再分发引用(可以在 getResource 中测试并重新加载)。这看起来不太理想,但它是您设计的一部分,因此它应该可以很好地工作。

编辑:您还可以让getResource返回共享指针,并让管理器持有弱指针,尝试锁定,在内部进行检查/重新加载,然后返回共享指针指针。由于无法直接创建weak_ptr,因此这可能会更好一些。

另一方面,您可以提供一个函数来补充为工作人员提供释放它并在管理器中进行计数检查的指针的函数。

Why is the manager holding a shared_ptr (strong reference) to the object if it doesn't need to retain control, only pass it on? Not seeing your code, it seems like having the manager hold a weak_ptr and then pass that on to the workers, who lock it into a shared_ptr on their end. That will allow the manager to pass on references without owning one of its own.

class Worker
{
    SomeSharedPointer my_sp;

    Worker()
    {
        String someUniqueId = "http://blah.com"
        weak_ptr wp = Manager::getResource(someUniqueId);
        my_sp = wp.lock();

        // do some work on the resource
    }

    ~Worker()
    {
        //my_sp.reset(); // handled automatically, as part of how shared pointers work
    }
}

If a worker finishes and releases the resource, it will be destroyed and the manager will no longer be able to hand out references (which can be tested in getResource and reloaded). This doesn't seem quite optimal, but is part of your design, so it should work like that well.

Edit: You could also have getResource return a shared pointer, and have the manager hold the weak pointer, attempt to lock, do checking/reloading internally, and then return the shared pointer. As weak_ptrs can't be directly created, that may work somewhat better.

On the other hand, you could provide a function to compliment the one providing the workers with the pointer that releases it and does count checking in the manager.

北方。的韩爷 2024-12-16 13:32:13

在管理器中使用弱指针,在工作器中使用共享指针,当工作器请求指针时,使用 lock 方法创建共享指针。

如 boost::shared_ptr fptr =weakfoo.lock();

如果共享指针为空,则该指针要么已被最后一个工作人员释放,要么尚未创建并且需要创建,

我肯定会避免任何涉及查看引用计数的解决方案......只会带来痛苦:)

Use a weak pointer in the manager and shared pointer in the workers, when a worker comes asking for the pointer create a shared pointer using the lock method.

as in boost::shared_ptr fptr = weakfoo.lock();

if shared pointer is empty, the pointer has either been released by the last worker or has not been created yet and needs creating

I would definitely avoid any solutions that involve looking at the ref count... only pain will ensue :)

爱冒险 2024-12-16 13:32:13

我认为以下几点是关键:

我需要管理器保留一个指向引用的共享指针,以便如果任何工作人员请求共享指针,管理器将能够提供一个。

您需要决定在什么时候不再有工作人员可以请求共享指针。一旦知道情况如此,主设备就可以简单地重置其共享指针的实例,从而释放引用。

I think the following is key:

I need the manager to hang on to a shared pointer to the reference so that if any worker comes asking for a shared pointer, the manager will be able to provide it one.

You need to decide at which point no more workers can come asking for the shared pointer. Once you know that's the case, the master can simply reset its instance of the shared pointer, thereby releasing the reference.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文