如何通过引用返回对象是可能的
How is returning an object by reference possible?
我正在阅读OpenCV教程,其中介绍了以下关于OpenCV的图像持有者类(cv::Mat)的内容:
The cv::Mat class implements reference counting and shallow copy such that when an image
is assigned to another one, the image data (that is the pixels) is not copied, and both images
will point to the same memory block. This also applies to images passed by value or returned
by value. A reference count is kept such that the memory will be released only when all of the
references to the image will be destructed.
我特别感兴趣的是说This also applies to images passed by value or returned.
的部分。当通过值传递时,如何可能指向同一个内存块?我觉得这与重载=
运算符有关。但它表示,即使返回了一个图像,它也只返回一个指向同一内存块的图像,而不会创建新的内存块。我不明白他们是怎么做到的。
但我的理解是:
假设传递值和返回图像使新图像共享相同的内存块,那么实现参考计数是有意义的。
但是,您能解释一下内存块是如何共享的吗?即使对象是按值返回或传递的?
这相对容易:在类的构造函数中,您可以分配内存,例如使用new
。如果你复制一个对象,你不会每次都分配新的内存,而是只复制指向原始内存块的指针,同时增加一个也存储在内存中的引用计数器,这样对象的每个副本都可以访问它。销毁对象将减少引用计数,并且只有在引用计数降至零时才释放分配的内存。
您只需要一个自定义的复制构造函数和赋值运算符。
这基本上就是共享指针的工作方式。
它可以像cv::Mat
一样简单,它有一个指向动态分配的内存块的共享指针。复制Mat
实例时,复制的是共享指针(增加引用计数),而不是它所指向的资源。
多个cv::Mat
可以共享相同的数据数组,但具有不同的标头。有一个计数器可以统计有多少垫子正在使用此数据阵列。当计数器到达0时,数据数组被释放。或者它将一直存在。此外,CvMat
、Mat
和IplImage
可以毫无问题地共享同一数据阵列。它们之间唯一的区别是头。
传递时如何指向同一内存块按价值?
cv::Mat结构实际上管理一个动态分配的内存位置。它只是充当一个指向该位置的指针,并携带有关矩阵属性的信息。当您通过值传递这个变量时,您只复制这个指针,动态内存不会被复制。为了深入复制cv::Mat的所有元素,有一种方法叫做copyTo()。
- 如何通过引用返回对象
- 通过switch和static_cast访问多态对象的运行时类型
- 通过构造函数创建的所有对象都具有相同的向量
- 有没有办法一次声明相同类型的多个对象,并通过一个表达式立即使用相同的右值初始化它们?
- 我们可以通过 IPC 传递具有动态管理成员的类对象吗?
- 无法通过指针访问对象的成员
- 通过 Gazebo 世界插件将静态对象附加到机器人链接
- 通过插槽和信号在不同线程中的两个qt对象之间进行通信
- push_back通过自行创建的对象获取最后一个元素的向量
- 单一实例对象是否通过线程安全返回shared_ptr
- 创建多个对象并通过构造函数传递参数
- 为什么静态本地对象可以通过指针或外部引用访问?
- 对象切片:通过按值派生为 Base - 安全还是危险?
- 如何从被传递的对象中通过引用传递 self
- 如果在C++中,具有自动存储的对象没有通过调用exit来销毁,那么在离开程序后,这些对象会发生什么
- 如果对象只能通过存储在数组中的共享指针访问,如何调用函数?
- 序列化/封送C#中的简单对象以通过网络发送,供非托管C++应用程序读取
- 通过值传递函数对象vs通过引用传递函数对象(c++)
- 序列化c++对象,通过套接字发送给Python -最好的方法
- 如何动态加载c++对象并通过包装器接口使用它们