|
发表于 2022-1-24 22:24:29
|
显示全部楼层
从结果上看,
直接写32 是进行了左移,变成了0
变量赋值32 是进行了循环左移,变成了原数
反汇编看一下就知道了
方便查看汇编,代码先写成这样
- #include <stdio.h>
- #include <stdlib.h>
- int main (){
- int i = 32;
- int j;
- int k;
- j = 1 << i;
- printf("%x", j);
-
- k = 1 << 32;
-
- printf("\n%x",k);
-
- return 0;
- }
复制代码
汇编代码
- .file "main.c"
- .def ___main; .scl 2; .type 32; .endef
- .section .rdata,"dr"
- LC0:
- .ascii "%x\0"
- LC1:
- .ascii "\12%x\0"
- .text
- .globl _main
- .def _main; .scl 2; .type 32; .endef
- _main:
- pushl %ebp
- movl %esp, %ebp
- andl $-16, %esp
- pushl %ebx
- subl $44, %esp
- call ___main
- movl $32, 20(%esp)
- movl 20(%esp), %eax
- movl $1, %edx
- movl %edx, %ebx
- movb %al, %cl
- sall %cl, %ebx
- movl %ebx, %eax
- movl %eax, 24(%esp)
- movl 24(%esp), %eax
- movl %eax, 4(%esp)
- movl $LC0, (%esp)
- call _printf
- movl $0, 28(%esp)
- movl 28(%esp), %eax
- movl %eax, 4(%esp)
- movl $LC1, (%esp)
- call _printf
- movl $0, %eax
- addl $44, %esp
- popl %ebx
- leave
- ret
- .def _printf; .scl 2; .type 32; .endef
复制代码
去掉没用的
- call ___main
-
- movl $32, 20(%esp) 这句是把32 赋值给i
-
- movl 20(%esp), %eax 这块是循环左移的
- movl $1, %edx
- movl %edx, %ebx
- movb %al, %cl
- sall %cl, %ebx
- movl %ebx, %eax 求出的值放到寄存器eax中
- movl %eax, 24(%esp) 这里把eax的值给j,然后打印
- movl 24(%esp), %eax
- movl %eax, 4(%esp)
- movl $LC0, (%esp)
- call _printf
-
- movl $0, 28(%esp) 这里直接把0给k,没有运算过程
-
- movl 28(%esp), %eax
- movl %eax, 4(%esp)
- movl $LC1, (%esp)
- call _printf
复制代码
结论:"<< 32" 在编译的时候就已经计算得到结果了
应该是 "<< i"因为是变量,编译的时候还没有计算,运行的时候才会执行
验证一下 <<31 汇编是不是也是直接有结果
- #include <stdio.h>
- #include <stdlib.h>
- int main (){
- int k;
- k = 1 << 31;
- return 0;
- }
复制代码
汇编:
- .file "main.c"
- .def ___main; .scl 2; .type 32; .endef
- .text
- .globl _main
- .def _main; .scl 2; .type 32; .endef
- _main:
- pushl %ebp
- movl %esp, %ebp
- andl $-16, %esp
- subl $16, %esp
- call ___main
- movl $-2147483648, 12(%esp) 直接有结果,没运算
- movl $0, %eax
- leave
- ret
复制代码
|
|