我的可执行文件大小为364KB。它没有使用Vector2D类,所以我用重载运算符实现了一个。
我改变了我的大部分代码
point.x = point2.x;
point.y = point2.y;
到
point = point2;
这导致删除了近1/3的代码行,但我的exe仍然是364KB。究竟是什么导致它的大小增长?
答案 0 :(得分:11)
编译器可能通过内联来优化运算符重载。所以它有效地编译成与原始示例相同的代码。因此,您可能通过重载赋值运算符来减少许多代码行,但是当编译器内联时,它会获取赋值运算符的内容并在调用点处将其内联。
内联是可执行文件大小增加的方式之一。这不是唯一的方法,正如你在其他答案中看到的那样。
答案 1 :(得分:9)
是什么让EXE的规模增长?
外部库,尤其是静态库和调试信息,代码的总大小,运行时库。更多代码,更多库==更大的exe。
要减小exe的大小,您需要使用gnu strip实用程序处理exe,删除所有静态库,摆脱C / C ++运行时库,禁用所有运行时检查并打开编译器大小优化。没有CRT的工作是一种痛苦,但它是可能的。还有一个wcrt(替代C运行时)库,用于创建小型应用程序(顺便说一句,它在过去5年中未被更新/维护)。
我用msvc编译器创建的最小的exe大约是16千字节。这是一个Windows应用程序,它显示单个窗口并运行所需的msvcrt.dll。我对它进行了一些修改,并把它变成了一个恶意的笑话,在显示器上消除了画面。
对于令人印象深刻的exe大小减少技术,您可能需要查看.kkrieger。这是一个3D第一人称射击游戏,总共96千字节。游戏具有大而详细的级别,支持着色器,实时阴影等。与Saurbraten相当(见screenshots)。我遇到过的最小的工作窗口应用程序(带有音乐的3d演示)是4千字节大,并且使用了压缩技术和(可能)未记录的功能(即* .com executbale可以解压缩并在windows xp上启动win32 exe的事实)。
在大多数情况下,只要合理(低于100兆字节),* .exe的大小就不会真正打扰你(我几年没见过磁盘)。例如“不合理”的文件大小,请参阅Qt 4的调试版本,用于mingw。
这导致删除了近1/3的代码行,但我的exe仍然是364KB。
很可能是由编译器使用的外部库,运行时检查等引起的。 此外,这是一个赋值操作。如果你没有使用x的自定义类型(带有复制构造函数),“复制”操作很可能导致少量操作 - 即删除1/3行并不能保证你的代码将是1/3短。
如果你想看看你的修改产生了多大的影响,你可以“要求”编译器为程序的两个版本生成asm列表然后比较结果(手动或与diff)。或者您可以解析/比较两个版本的可执行文件。我确定使用GNU strip或删除额外的库比删除赋值运算符更有效。
答案 2 :(得分:6)
什么类型的点?如果它是两个浮点数,那么编译器将隐式地执行逐个成员的复制,这与之前的操作相同。
编辑:显然,今天人群中的一些人不理解这个答案,并通过downvoting来补偿。所以让我详细说明一下:代码行与可执行文件大小无关。源代码告诉编译器要创建的组装线。一行代码可能会导致数百甚至数千个汇编指令。在C ++中尤其如此,其中一行可能导致隐式对象构造,破坏,复制等。
在这种特殊情况下,我认为“point”是一个带有两个浮点数的类,因此使用赋值运算符将执行逐个成员的复制,即它将单独的每个成员复制并复制它。这与他之前做过的完全相同,只是现在已经隐含了。生成的程序集(以及可执行的大小)是相同的。
答案 3 :(得分:4)
可执行文件的大小通常是“页面”而不是离散字节。
答案 4 :(得分:3)
我认为这是一个很好的例子,如果你有一个很好的优化编译器,为什么人们不应该太担心代码太冗长。相反,总是编码清楚,以便其他程序员可以读取您的代码并将优化留给编译器。
答案 5 :(得分:2)
要查看的一些链接
http://www2.research.att.com/~bs/bs_faq.html#Hello-world
http://www.catch22.net/tuts/minexe
对于Windows,VC ++中的许多编译器选项可能会被激活,如RTTI,异常处理,缓冲区检查等,可能会在幕后添加更多的整体大小。
答案 6 :(得分:1)
当您将c或c ++程序编译为可执行文件时,编译器会将您的代码转换为机器代码,并在其认为合适时应用优化。 但简单地说,更多的代码=更多的机器代码生成=更大的可执行文件大小。
答案 7 :(得分:0)
另外,检查是否有很多静态/全局对象。如果它们未初始化为零,则会大大增加您的exe大小。
例如:
int temp[100] = {0};
int main()
{
}
我的linux机器上面程序的大小是9140字节。
如果我将临时数组初始化为5,则大小将会增加大约400个字节。我的linux机器上的以下程序的大小是9588。
int temp[100] = {5};
int main()
{
}
这是因为零初始化的全局对象进入.bss段,在程序启动期间立即初始化。其中非零初始化对象的内容将嵌入到exe本身中。