以下来自Chromium来源的代码段引起了我的注意(见第155行here):
std::string PrintPreviewUI::GetPrintPreviewUIAddress() const {
// Store the PrintPreviewUIAddress as a string.
// "0x" + deadc0de + '\0' = 2 + 2 * sizeof(this) + 1;
char preview_ui_addr[2 + (2 * sizeof(this)) + 1];
base::snprintf(preview_ui_addr, sizeof(preview_ui_addr), "%p", this);
return preview_ui_addr;
}
不2 + (2 * sizeof(this)) + 1
评估为3 + 2 * sizeof(this)
吗?为什么作者选择以这种方式写表达式?
答案 0 :(得分:11)
是的,它确实以同样的方式评估。
据推测,作者写道的方式是让它更清楚地表明它们的数组是如何布局的 - 即它包含2个字节,然后是2个指针,然后是1个字节。 (实际上我不确定为什么在这种情况下他们选择使用sizeof()运算符,因为指针的字符串表示的长度与指针的内存宽度不同)
编译器将在编译时优化数学运算,因此性能不受影响;这只是为了让其他程序员不必弄清楚3来自哪里。
答案 1 :(得分:2)
是的,它是相同的,假设所有类型都是整数而不是浮点数,就像它们在这种情况下一样(对于浮点数,结果通常是相同的,但是有一些奇怪的边缘情况涉及到事情四舍五入会让你大吃一惊。)
为了清楚起见,作者可能选择以这种方式编写它们:它们在缓冲区中存储一个特定的字符串,该字符串由两个字节构成,添加一些数据,然后再添加一个字节。以这种方式编写它允许代码阅读器通过一次匹配一个部分,轻松地仔细检查计算出的大小是否确实与正在写入的数据量相匹配。
答案 2 :(得分:2)
可能是为了便于阅读。写这篇文章的人试图表达2和1是两个不同的信息,而不仅仅是3而不知道是什么构成了
答案 3 :(得分:0)
这对编译过程的转换阶段生成的汇编代码没有任何影响。
我能想到让作者以这种方式编写代码的唯一真正原因可能是出于可读性的原因 - 也许逻辑比这更清晰,比如果作者在代码中实现这个逻辑之前使用了“代数简化”
关于帖子标题的纯粹数学注释 - 是2 + x + 1确实等于x + 3.但是,与计算机编程不同,它在数学(至少算术/代数)中永远不会有效说x = x + 1: - )