san*_*orn 5 c++ optimization range-v3 string-view
随着std::string_view,与两者range::for_each产生精确组装const char[N]并const char *传递给std::string_viewctor
换句话说,这段代码
auto str = "the quick brown fox is jumping on a lazy dog\nthe quick brown fox is jumping on a lazy dog\n";
ranges::for_each(std::string_view{str}, std::putchar);
Run Code Online (Sandbox Code Playgroud)
和
auto& str = "the quick brown fox is jumping on a lazy dog\nthe quick brown fox is jumping on a lazy dog\n";
ranges::for_each(std::string_view{str}, std::putchar);
Run Code Online (Sandbox Code Playgroud)
两者都低于汇编:
main: # @main
pushq %rbx
movq $-90, %rbx
.LBB0_1: # =>This Inner Loop Header: Depth=1
movsbl .L.str+90(%rbx), %edi
movq stdout(%rip), %rsi
callq _IO_putc
addq $1, %rbx
jne .LBB0_1
xorl %eax, %eax
popq %rbx
retq
.L.str:
.asciz "the quick brown fox is jumping on a lazy dog\nthe quick brown fox is jumping on a lazy dog\n"
Run Code Online (Sandbox Code Playgroud)
此外,如果我们通过交流字符串const char[N]来ranges::view::c_str(),
auto& str = "the quick brown fox is jumping on a lazy dog\nthe quick brown fox is jumping on a lazy dog\n";
ranges::for_each(ranges::view::c_str(str), std::putchar);
Run Code Online (Sandbox Code Playgroud)
这就产生了像上面那样产生的精确装配std::string_view.
在另一方面,如果我们经过交流字符串const char*来ranges::view::c_str()
auto str = "the quick brown fox is jumping on a lazy dog\nthe quick brown fox is jumping on a lazy dog\n";
ranges::for_each(ranges::view::c_str(str), std::putchar);
Run Code Online (Sandbox Code Playgroud)
这次它产生一个不同的组件如下:
main: # @main
pushq %rbx
movb $116, %al
movq $-90, %rbx
.LBB0_1: # =>This Inner Loop Header: Depth=1
movsbl %al, %edi
movq stdout(%rip), %rsi
callq _IO_putc
movzbl .L.str+91(%rbx), %eax
incq %rbx
jne .LBB0_1
xorl %eax, %eax
popq %rbx
retq
.L.str:
.asciz "the quick brown fox is jumping on a lazy dog\nthe quick brown fox is jumping on a lazy dog\n"
Run Code Online (Sandbox Code Playgroud)
哪个组装胜利?
为什么std::string_view决定产生相同的二进制文件?
能否view::c_str()既产生只有一个更快的组装const char*和const char [N]?
两个std::string_view版本都调用相同的构造函数,它const char*使用a 然后使用std::char_traits::length(基本上是strlen)来查找长度.编译器优化掉了strlen因为字符串文字对于编译器是可见的,因此它的长度是已知的,但是两种形式都使用完全相同的构造函数,并且两者都优化掉了strlen,因此两者都生成相同的代码.
该view::c_str版本使用不同的重载,具体取决于它是指针还是数组,请参阅https://github.com/ericniebler/range-v3/blob/1f4a96e9240786801e95a6c70afebf27f04cffeb/include/range/v3/view/c_str.hpp#L68
当给定指针时,它必须找到与使用类似的长度strlen,但是当给定一个大小的数组时,N它N-1用于长度.即使编译器strlen将类似代码优化为固定的编译时值,它仍然在编译不同的东西,因此生成的代码不相同并不奇怪.
| 归档时间: |
|
| 查看次数: |
148 次 |
| 最近记录: |