首页 > 试题广场 >

请问该程序的输出是多少?

[单选题]
#include<stdio.h>
int main(){
    unsigned char i = 7;
    int j = 0;
    for(;i > 0;i -= 3){
       ++j;
    }
    printf("%d\n", j);
    return 0;
}
请问该程序的输出是多少?
  • 2
  • 死循环
  • 173
  • 172
推荐
啥头像
这题正着推不容易,可以考虑反着推
要想退出循环  最后必定是 i=0
根据选项
A:        (0 + 2*3) % 256 = 6  不是7 , 所以A错误
C:          (0 + 173*3) % 256 = 7 ,           所以C可以
D:          (0 + 172*3) % 256 = 4 不是7,所以D错误
B: 既然C可以,当然B就错误
编辑于 2016-08-26 10:22:37 回复(20)
感谢牛客2862122号,细节已修正。
————————————————
unsigned char 8位数据位,范围0-255
所以-2(11111110)时,溢出变成254;
同理-1(11111111)时,溢出变成255;
最后减到0时,不满足循环条件,for停止。
刚好173次。
7 4 1 ==> 共(7-1)/3+1=3次(1-3=-2,即254,继续循环
254 251 ... 5 2 ==> 共(254-2)/3+1=85次(2-3=-1,即255,继续循环
255 252 ... 6 3 ==> 共(255-5)/3+1=85次(3-3=0,退出循环
所以总共173次。

编辑于 2016-08-26 10:28:59 回复(6)
-2的原码是1000 0010,反码是1111 1101,补码是1111 1110,计算机中存储的是补码,即存的是1111 1110,又因为这里是无符号的,所以最高位的1不代表符号,所以1111 1110为254,同理,依次推,直到i为0,可得一共173次
7 4 1——3次
254 251....2——85次
255 252....3——85次
3-3为0,就不会进入循环了,一共173次
发表于 2016-03-02 17:30:48 回复(5)
其实这个题很简单,首先在明白减为负数会导致下溢的前提下,7除以3除不尽,就不能让i等于0(为什么要等于0呢,i如果大于0,则循环则继续,如果小于0,则下溢,同样,循环继续,所以只有当i等于0,循环才能终止),所以只要求7加上若干个256后得到3的倍数。然后求得余数就是循环的次数,(7+256)/3除不尽,(7+256+256)/3=173得本题解。
发表于 2020-12-29 22:46:06 回复(2)
因为i是unsigned char类型,当i变少成负数的时候,会加上256以满足unsigned char 的0~255的范围,那么循环停止的条件只有i==0这种情况,所以问题就变成了找到序列(7,7+256,7+2*256......)中是3的倍数的最小值,即7+2*256=519,519/3=173.
发表于 2018-07-16 11:01:52 回复(0)

i和j的序列:
 i         j
-------------
7         0
4         1
1         2
254(-2)   3
251(-5)   4
248(-8)   5
……

i小于-127后,溢出为正数,直到i=0,才满足

i=(7- j*3)%256 =0
求j的最小值。

等价于 j*3-7 = 256*n
j*3 = 256*n +7
(n*256+7)%3=0
n>=0,满足等式的最小的n是2.

j*3 = 256*2 +7 
j= (512+7)/3 = 173
发表于 2016-02-23 14:42:30 回复(0)
unsign char i参与运算时会隐式转换为int类型,
当i=7时,i-3,虽然转换为int,但不影响计算结果,所以i-3=4;
当=4时, 同理等于i-3= 1
当i=1时,同理等于-2,但是-2 [补码:11111110]赋值给i 时,因为i是unsign char类型,所以最高位1不作为符号,那么i=254
剩下,网友说的很明白了
发表于 2017-03-28 07:01:07 回复(1)
设循环y次,则满足 7+256x = 3y,其中x,y为正整数。当x=2时,y存在正整数173。
首先,理解二进制无符号数0减去1的二进制值为(11111111)实际为255,等价于从(1 0000 0000)的第9位高位借1代表256减去1的值。
题解为存在二进制 (xx......xx 0000 0000) + 7(初始值) - 3*y = 0,其中x为0或1
发表于 2022-06-27 21:33:47 回复(0)
首先  还是把i输出来看 更直观
   7     4     1   254    251   248   245   242   239   236   233   230   227   224   221   218   215   212   209   206   203   200   197   194   191   188   185   182   179   176   173   170   167   164   161   158   155   152   149   146   143   140   137   134   131   128   125   122   119   116   113   110   107   104   101    98    95    92    89    86    83    80    77    74    71    68    65    62    59    56    53    50    47    44    41    38    35    32    29    26    23    20    17    14    11     8     5     2   255    252   249   246   243   240   237   234   231   228   225   222   219   216   213   210   207   204   201   198   195   192   189   186   183   180   177   174   171   168   165   162   159   156   153   150   147   144   141   138   135   132   129   126   123   120   117   114   111   108   105   102    99    96    93    90    87    84    81    78    75    72    69    66    63    60    57    54    51    48    45    42    39    36    33    30    27    24    21    18    15    12     9     6     3
 j = 173

//  从1到254    :     1   0   255  254
需要注意的部分我已经用粗斜体标注

假设循环了j次
则循环j次后,理论上保存的值为  s = 7-3j;
根据选项 得出s   A :   s = 7 - 3 * 2 = 1;
C :   s = 7 - 3 * 173 = 519;
D :   s = 7 - 3 * 172 = 516;
因为计算机存在着溢出,一个字节最大能存储256个数,即 0 ~ 255;
所以能整除256的必然就是在计算机里面存储的是零。
所以  选C
编辑于 2016-11-04 18:29:10 回复(0)
unsigned char 类型的值为0~255,共256个数。
7 / 3 不能整除。(7 + 256) / 3 也不能整除。 (7 + 256 * 2) = 173。刚好能整除。所以答案为173

发表于 2016-03-03 15:14:32 回复(2)
建立一个方程
7-3x+256y=0;//等于0的时候循环退出,x就是循环的次数
//这里的y就从1开始试一下,x能是整数就行

发表于 2016-11-03 23:01:31 回复(0)
此外,做一下说明
这里求第n项的值,使用的是等差数列求第n项的公式an = a1 +(n-1)*d

编辑于 2022-11-30 10:56:03 回复(0)
最开始   i=7
i-3   运行两次  i=1 
i-3   运行一次  i=254
i-3   运行84次  i=2
i-3   运行一次   i=255  (可惜这步我忘记加了...)
i-3   运行85次   i=0
总共就是173次!!!
发表于 2022-07-09 20:48:42 回复(0)
7+256x=3*n;=>n=173
发表于 2017-08-09 17:26:25 回复(0)
这道题目很好解释。7+256x = 3n。x从0开始取值,直到n为最小整数时,n即是目标值。这道题目中,x = 2时,n = 173。所以需要循环173次。
发表于 2017-01-26 15:55:42 回复(0)
解析:3*j - 7 = 256*n
其中n=0,1,2,...
当n=0,3*j=7,j无整数解;
n=1,3*j = 263,j无整数解;
n=2, 3*j = 519  ==> j = 173
发表于 2016-06-29 18:01:02 回复(0)
注意无符号字符型的取值范围是0-255,做题时注意理解分析。
发表于 2016-05-24 21:42:42 回复(0)
unsigned char 8位数据位,计算机中的数据是用补码存储的,所以-2的补码为原码各位取反加1(包括符号位),-2原码为00000010,变反----》11111101,加1--》11111110,所以第一次循环时i变成-2后其实是254(因为unsigned在存储时是没有符号位的),所以答案是173
发表于 2016-02-19 17:33:33 回复(0)
256*2+7=519=173*3
发表于 2015-12-04 09:19:54 回复(0)
执行过程: 1.初始时,i = 7,满足循环条件,进入循环。i 减去 3 变为 4,j 增加为 1。 2.i 的新值为 4,仍然大于 0,继续循环。i 减去 3 变为 1,j 增加为 2。 3.i 的新值为 1,仍然大于 0,继续循环。i 减去 3 变为 254(由于 unsigned char 的范围是 0 到 255)。 4.i 的新值为 254,仍然大于 0,继续循环。i 减去 3 变为 251。 5.循环持续下去,由于 i 是无符号字符型,在减去 3 后一直保持大于 0,直到 i 减到 173。 现在,循环并没有在 i 减到 173 时结束。而是由于 unsigned char 类型的溢出规则,i 会在减法操作后重新回到 255,然后继续减去 3,循环溢出,以此类推。这就导致循环一直进行下去。 所以,实际上这个程序陷入了一个无限循环,并且不会停止。这个程序应该永远不会输出任何东西。如果你确实得到了 173 的输出,这可能是由于编译器或执行环境的一些特殊情况导致的。在标准的 C 语言环境下,这个程序是不应该输出任何东西的。
编辑于 2023-12-06 09:26:15 回复(0)
unsigned char的范围是0-255
所以这个循环停止的条件是i==0就停止

i 从7开始,所以肯定会进入第一次循环,就变成了i=4
然后i=1,最后i=-2
但是最后i不会等于-2,因为他无符号的,他会变成254

-2
10000000000000000000000000000010
11111111111111111111111111111101
11111111111111111111111111111110
11111110

就这样依次往下走, 我依次-3,要多少次才能到0呢?
7 3 1 254 251…………

254/3=84。也就是说可以除84次。当254-84*3的时候,等于2,说明还剩一个2。最后-3又变成了-1,也就是255(共85次)

255这样一直-3,可以减85个,255-85*3就刚好等于0。(85次)

所以需要85+85+3=173次

发表于 2023-04-28 11:33:36 回复(0)