我想弄清楚使用constexpr
和preprocessor macro
定義整數和字符串文字之間的「底層」差異。C++ constexpr vs宏中的字符串字面值與整數
#define FIRST_STRING "first_stringer"
constexpr char second_string[] = "second_stringer";
#define FIRST_INT 1234
constexpr int second_int = 12345;
int main()
{
printf("%s\n", second_string);
printf("%s\n", FIRST_STRING);
printf("%d\n", FIRST_INT);
printf("%d\n", second_int);
return 0;
}
void hello() {
printf("%s\n", second_string);
printf("%s\n", FIRST_STRING);
printf("%d\n", FIRST_INT);
printf("%d\n", second_int);
}
當與g++ -S main.cpp -std=c++11
.file "main.cpp"
.section .rodata
.LC0:
.string "first_stringer"
.LC1:
.string "%d\n"
.text
.globl main
.type main, @function
main:
.LFB0:
.cfi_startproc
pushq %rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
movq %rsp, %rbp
.cfi_def_cfa_register 6
movl $_ZL13second_string, %edi
call puts
movl $.LC0, %edi
call puts
movl $1234, %esi
movl $.LC1, %edi
movl $0, %eax
call printf
movl $12345, %esi
movl $.LC1, %edi
movl $0, %eax
call printf
movl $0, %eax
popq %rbp
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE0:
.size main, .-main
.globl _Z5hellov
.type _Z5hellov, @function
_Z5hellov:
.LFB1:
.cfi_startproc
pushq %rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
movq %rsp, %rbp
.cfi_def_cfa_register 6
movl $_ZL13second_string, %edi
call puts
movl $.LC0, %edi
call puts
movl $1234, %esi
movl $.LC1, %edi
movl $0, %eax
call printf
movl $12345, %esi
movl $.LC1, %edi
movl $0, %eax
call printf
popq %rbp
.cfi_def_cfa 7, 8
ret
.cfi_endproc
.LFE1:
.size _Z5hellov, .-_Z5hellov
.section .rodata
.align 16
.type _ZL13second_string, @object
.size _ZL13second_string, 16
_ZL13second_string:
.string "second_stringer"
.align 4
.type _ZL10second_int, @object
.size _ZL10second_int, 4
_ZL10second_int:
.long 12345
.ident "GCC: (Ubuntu 4.8.4-2ubuntu1~14.04.3) 4.8.4"
.section .note.GNU-stack,"",@progbits
編譯在檢查彙編代碼這樣做具有以下組件的輸出,就可以在這兩種功能觀察,我們有指令movl $1234, %esi
和movl $12345, %esi
。即有一個宏觀整數文字和constexp int
之間的引擎蓋下沒有明顯的區別,即使constexpr int
被儲存在一個單獨的部分_ZL10second_int
在另一方面,對於字符串常量,我們看到,該指令movl $_ZL13second_string, %edi
和movl $.LC0, %edi
地圖他們各自的字符串文字到兩個不同的部分
這兩個部分有什麼區別?一旦加載可執行文件,它們是否映射到主內存的不同部分?如果是的話,訪問比另一部分快嗎?我知道我可以描述性能影響,但我想了解這兩部分之間的理論原因和差異。
如果使用字符串'#define'兩次,你必須依靠編譯器來刪除重複的字符串文字,或可執行空間被浪費。 'constexpr'保證獨特性。 –