gpt4 book ai didi

C++11 shared_ptr 和 pthread

转载 作者:行者123 更新时间:2023-11-30 04:54:48 29 4
gpt4 key购买 nike

我有一个库,其中的 API 使用 std::shared_ptr 作为参数。

我想将这些 API 与 pthreads 一起使用。

我正在做的是:从 shared_ptr 获取原始指针,以便将其传递给 pthread。从原始的 shared_ptr 创建一个新的 shared_ptr 并从另一个线程调用我的 API。但是,在将原始指针转换回共享指针时,我遇到了 double free or corruption 错误。

这是我的代码

#include <memory>
#include <iostream>
#include <thread>
#include <pthread.h>

void* print_task(void* ptr)
{
int* val_raw = static_cast<int*>(ptr);
std::shared_ptr<int> val(val_raw);

// CALL MY API WHICH TAKES A SHARED_PTR AS ARGUMENT
std::cout<<"thread job done \n";
}

int main(int argc, char ** argv)
{

pthread_t thread;

std::shared_ptr<int> val = std::make_shared<int>(10);
pthread_create(&thread, nullptr, &print_task, static_cast<void *>(val.get()));

std::this_thread::sleep_for(std::chrono::seconds(5));

return 0;
}

我想我在从共享指针到原始指针的所有转换中都做错了,因为使用 std::threads 的相同代码(我可以在其中直接传递 shared_ptr)有效。但是我需要设置线程优先级,因此我正在尝试使用 pthreads 来做到这一点。

您知道如何更改我的代码以便能够传递共享指针并在 pthread 中使用它吗?

最佳答案

如评论中所述,问题在于通过原始 void 指针传递共享指针,因此我暂时忽略线程部分:

// this is what we have and what we want to pass to the given function
shared_ptr<some_type> sptr;

// function to somehow pass the shared pointer to
void function(void* ptr);

// As always, when passing anything that doesn't fit into
// the raw pointer, we need to do dynamic allocation:
void* arg = new shared_ptr<some_type>(sptr);

// we can now pass this to the function as intended:
function(arg);

// Note that we give up ownership of the dynamically allocated
// shared pointer instance. Hence, the called function must
// release that object again (it takes ownership). The function
// therefore starts like this:
void function(void* ptr)
{
// convert the typeless pointer to a typed pointer again
shared_ptr<some_type>* psptr = static_cast<shared_ptr<some_type>*>(ptr);
// move the content to a new, local instance
shared_ptr<some_type> sptr = *psptr;
// release the dynamically allocated shared pointer again
delete psptr;
/// ... code using sptr here ...
}

现在,虽然这保证有效,但在某些情况下这可能不是最佳解决方案:

  • 首先,引用计数器的起伏不是免费的,尤其是因为这是以线程安全的原子方式完成的。可以避免在函数内部复制共享指针然后删除复制的指针。只需创建一个空实例并用要复制的指针交换()它。假设 swap() 是专门的,这是一个安全的选择,因为它是一个明显的优化,然后归结为交换两个原始指针。这种交换不必是线程安全的,因此速度要快得多。
  • 其次,动态分配非常昂贵。您可以通过将原始对象的地址传递给函数来避免这种情况和手动释放,但是您必须保证在函数仍在执行时不会触及该对象。尤其是线程,需要格外小心。

关于C++11 shared_ptr 和 pthread,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53401379/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com