获取 Qt 对象的大小

Posted

技术标签:

【中文标题】获取 Qt 对象的大小【英文标题】:Getting the size of a Qt Object 【发布时间】:2009-08-13 19:16:40 【问题描述】:

我正在使用 Qt 和 C++,我需要找出某些 Qt 类的实例使用的内存量,这通常使用 sizeof 来完成,但是在 Qt 中,每个类都有一个指向另一个包含实际的类的指针实现,这个私有实现类的定义不在头文件中,而只在源代码中。

我是 Qt 的新手,所以可能有一种标准的方法可以做到这一点,如果你没有任何想法来解决这个问题?

【问题讨论】:

你认为你为什么需要这样做? 我需要知道我是否可以创建数千个或对象太大。 @Diaa:尝试创建它们,并正确检查错误 ***.com/questions/15763088/… @anon 有些人没有无限的内存,实际上必须考虑这一点,而不是编写臃肿的代码。 QObject 添加了不错的功能,但如果我们要嘲讽 oom 杀手,那就不值得了 【参考方案1】:

在标准 C++ 中无法做到这一点,而且很少有框架支持类似的东西。原因很简单——正如您所观察到的,一个对象可能包含指针,而这些指针可能指向包含指针的其他对象, 等等。甚至当你到达指针链的末端时,也没有通用的方法来找出一个指针指向多少内存。

因此,您需要找到另一种方法来解决您的问题,我认为这不是首先要解决的正确问题。

【讨论】:

【参考方案2】:

这个问题没有确切的答案,因为为相同类型的不同对象分配的内存量甚至可能不相同(例如,QSomething A 可能能够重用缓存中的一些数据,而 QSomething B 可能必须单独分配,等等)。

我想你可以做的是编写一个简单的测试程序,它启动,分配 N 个有问题的对象,然后进入 sleep() 很长一段时间。当程序处于休眠状态时,使用任务管理器(或您喜欢的任何工具)查看进程正在使用多少 RAM。然后 ctrl-C(或终止)该进程,并以较大的 N 值再次运行它,并重复测量。重复该过程,最终您将了解该进程的 RAM 分配如何随着分配的项目数量而增长,然后您可以做一些代数来大致了解每个对象的平均内存成本。

(请记住,在启动进程时会产生大量内存开销,因此请从所有案例中减去 N=0 案例使用的内存,以便您仅测量对象的成本,而不是环境开销)

【讨论】:

【参考方案3】:

事实上,这个问题并不是 Qt 独有的。考虑std::string 使用了多少空间。它既不是sizeof(std::string) 也不是std::string::size()

C++ 没有这个问题的答案,因为这个问题很少有意义。

【讨论】:

对于 std::string,使用 sizeof(std::string) + string length 可以得到一个几乎正确的数字。人们应该知道一个对象有多重才能编写高效的应用程序。我觉得奇怪的是,这样的问题在允许低级编程并给予您绝对控制权的语言中很少有意义。 仅举几个不那么可靠的原因:小字符串优化、大小舍入、堆开销、COW。写你的第二句话,我还没有遇到过缺乏这些信息阻碍我的情况。 @Diaa 它确实为您提供了绝对的控制权,但如果您愿意,您不能使用 Qt 之类的库或标准库——您必须自己编写。但是,这些库都没有提供您的问题所询问的功能这一事实应该向您表明它不是一个特别有用的功能。 @Neil, @MSalters 感谢您的回复,我理解您的观点,但我不相信。我想多讨论一下,但是 cmets 不太适合这个。【参考方案4】:

我发现一般来说 QObject 对于创建几千个以上的实例是相当繁重的。

正如其他几个人所提到的,解决这个问题的最佳方法通常是尝试一下,看看会发生什么。你甚至可以像这样编写一个小应用程序:

int main(int argc, char **argv)

    QApplication app(argc, argv);
    QObject objects[5000];
    return app.exec();

然后在退出应用程序之前测量内存使用情况。

【讨论】:

将对象放入堆栈中不会反映在应用程序的内存使用中,因为堆栈已经是预先分配的内存块。此外,这不会为您提供 QObject 的实际大小,而只是对象外壳的大小,无论如何您都可以使用 sizeof 轻松且更准确地获得...

以上是关于获取 Qt 对象的大小的主要内容,如果未能解决你的问题,请参考以下文章

QT获取图片-》改变图片大小-》保存

在 Qt 中获取物理屏幕大小

Qt 中如何获取系统默认字体大小?

如何在qt中获取视口大小

qt里面怎么设置窗口大小改变不触发update

Qt获取当前屏幕大小