new 新建一个对象,它的所有成员也是在堆上的吧?

王桑的一天 2020-09-09 09:26:34

class A : public QObject
{
Q_OBJECT

public:
A(QObject *parent=nullptr);
~A();

private:
QMap<QString, QVariant> mmap;
QMap<QString, QObject *> smap;
QVector<double> data;
};


A *a = new A();


*a 的 mmap, smap 都是在堆上吧?
操作 mmap, smap 删除 key/value 时,mmap 只要用remove()方法就好了,是不是?
而 smap 要先 delete value 对象,再remove(),对吧?

那么,如果成员 data 的 size 不断增大(如不断append 数据),会涉及到重新分配内存给 data。那么整个 *a 对象会被迁移到另一块内存?
...全文
537 7 打赏 收藏 转发到动态 举报
写回复
用AI写文章
7 条回复
切换为时间正序
请发表友善的回复…
发表回复
mideum 2020-09-09
  • 打赏
  • 举报
回复
一个很简单的测试,不管你向a->data里面append多少数据, sizeof(a->data)的值总是固定的,这是a->data这个变量本身所占用的内存大小
同理不管你向a->data,a->mmap,a->smap里面插多少数据sizeof(*a)的值也总是固定的,所以*a所占用的内存大小是永远不变的
不管是QVector还是QMap,这些容器类所插进去的数据都是另外分配内存的
mideum 2020-09-09
  • 打赏
  • 举报
回复
引用 2 楼 管理員 的回复:
data 的 size 会不断变大,它不在 *a 的地址空间中吗?你的意思是,*a 对象只是一个像链接似的东西,它内部的数据都是保存在另外开辟的内存空间内?

不是*a,是QVector<double> data
QVector本身就是个包装类,内部有自己的内存管理,a->data这个变量本身分配的内存是固定的,你append进去的数据根本不是跟*a,或是跟a->data存在一起,而是存在QVector另外创建的内存空间里
只有C语言下的大小不可变的数组是跟对象一起分配内存空间的:double data[10]这种。
王桑的一天 2020-09-09
  • 打赏
  • 举报
回复
引用 1 楼 mideum 的回复:
前两句都是是 smap不一定,如果是由smap管理指针内存的销毁那就是,有时候只是存一个指针,不负责销毁的,那就不用先delete 最后一句不对,QVector又不是真的数组,真正跟对象一起分配内存的数组只能是固定大小的 QVector这个变量虽然是跟*a在一起的,但实际上存储内部数据的内存也是另外new出来的,不跟*a在一起的,所以不管涨多大都跟a的内存没有关系
谢谢你的解答。 最后一个,比如 A 还有一个公有成员函数:

void A::add_data(int count)
{
    for(int i = 0; i < count; i++)
        data.append(10.7891);
}
data 的 size 会不断变大,它不在 *a 的地址空间中吗?你的意思是,*a 对象只是一个像链接似的东西,它内部的数据都是保存在另外开辟的内存空间内?
mideum 2020-09-09
  • 打赏
  • 举报
回复
前两句都是是
smap不一定,如果是由smap管理指针内存的销毁那就是,有时候只是存一个指针,不负责销毁的,那就不用先delete
最后一句不对,QVector又不是真的数组,真正跟对象一起分配内存的数组只能是固定大小的
QVector这个变量虽然是跟*a在一起的,但实际上存储内部数据的内存也是另外new出来的,不跟*a在一起的,所以不管涨多大都跟a的内存没有关系
王桑的一天 2020-09-09
  • 打赏
  • 举报
回复
引用 5 楼 管理員 的回复:
[quote=引用 4 楼 mideum 的回复:]一个很简单的测试,不管你向a->data里面append多少数据, sizeof(a->data)的值总是固定的,这是a->data这个变量本身所占用的内存大小 同理不管你向a->data,a->mmap,a->smap里面插多少数据sizeof(*a)的值也总是固定的,所以*a所占用的内存大小是永远不变的 不管是QVector还是QMap,这些容器类所插进去的数据都是另外分配内存的
你好,我还有一个疑问: 上面我说了,A 的成员 data 不断地 append 数据后,变得很大。 如果此时, 我直接给它赋值为一个空QVector<double>(),那么它所占用的空间会自动释放?[/quote] 我试了一下,是会自动释放的。应该就是像你所说, vector 容器会将空间申请在堆上,并管理它

    QVector<double> data;
    for(int i = 0; i < 20000000; i++)
        data.append(0.0098);
    data = QVector<double>();   // 空间在堆上,这里会释放堆上的空间

    QVector<double> *data;
    data = new QVector<double>();
    for(int i = 0; i < 20000000; i++)
        data->append(0.0098);
    *data = QVector<double>();  // 会释放之前的空间
    // data = new QVector<double>(); // 这样就不会释放了
王桑的一天 2020-09-09
  • 打赏
  • 举报
回复
引用 5 楼 管理員 的回复:
[quote=引用 4 楼 mideum 的回复:]一个很简单的测试,不管你向a->data里面append多少数据, sizeof(a->data)的值总是固定的,这是a->data这个变量本身所占用的内存大小 同理不管你向a->data,a->mmap,a->smap里面插多少数据sizeof(*a)的值也总是固定的,所以*a所占用的内存大小是永远不变的 不管是QVector还是QMap,这些容器类所插进去的数据都是另外分配内存的
你好,我还有一个疑问: 上面我说了,A 的成员 data 不断地 append 数据后,变得很大。 如果此时, 我直接给它赋值为一个空QVector<double>(),那么它所占用的空间会自动释放?[/quote] 是不是这样的,*a 是申请在堆上,*a 的成员 data 申请的空间是在栈上?因为它不是指针
王桑的一天 2020-09-09
  • 打赏
  • 举报
回复
引用 4 楼 mideum 的回复:
一个很简单的测试,不管你向a->data里面append多少数据, sizeof(a->data)的值总是固定的,这是a->data这个变量本身所占用的内存大小 同理不管你向a->data,a->mmap,a->smap里面插多少数据sizeof(*a)的值也总是固定的,所以*a所占用的内存大小是永远不变的 不管是QVector还是QMap,这些容器类所插进去的数据都是另外分配内存的
你好,我还有一个疑问: 上面我说了,A 的成员 data 不断地 append 数据后,变得很大。 如果此时, 我直接给它赋值为一个空QVector<double>(),那么它所占用的空间会自动释放?

16,225

社区成员

发帖
与我相关
我的任务
社区描述
Qt 是一个跨平台应用程序框架。通过使用 Qt,您可以一次性开发应用程序和用户界面,然后将其部署到多个桌面和嵌入式操作系统,而无需重复编写源代码。
社区管理员
  • Qt
  • 亭台六七座
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧