鱼C论坛

 找回密码
 立即注册
查看: 1722|回复: 5

[已解决]新手路过

[复制链接]
发表于 2021-1-14 16:19:08 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
int  j=5;
q=(++j)+(++j)+(++j)求q的值。这一串是怎么算的,为什么结果是24呢?
(不是写代码,只是单纯想问怎么算的)。
最佳答案
2021-1-14 18:09:18
本帖最后由 jackz007 于 2021-1-14 18:39 编辑

      使用 gcc 编译这个代码
  1. #include <stdio.h>

  2. int main(void)
  3. {
  4.         int j = 5 , q                ;
  5.         q = (++ j) + (++ j) + (++ j) ;
  6.         printf("%d\n" , q)           ;
  7. }
复制代码

       运行结果是 22,非常的怪异,为了搞清楚这个值的来历,我用 OD 对可执行程序的反汇编代码进行了静态分析
  1. 00401360  /$  55                         push    ebp
  2. 00401361  |.  89E5                       mov     ebp, esp
  3. 00401363  |.  83E4 F0                    and     esp, 0xFFFFFFF0
  4. 00401366  |.  83EC 20                    sub     esp, 0x20
  5. 00401369  |.  E8 A2050000                call    00401910
  6. 0040136E  |.  C74424 1C 05000000         mov     dword ptr [esp+0x1C], 0x5                     ; j = 5
  7. 00401376  |.  834424 1C 01               add     dword ptr [esp+0x1C], 0x1                     ; j = j + 1 = 6
  8. 0040137B  |.  834424 1C 01               add     dword ptr [esp+0x1C], 0x1                     ; j = j + 1 = 7
  9. 00401380  |.  8B4424 1C                  mov     eax, dword ptr [esp+0x1C]                     ;
  10. 00401384  |.  8D1400                     lea     edx, dword ptr [eax+eax]                      ; i = j + j = 14
  11. 00401387  |.  834424 1C 01               add     dword ptr [esp+0x1C], 0x1                     ; j = j + 1 = 8
  12. 0040138C  |.  8B4424 1C                  mov     eax, dword ptr [esp+0x1C]                     ;
  13. 00401390  |.  01D0                       add     eax, edx                                      ; q = j + i = 8 + 14 = 22
  14. 00401392  |.  894424 18                  mov     dword ptr [esp+0x18], eax                     ; |
  15. 00401396  |.  8B4424 18                  mov     eax, dword ptr [esp+0x18]                     ; |
  16. 0040139A  |.  894424 04                  mov     dword ptr [esp+0x4], eax                      ; |
  17. 0040139E  |.  C70424 00504000            mov     dword ptr [esp], 00405000                     ; |ASCII "%d\n"
  18. 004013A5  |.  E8 66270000                call    <jmp.&msvcrt.printf>                          ; \printf
  19. 004013AA  |.  B8 00000000                mov     eax, 0x0
  20. 004013AF  |.  C9                         leave
  21. 004013B0  \.  C3                         retn
复制代码

        上面的汇编代码我已经做了注释。
        我们看到,代码执行细节用 C 语言描述过程是这样的:
  1.         int i , j = 5 , q ;
  2.         j ++              ;
  3.         j ++              ;
  4.         i = j + j         ;
  5.         j ++              ;
  6.         q = j + i         ;
复制代码

        这就是 22 的来历。
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2021-1-14 16:22:11 | 显示全部楼层
这个问题你可以看下这个https://fishc.com.cn/forum.php?m ... d=188583#pid5187354
我用的Dev结果是22
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2021-1-14 17:40:01 | 显示全部楼层
         24 说明使用的编译器是 VC,估计是先完成 3 个 ++ j,使 j 由 5 变成 8,然后,3 个 8 相加不就是 24 了?
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2021-1-14 18:09:18 | 显示全部楼层    本楼为最佳答案   
本帖最后由 jackz007 于 2021-1-14 18:39 编辑

      使用 gcc 编译这个代码
  1. #include <stdio.h>

  2. int main(void)
  3. {
  4.         int j = 5 , q                ;
  5.         q = (++ j) + (++ j) + (++ j) ;
  6.         printf("%d\n" , q)           ;
  7. }
复制代码

       运行结果是 22,非常的怪异,为了搞清楚这个值的来历,我用 OD 对可执行程序的反汇编代码进行了静态分析
  1. 00401360  /$  55                         push    ebp
  2. 00401361  |.  89E5                       mov     ebp, esp
  3. 00401363  |.  83E4 F0                    and     esp, 0xFFFFFFF0
  4. 00401366  |.  83EC 20                    sub     esp, 0x20
  5. 00401369  |.  E8 A2050000                call    00401910
  6. 0040136E  |.  C74424 1C 05000000         mov     dword ptr [esp+0x1C], 0x5                     ; j = 5
  7. 00401376  |.  834424 1C 01               add     dword ptr [esp+0x1C], 0x1                     ; j = j + 1 = 6
  8. 0040137B  |.  834424 1C 01               add     dword ptr [esp+0x1C], 0x1                     ; j = j + 1 = 7
  9. 00401380  |.  8B4424 1C                  mov     eax, dword ptr [esp+0x1C]                     ;
  10. 00401384  |.  8D1400                     lea     edx, dword ptr [eax+eax]                      ; i = j + j = 14
  11. 00401387  |.  834424 1C 01               add     dword ptr [esp+0x1C], 0x1                     ; j = j + 1 = 8
  12. 0040138C  |.  8B4424 1C                  mov     eax, dword ptr [esp+0x1C]                     ;
  13. 00401390  |.  01D0                       add     eax, edx                                      ; q = j + i = 8 + 14 = 22
  14. 00401392  |.  894424 18                  mov     dword ptr [esp+0x18], eax                     ; |
  15. 00401396  |.  8B4424 18                  mov     eax, dword ptr [esp+0x18]                     ; |
  16. 0040139A  |.  894424 04                  mov     dword ptr [esp+0x4], eax                      ; |
  17. 0040139E  |.  C70424 00504000            mov     dword ptr [esp], 00405000                     ; |ASCII "%d\n"
  18. 004013A5  |.  E8 66270000                call    <jmp.&msvcrt.printf>                          ; \printf
  19. 004013AA  |.  B8 00000000                mov     eax, 0x0
  20. 004013AF  |.  C9                         leave
  21. 004013B0  \.  C3                         retn
复制代码

        上面的汇编代码我已经做了注释。
        我们看到,代码执行细节用 C 语言描述过程是这样的:
  1.         int i , j = 5 , q ;
  2.         j ++              ;
  3.         j ++              ;
  4.         i = j + j         ;
  5.         j ++              ;
  6.         q = j + i         ;
复制代码

        这就是 22 的来历。
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2021-1-14 22:20:43 | 显示全部楼层
jackz007 发表于 2021-1-14 18:09
使用 gcc 编译这个代码

       运行结果是 22,非常的怪异,为了搞清楚这个值的来历,我用 OD 对 ...

向大佬看齐!
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2021-1-15 19:04:08 | 显示全部楼层
编译器对待不同。VS编译器按++在前则先自增来算。所以J自增了三次,然后才进行其它运算
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2025-5-2 19:32

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表