Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/node.js/33.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 将解引用智能指针的地址传递给需要原始指针的函数_C++_Smart Pointers - Fatal编程技术网

C++ 将解引用智能指针的地址传递给需要原始指针的函数

C++ 将解引用智能指针的地址传递给需要原始指针的函数,c++,smart-pointers,C++,Smart Pointers,(假设我使用的库或框架期望使用原始指针,) 使用拥有某些数据的智能指针,然后将解除防护的智能指针的地址传递给需要原始指针的函数,这是有效的做法吗?只要函数不希望获得数据的所有权,就可以 事实上,这也是您应该如何设计自己的函数:在接口中使用智能指针,当且仅当它应该参与指针对象的所有权时。是的,这是有效的做法。std智能指针有一个get()成员函数正好用于此目的 通常,当您通过智能指针管理对象时,当这些函数暗示所有权语义时,您只应将整个智能指针对象原样传递给其他函数:如果函数将复制std::shar

(假设我使用的库或框架期望使用原始指针,)


使用拥有某些数据的智能指针,然后将解除防护的智能指针的地址传递给需要原始指针的函数,这是有效的做法吗?

只要函数不希望获得数据的所有权,就可以


事实上,这也是您应该如何设计自己的函数:在接口中使用智能指针,当且仅当它应该参与指针对象的所有权时。

是的,这是有效的做法。
std
智能指针有一个
get()
成员函数正好用于此目的

通常,当您通过智能指针管理对象时,当这些函数暗示所有权语义时,您只应将整个智能指针对象原样传递给其他函数:如果函数将复制
std::shared_ptr
,则应按值接受它。类似于
std::unique\u ptr
。更常见的情况是,函数与所有权无关,它只想对传递给它的数据和/或行为进行操作。然后,您的第一个选择应该是获取(
const
-qualified)引用,因为它没有额外的
nullptr
-state指针。否则,指针就可以了

长话短说:如果您处理的API接受原始指针,但没有对其执行任何与所有权相关的操作(删除它,复制指针对象),那么可以将
.get()
传递给它

使用拥有某些数据的智能指针,然后将解除防护的智能指针的地址传递给需要原始指针的函数,这是否有效

是的,这可能是一种有效的做法。。。只要该函数没有获得原始指针的所有权。但是,重要的是要注意传递的指针将使用多长时间。智能指针的生存期必须匹配或超过该指针的使用寿命


如果函数确实拥有所有权,那么从智能指针传递地址
release
d可能是一种有效的做法,但前提是删除程序与框架将对指针执行的操作相匹配。

以上答案是正确的,我只想添加一个小问题:当涉及线程执行时。然后,您应该特别小心使用原始指针的函数,因为它们在执行时可能会变得无效,而另一个堆栈已经释放了它们

在设计自己的线程化函数时,最好使用
std::shared_ptr
,即使该函数可以使用原始指针

struct foo = {...};
void testfoo(foo* msg)
{
}

if (1)    
{
shared<foo> f = std::make_shared<foo>(...);
std::thread t(testfoo,f.get());
t.detach();
}  // whops. f destructed perhaps before testfoo could manipulate it
structfoo={…};
void testfoo(foo*msg)
{
}
如果(1)
{
共享f=std::使_共享(…);
std::线程t(testfoo,f.get());
t、 分离();
}//哇。f可能在testfoo操作它之前就被破坏了
更好:

void testfoo(std::shared_ptr<foo> msg)
{
}

if (1)    
{
shared<foo> f = std::make_shared<foo>(...);
std::thread t(testfoo,f);
t.detach();
} // f has been copied, so no pointer release
void testfoo(std::shared_ptr msg)
{
}
如果(1)
{
共享f=std::使_共享(…);
标准:螺纹t(testfoo,f);
t、 分离();
}//f已被复制,因此没有释放指针

这就是为什么智能指针有一个
运算符T*
。你不应该自己带地址。@Botje他们(编辑:我指的是标准地址)不需要。但它们确实有一个
get()
成员函数。@Quentin Microsoft的函数(如
CComPtr
)有。@Evg的确,我的心思都放在了标准智能指针上。@Quentin一定是有问题的。谢谢要是每个人都能坚持下去就好了。不幸的是,作为参数的原始指针并不一定表示函数不参与ownership@idclev463035818然后,行为不好的函数应该在其文档中提到它,并进行包装以确保正确的所有权语义。实际上,如果您不打算拥有智能指针,那么使用智能指针是非常糟糕的行为。这种行为在不需要时浪费时间增加引用计数。实际上,它并不要求函数本身必须这样做。在带有lambda作为包装器的
std::thread
中使用函数(按值捕获
std::shared_ptr
)也可以。Win32回调和
std::shared_ptr
?;-)