你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

14个C语言的迷题以及答案

[复制链接]
gaosmile 发布时间:2020-11-26 20:12
[导读]本文展示了14个C语言的迷题以及答案,代码应该是足够清楚的,而且有相当的一些例子可能是我们日常工作可能会见得到的。通过这些迷题,希望你能更了解C语言。如果你不看答案,不知道是否有把握回答各个谜题?让我们来试试。
( Z' ~8 V- Y8 Z1 T+ L8 d7 H9 c4 `, z) L* B( d8 N

* p) X9 w" u0 b. i9 H3 i9 P, a* s( ^( N) k: v5 B
本文展示了14个C语言的迷题以及答案,代码应该是足够清楚的,而且有相当的一些例子可能是我们日常工作可能会见得到的。通过这些迷题,希望你能更了解C语言。
+ N/ C! z- J* D3 x* ~7 }
如果你不看答案,不知道是否有把握回答各个谜题?让我们来试试。" p+ W$ i* |  Y+ {7 C
  I2 z1 e- ?/ g- ?, Y& a' l
11 U/ t" g- a* w* B0 R# [
" q! }: Q4 K3 [- [6 o
下面的程序并不见得会输出"hello-std-out",你知道为什么吗?
  1. #include; U+ g& ?0 |" F) m; E3 \  m" `
  2. 1 `+ X/ C: S7 w' o! V7 k
  3.      " [# G0 m2 g9 ~1 V  p( `% _: R
  4. #include4 ]) V8 c: {* a

  5. ' j! [, H4 M8 w" V  Q2 J# t
  6.      ( `/ R0 [. k3 }4 K9 r4 W2 o1 _- B1 l
  7. int main()' K/ q0 ?! N. J4 o% y9 q( \- O' \: T

  8. : [: ~! p! i8 J" R* `( \" e; ?
  9.      
    . G) m) d9 M8 H" h( X
  10. {
    * X* \" p* D$ i6 z

  11. # r8 I# b8 k- u5 |3 n8 z4 [2 E
  12.      1 s8 M% k5 V  W0 q: \; U
  13. while(1)
    , o5 o4 g4 M  y3 E; Z/ P$ s  ?
  14. 5 w- G/ x+ o; l8 F$ `( |
  15.      
    ! x4 a. w6 A/ y
  16. {8 @  e# @' O$ l  k; D7 A
  17. $ C2 J/ n+ f# O- g  s" f: U
  18.      ; N. _: y. b$ |- D! r1 |2 o$ _6 M  t
  19. fprintf(stdout,"hello-std-out");
    % u/ q& f( H4 P2 c6 q4 b

  20. 5 t6 Q( [6 A* b4 C0 c# S
  21.      3 I& `: z2 e( S; p( C1 @
  22. fprintf(stderr,"hello-std-err");
    : ]8 M% U1 |* d) N

  23. " u6 v$ {& S# i& V; e' ~
  24.      
    ) W2 h. w* r0 T! H7 S# B
  25. sleep(1);: b; }, j2 C3 G5 l9 H
  26. 7 S6 W( a1 s9 S& q* R3 X
  27.      3 |8 c' @6 M! a' s0 p9 H
  28. }6 D7 E5 O8 W; c+ Y' u* P7 c4 R

  29. ( Z7 }7 ]* r3 p: q; g; y4 D9 _
  30.      9 A; e( S, z( b1 j' d
  31. return 0;* T7 _; V. M. c/ n( z" D3 i$ l$ V: {
  32. % U( o! a: b9 s; F: i8 P
  33.      
    & j8 O7 Y( T( i) L" O$ z
  34. }2 w! T/ N% E! Q
复制代码

0 C) x+ [9 C+ }
参考答案
stdout和stderr是不同设备描述符。stdout是块设备,stderr则不是。对于块设备,只有当下面几种情况下才会被输入:遇到回车;缓冲区满;flush被调用。而stderr则不会。
9 R/ u' i* E1 o4 z, c2 q
  L" s' ^/ J; M# W& D: @. q
2
* n  @0 I# f% L" I* y0 Y
0 K7 m7 L& Z  R1 p1 }
下面的程序看起来是正常的,使用了一个逗号表达式来做初始化。可惜这段程序是有问题的。你知道为什么吗?
  1. #include
    ( |# @2 F+ Y% D# T

  2. 2 b5 s9 a3 d3 p3 C
  3.      - `+ |# J( }9 x1 x: _1 L: g$ Y
  4. int main()7 `( z( u; i- e' I2 o
  5. % {! U; W5 V" b  U0 e& n& X: `3 ]
  6.      
    9 ?3 G/ U( R9 X8 J, h2 [3 L7 M7 W
  7. {  A9 I, y5 Z/ o; @5 U2 j

  8. " j  x5 d; m3 `7 F# G
  9.      
    ( D1 |6 O1 N8 Q; F* f
  10. int a = 1,2;( L: x  I9 q: m
  11. ! T- X% Y* Q, \" ^  z) h$ u8 Z8 I
  12.      2 r+ e. T, E( G/ \$ q" Z  O  B! A
  13. printf("a : %d\n",a);" O5 \  ]( v$ [4 ^: e( b

  14. : [4 W; [% K% |/ J/ ]0 |  J$ j
  15.      
    % K$ U5 ^* O& A+ a1 n
  16. return 0;/ E+ I9 D4 e* @1 V3 @
  17. / x" N( `* h& I7 _& t
  18.      1 C. @+ i; {; D5 _3 W
  19. }
复制代码

, i6 f7 _5 R* S! Q

, H1 S: P  R. i6 D
参考答案
这个程序会得到编译出错(语法出错)。逗号表达式是没错,可是在初始化和变量声明时,逗号并不是逗号表达式的意义。这点要区分,要修改上面这个程序,你需要加上括号:"int a = (1,2);"。
5 q3 ?6 @$ l8 b- Y0 z9 x3 g! l
& F* k- Y; S6 x. h; V# K9 h0 _
3* t: l2 ?; ]8 N* O' n
3 \/ e) t) ~/ h0 V" D  J! p
下面的程序会有什么样的输出呢?
  1. #include7 `/ S$ s6 z4 d- P: u9 q
  2. 6 q7 W: V' E$ t( b( v- y* I8 R
  3.      
    ( e+ i$ P; G7 J( `( ^
  4. int main()
    9 \- H3 y2 V% ^% m
  5. 8 O" A: A( ~# H/ H( R
  6.      
    ( f4 w+ ?! ^% E6 k/ ]: n0 J
  7. {4 }. m; g7 `4 J! K! P, [. w+ M

  8. # e& u1 g4 V) _+ k- E3 r2 w
  9.      - I& n  G6 ~% V- I6 w
  10. int i=43;
    + i' J) w5 T4 v4 d! i6 f7 t

  11. & C, c* A# E4 K  a7 p( ^8 F# _
  12.      
    : V' p% `% d( s/ d4 v
  13. printf("%d\n",printf("%d",printf("%d",i)));: r( b; A. a% F- x
  14. + D+ c4 n! z8 y4 i; F
  15.      " m# }: i6 ^' Y/ m- |
  16. return 0;
    : \- o5 h% {; ~, u0 c  s
  17. 2 p( d- n% S! |' L5 O
  18.      
      T2 r3 F3 w  ~, a" U# B4 @  [" d
  19. }
复制代码

; p* b! ^3 Q0 n- e, c
参考答案
程序会输出4321,你知道为什么吗?要知道为什么,你需要知道printf的返回值是什么。printf返回值是输出的字符个数。% h2 g0 S; g) f) l+ `1 \: g/ R

9 h3 o1 G- P0 |/ [2 G
4
, a+ A8 g! [& S

8 a2 r* m- ?$ O3 @, _
下面的程序会输出什么?
  1. #include% e8 n; _) z% {5 j6 a5 U! |0 Z

  2. " X) ]5 m, W, Q2 S; Z/ l5 X4 q
  3.      
    8 o& e+ [0 V6 ]) `( k2 d: [
  4. int main()8 z  v, l& `: J' }2 c% K

  5. * u- x8 [/ W2 q
  6.      
    + [0 G. T, [3 ^0 G) M8 w5 J& h
  7. {
    5 O& r9 ]' U( i+ [2 L3 X5 b

  8. & P6 \$ u3 B4 i# O$ B( d- n2 X- E
  9.      
    4 w! f- |: a' g5 c5 @& Y6 Y
  10. float a = 12.5;
    3 h9 |9 _  d9 L+ K& h4 z
  11. 8 p9 W$ c5 h7 v$ o# |
  12.      
    ' n( t( q& ^' v! j
  13. printf("%d\n", a);
    $ V. l% ]" e6 G7 |, J

  14. 7 J( L+ ~% z# y! i7 Q8 b2 }* a
  15.      3 o0 q6 J5 `) V4 I, b, w2 r* M
  16. printf("%d\n", (int)a);" l" ~. v: h" X* s5 {
  17.   [' j0 f/ g0 U
  18.      
    : B  X7 m8 t/ z8 h0 N1 l
  19. printf("%d\n", *(int *)&a);
    3 K* w' J! k& ?3 O1 p! A0 c9 c. [
  20. 0 C  f' T0 _- F: w8 C4 s
  21.      ( U8 A7 m2 o. c+ C  k
  22. return 0;
    - p  Q  `1 J* t) s9 u# @

  23. , ^2 ^2 F/ G# y  e
  24.      
    % Q. C8 a1 ]5 F% F. z6 l: T; i
  25. }
复制代码
6 N2 O: C1 V! [* N' ^8 F6 R
参考答案
该项程序输出:"0 12 1095237632"。
0 h9 D' |/ Z% y5 O: k
原因是:浮点数是4个字节,12.5f转成二进制是:01000001010010000000000000000000,十六进制是:0x41480000,十进制是:1095237632。所以,第二和第三个输出相信大家也知道是为什么了。
' a1 d" C( l) N! u9 [  G
而对于第一个,为什么会输出0,我们需要了解一下float和double的内存布局,如下:( O$ Q3 R$ A/ x+ ]0 S/ o  F
• float: 1位符号位(s)、8位指数(e),23位尾数(m,共32位)。• double: 1位符号位(s)、11位指数(e),52位尾数(m,共64位)。
7 q1 {- M9 q' ~
然后,我们还需要了解一下printf由于类型不匹配,所以,会把float直接转成double,注意,12.5的float和double的内存二进制完全不一样。别忘了在x86芯片下使用是的反字节序,高位字节和低位字位要反过来。所以:• float版:0x41480000 (在内存中是:00 00 48 41)。
; J9 m5 \1 ?5 C/ D3 _4 v2 s  K7 ^
• double版:0x4029000000000000 (在内存中是:00 00 00 00 00 00 29 40)。
& l* _3 I/ n. ~* ?' X# Q5 l/ y
: ?* o* N: E7 \8 J$ w! j+ m4 X8 J3 i2 V
而我们的%d要求是一个4字节的int,对于double的内存布局,我们可以看到前四个字节是00,所以输出自然是0了。这个示例向我们说明printf并不是类型安全的,这就是为什么C++要引如cout的原因了。( K7 \% g- T' ?

$ U, f' a) m7 Y; I" |# T
" H4 a9 r$ ]2 _9 Y, Y  K6 h
5
: ]2 R' a, F, N, S$ k6 U! |+ F
4 u; r- e6 e' v# I
下面,我们再来看一个交叉编译的事情,下面的两个文件可以编译通过吗?如果可以通过,结果是什么?
  1. //file1.cint arr[80];* u4 j! X" h, f
  2. 5 j' b, w8 ?+ Z9 M; x8 Z" q) x8 D0 Q
  3.      
    6 J( Q; o: Q, C5 ~: x! ~" P8 Z
  4. //file2.cextern int *arr;+ [! _1 x2 K0 t  l5 s
  5. ! c1 X) t9 v& _# Q5 Y7 S! {) A
  6.      
    3 o5 n# T+ ^/ ]. _' l+ t
  7. int main()
    ( ]$ L7 n4 ^1 ]2 L; |, o$ E

  8. 1 f+ O  ]6 S( S( i+ z
  9.      
      q; z, g; f( I- W: A
  10. {
    ; T6 f2 f# a6 d: s1 G; r0 o
  11. 3 u3 w. @& c$ z' h4 ~
  12.      
    8 ]- o4 C# O1 w) ~
  13. arr[1] = 100;
    / o8 l- j0 W# @4 t# v

  14. / s5 a9 a3 W; j7 J- U  i
  15.      0 u2 k% Y& y" s7 r4 m7 [! g, k
  16. printf("%d\n", arr[1]);0 f5 L" E. D; z. q
  17. " U3 _1 K( X( z: {- Z
  18.      + |, F1 w' a- G: s
  19. return 0;
    7 n8 A9 B, L! {4 G4 a

  20. + r$ ^- [; s3 s, q% c2 Q/ q3 ?
  21.      
    ' h' O) K( y3 n3 c+ O7 Q3 i0 n
  22. }
复制代码
    9 |1 R4 w/ r$ i' k
参考答案
该程序可以编译通过,但运行时会出错。为什么呢?原因是,在另一个文件中用 extern int *arr来外部声明一个数组并不能得到实际的期望值,因为他们的类型并不匹配。所以导致指针实际并没有指向那个数组。* m& Z+ S6 c$ t
注意:一个指向数组的指针,并不等于一个数组。
7 b2 U( d6 J; t* }2 w
修改:"extern int arr[]"。
2 V3 i- l* u7 C

4 F& J  A) H1 B$ g
6
3 D/ [. f7 `/ E9 [

7 N1 J. t6 |- i+ G) @$ c; ?; p3 `
请说出下面的程序输出是多少?并解释为什么?(注意,该程序并不会输出"b is 20")
  1. #include
    1 t# T3 a. ^0 \) T( Z3 y9 |0 ^8 L
  2. , J. i5 l9 a5 W2 o$ i$ q  j
  3.      
      }$ y! A- ?8 G. E7 j6 i& ~
  4. int main()! z. F: P: F2 f9 H
  5. " r+ s2 M& G; d; c* F
  6.      
    ( V! Y. X, g$ w; r
  7. {
    . c1 H7 v8 r+ @6 ?  s5 k2 Q
  8. 0 D# _& y8 |: Y8 K
  9.      
    9 c- o4 I! A1 @( _' m! J
  10. int a=1;
    " x$ h9 o0 a' e6 B% ]  n
  11. 2 d! D: v0 o( L$ Q% ], k
  12.      
    7 \1 u/ L+ M8 {9 y, c
  13. switch(a)/ a8 T8 Z% D* H: f: j9 o& ?# |& N+ v
  14. ! y$ U2 d. [$ Q1 F4 D& I1 u4 ?
  15.      
    5 p( [& {8 h* O* n( S6 M
  16. {
    . p1 K5 K8 G- ^. q% g; [4 }9 J4 X
  17. , h: z# u  Q" O2 _6 P) M
  18.      
    ! ~& q# R" H& C" c1 q( i$ \
  19. int b=20;3 y0 X. X) c9 g  M- L( I
  20. % m  L9 j" c# F) s: y9 n
  21.      
    7 e  a/ m/ Z' p/ b1 I* g9 Y% l
  22. case 1:
      N* p1 _9 L, F* U1 n5 q

  23.   P8 H8 \" K. ^- b# V
  24.      ) d# M4 c: b# ]- ?% p# G
  25. printf("b is %d\n",b);
    8 L4 L1 S- n4 h3 t
  26. 6 K1 X8 f0 o7 e
  27.      
    + `2 m. ?! R+ t, s3 m
  28. break;
    ! Y3 [0 ?& [! F1 H* T! f0 M" O

  29. 5 G# p* o, j; A) Z
  30.      
    # q9 w3 D! p  w  T, q
  31. default:$ }7 w! v8 B5 H' s" o

  32. ( m2 [9 E* ~- Y8 J( i  o
  33.      
    . x. a- ^8 }: u0 T9 [" k6 G
  34. printf("b is %d\n",b);
    : j, l8 r7 a* K2 _3 y( Q
  35. + C+ z% L$ R6 @7 f/ t# {" }
  36.      2 n- y0 M2 \3 d5 X- v+ q
  37. break;6 F# n6 x# X+ C2 J: d

  38. ; o# j6 I- Y4 P2 h% v2 m# }
  39.      4 p) C4 P; W6 S- y3 i
  40. }  b9 }; ?" z& B! J2 n

  41. : u- M# @) @' c  L
  42.      
    ! E% [1 ?7 V! \) S7 D$ z2 S" W
  43. return 0;" W" D: R, C6 b

  44. ; z/ j% w, q% @/ n
  45.      
    5 z( Q: V6 ~0 f- ?
  46. }
复制代码

3 I3 f, j. T( B! @/ o
7 s! g% \; a: o# S: F/ w! q
参考答案
该程序在编译时,可能会出现一条warning: unreachable code at beginning of switch statement。我们以为进入switch后,变量b会被初始化,其实并不然,因为switch-case语句会把变量b的初始化直接就跳过了。所以,程序会输出一个随机的内存值。
. O0 Z( O! R! X5 A8 Z

6 Y& z+ f$ P& W5 p0 {, _- ]; a* f# ^
7
1 A9 H4 b" S  U& h; C( a5 L" h$ N

. n4 C) q# z; b6 E" I
请问下面的程序会有什么潜在的危险?
  1. #include
    7 W# {' F  u* s1 O2 R

  2. 2 k6 {% q* N6 d1 p# x
  3.      9 T( o( U' T8 b2 Y+ T3 Z/ R) a
  4. int main()
    , n$ I* z& X5 n' _
  5.   a# _0 F' W( Y5 n
  6.      
    1 f. j8 c4 T) t
  7. {' ^& `" u( x2 O6 ?6 H' `

  8. 7 g5 b5 k9 V2 E7 Y/ P
  9.      
    ; e/ c: Y/ j- z+ P6 J; x
  10. char str[80];
    2 x: d( U) b. V, i
  11. . z: M7 n1 A9 O/ |
  12.      
    - P1 `. Y: U7 P/ m
  13. printf("Enter the string:");
    & P; F/ O# @% }2 x0 I

  14. $ H5 Y, |1 c* K
  15.      & m2 ]- s3 M1 A- \
  16. scanf("%s",str);
    - ?0 v3 y) i& n* v

  17. 1 B# S# T8 s! F1 N% w6 q- i
  18.      
    3 T) Y6 `8 T/ o1 O( p
  19. printf("You entered:%s\n",str);
    6 _. a. ]( z+ H% y& h% Q' J$ i* V2 W
  20. : ^- b. u/ ^1 [
  21.      
    & r" ~2 ~# g" i; E( {; ^& I. i7 I- [
  22. return 0;* C7 b5 Y' ?1 ]* L, A  d; w
  23. ( s$ e- N0 [# J( a3 i# W8 C
  24.      
    , ~$ n# e5 ~/ ^, J% C/ u, P
  25. }
复制代码

: c: U. J; ]3 Z: ~3 A
参考答案
本题很简单了。这个程序的潜在问题是,如果用户输入了超过80个长度的字符,那么就会有数组越界的问题了,你的程序很有可能会crash了。
# t1 x7 U* P2 x! k
& T4 H* z0 Q) a6 B
8
" ^+ j+ j' v3 ?' i( A$ z! Z
4 y2 `: b- B, P) k
请问下面的程序输出什么?
  1. #include5 b8 D! N, D/ C; D. n

  2. 0 o, o# f, I- N) W  _
  3.      
    # j/ \4 S% c5 @) L! F
  4. int main()
    / B& x9 E" b  P4 E& d
  5. ! C# N2 q3 J5 ?- m
  6.      
    8 t( }. }: z( x$ A) s, }
  7. {: [: L; |5 H# `# U3 m  H- Y
  8. + O/ y) B- u' w% S/ y
  9.      ; w8 {' C( _2 O4 H; z! W
  10. int i;
    / c8 l! X4 d$ q; F
  11. 7 U# k- _  T' L
  12.      
    + h- A# K, h  ^# U/ R8 C# K
  13. i = 10;
    5 `1 y- I& g7 t

  14. 3 t* z% I8 f7 e
  15.      * ?' U/ c" t5 V& w5 X
  16. printf("i : %d\n",i);
    # L' V+ t. R4 j) T
  17. 9 B) v1 C4 p$ T6 \1 t, r# }9 _4 q
  18.      
    * }, K( m5 b1 r1 [, V
  19. printf("sizeof(i++) is: %d\n",sizeof(i++));
    / i) E4 x5 a# _& b0 O0 [, l* c

  20. 9 q' B+ y; W* D2 ^
  21.      ; O- u" S# o- R) p
  22. printf("i : %d\n",i);
    ) G  {+ p6 o- P7 ^) S8 E
  23. ; ^/ Y; g, L9 K  q0 a5 u
  24.      
    3 {2 F1 C0 m6 g% V0 o
  25. return 0;
    ( L. c( }% {# A

  26. 0 }6 K4 D  ^# u9 b/ ]& E+ K  K; f
  27.      
    : L7 e* ~+ R/ }& h  K  }9 r7 M
  28. }
复制代码
, U9 U9 ^* E4 I( V! r
参考答案
如果你觉得输出分别是:10,4,11。那么你就错了。5 p* X- k6 F+ v' w7 v5 F1 T/ r
错在了第三个,第一个是10没有什么问题,第二个是4,也没有什么问题,因为是32位机上一个int有4个字节。但是第三个为什么输出的不是11呢?居然还是10?原因是,sizeof不是一个函数,是一个操作符,其求i++的类型的size,这是一件可以在程序运行前(编译时)完全的事情,所以,sizeof(i++)直接就被4给取代了,在运行时也就不会有了i++这个表达式。/ E( L+ {1 L2 B* b. |

" r9 S) E+ d6 V$ F
9
6 `+ @8 K- y- b! y- G

% P) E- f8 ]! S" @" f# E) \- {
请问下面的程序的输出值是什么?
  1. #include
      Y2 S( x$ m5 z! d4 a: U# _

  2. 3 q  s' v: d. u5 T
  3.      5 d: u& I" M" k0 i; D
  4. #include7 m- U) D+ P0 [  q7 c" D4 L
  5. 8 K, y$ b. H* w
  6.      % p5 C3 s+ s9 m- j( `6 Q4 ^9 q) k+ f
  7. % [! v, @, c+ R; y
  8. ; J0 \( c( n' v5 e& X/ b6 T
  9.      
    ; T  V( w- a1 g! T+ H* d, m/ a* y
  10. #define SIZEOF(arr) (sizeof(arr)/sizeof(arr[0]))" U0 U) T6 b; A2 f% K% B

  11. ( [6 j0 C- w  b
  12.      
    . J5 @9 y. \) i
  13. #define PrintInt(expr) printf("%s:%d\n",#expr,(expr))
    6 |" H1 }. ^# ]

  14. 8 B& \: I0 N! p" @
  15.      
    8 G$ _" q- U. z$ p

  16. 1 Z$ U$ P$ y) r! `) Q' B" d' Y
  17. , X. ?9 @5 y0 c7 N  N: Z
  18.      8 ]8 [4 i7 T8 @+ L$ m+ }2 M9 b0 |
  19. int main()8 Q: Y2 T5 Q1 s# E
  20. # \, Z- \' M0 o) P
  21.      
    . j' F9 U3 d9 v: Y# F- f& g
  22. {) P: Y3 s9 I* M

  23. 7 q  o- o3 S$ ], K4 f
  24.      
    & g5 Z* g! \4 ?3 A1 ]
  25. /* The powers of 10 */
    0 s% W& K0 K2 w' {) q  b

  26. ' H( k, {) E% `: h6 q
  27.      
    * Q9 |9 d  N! N4 r$ }
  28. int pot[] = {
    0 t( [! V+ B  @0 v
  29. / F: T# {) U) j
  30.      
    9 Y$ U) @0 m( M) Y: ?
  31. 0001,2 V+ j9 u9 @/ y$ I9 [: H' C
  32. 1 `$ D' m2 T; w: |7 i; r. k0 T
  33.      
    1 m- I, o6 G; h) K* k. l
  34. 0010,, w- ^1 |9 Y$ n# V

  35. $ p9 f5 |; O  [8 h. J! Z
  36.      
    * W  [7 `9 R; j  ?
  37. 0100,$ J0 v- c0 k- w- _- f# q- X1 P% b" a
  38. 1 l- O# w5 \, W' _. ~% N9 o
  39.      
    ' i8 j/ I8 s/ C0 l  ?! y
  40. 1000! j" ~, o9 ^8 O
  41. ) s- d) p5 L( j8 H8 x
  42.      % U  _$ `1 l# P0 f) `" a
  43.       };6 B1 a3 I% `1 P  N' \; X+ K

  44. / g# o5 j, ~. h  T& f7 L8 D
  45.      
      @8 |# Y' u- n8 T% K
  46. 5 o! `0 m; a! K# U( R
  47. & P& t, q( j; u! G8 A
  48.        P1 Q) R; z" {8 M+ m6 s% c& [* _
  49. int i;! s; }* b+ N3 {* P: s
  50. & g4 e, M& {6 h% P8 W7 D
  51.      - o( x+ B7 V! s& |
  52. for(i=0;i$ c8 m+ I4 ?$ [) n  y1 b" y
  53. ' m  l5 A9 V4 V: |. W6 a
  54.      9 c" _7 I8 l5 R# T0 Z
  55. return 0;3 N# L" f! ^8 |- s; W- R  Y' y

  56. ( K! L3 _: y6 ?" W0 C) B& @
  57.      3 R( {% U& J! {& h5 N- U6 j
  58. }1 I. e/ x: l0 A# {- k0 w, N
复制代码

' Y! a* \: A4 x: E8 s1 U7 _
参考答案
如果你对于PrintInt这个宏有问题的话,可以去看一看资料。不过,本例的问题不在这里,本例的输出会是:1,8,64,1000。其实很简单了,在C/C++中,以0开头的数字都是八进制的。
  j3 G5 ?! [3 ^) e8 F$ r# q
/ C4 m* l8 D) d6 _
10
/ {  q' q5 O+ U2 u" D

7 M1 Q+ [' P4 q- b* k
请问下面的程序输出是什么?(绝对不是10)
  1. #include; m" v; w+ V  }8 A! D! G; x- h

  2. ) O, B9 W5 ~& a
  3.      
    $ G! U6 h, J5 X" a7 @
  4. #define PrintInt(expr) printf("%s : %dn",#expr,(expr))6 D1 e* L0 @- m4 d. g( S

  5. ! Q" L2 F4 c! y( }0 b2 k  a, @
  6.      
    8 ^6 G* i7 L' X$ s
  7. int main()
    # T; K+ a0 }$ O
  8. , y4 a: F4 g1 Z+ |) E, i  ^( \
  9.      
    1 c6 D7 R* Q4 v
  10. {
    ; K  x) G- P  s9 [1 F6 \( s
  11. ( w7 v4 A% X7 X5 z$ x% \7 [/ _; `
  12.      ( r, s" b0 A  N8 s$ f; Y
  13. int y = 100;
    ) b) O; {- R3 U$ o

  14. 2 e2 X0 [) ^4 x# f8 w
  15.      . [# ?& w/ T8 I/ g5 C3 F8 K- ?
  16. int *p;+ F/ O! N+ E* L  S

  17. & C7 @' J; J: x) _( \/ j
  18.      - f  y: S, w  R1 n0 c, m, s$ g
  19. p = malloc(sizeof(int));' z6 V% D* z5 p2 b' w% l  K
  20. 6 d1 X$ @: s2 k! j) S6 M
  21.      
    " N8 d/ G2 c, k
  22. *p = 10;
    $ ~5 Q+ D! F1 e0 r. o/ ]

  23. & R9 M2 z1 A  _1 s1 [6 Y* U7 Z
  24.      / g; ]* ?# F% [, V' o! i
  25. y = y/*p; /*dividing y by *p */;
    6 O: o+ W1 ^& H; m

  26. , q# [2 O) r. O* o
  27.      # K' A' C0 _! W, V& p8 a, S
  28. PrintInt(y);% S# Z, p5 Y. w  J

  29. 0 w, w. g6 V4 _/ P4 L+ p
  30.      6 K9 t# B$ u3 b& N" O
  31. return 0;
    - j$ S7 x( u) X/ x

  32. ' \! f# Z1 e- }$ V( n3 Y
  33.      
    % y7 a; s/ Q. J9 u5 o" a0 G
  34. }
复制代码

8 V! x. n+ }' w. u/ ^, ?
参考答案
本题输出的是100。为什么呢?问题就出在"y = y/*p;"上了,我们本来想的是"y / (*p)",然而,我们没有加入空格和括号,结果"y/*p"中的"/*"被解释成了注释的开始。于是,这也是整个恶梦的开始。/ W7 `1 x2 u! k" n
8 Q- V6 A4 V9 i5 g. u; ?7 r
11
: V+ G7 [$ ^% S& V% L  `# w  J7 v

6 z+ w; {- Q% S) b2 b5 O" m6 w
下面的输出是什么?
  1. #include! \3 b: \( j4 z' t7 H3 b

  2. # T4 z, r# G5 ^# h) n
  3.      ' k# a' n9 Y1 V- d
  4. int main()
    ' |$ ~0 v7 c. J/ ~: J

  5. 0 J( P' }, B* v- j) r$ ^5 D
  6.      % q/ x" G& f: Z0 }+ S
  7. {8 h& [% N' G" l1 m' j7 e- D" u% o8 ?' N
  8. . Z/ n4 E4 Y1 m% `0 C' m$ d# Q) T
  9.      ' ]7 U' k9 A! V/ C. @: u* L- D
  10. int i = 6;4 j" \9 m# {0 P' o

  11. 8 _7 g% |: C0 F  x) h) ?
  12.      ) h. }+ W4 O$ p. Z/ f
  13. if( ((++i < 7) && ( i++/6)) || (++i <= 9));
    # h  e: b4 r/ k+ j

  14. / r* i; x, e$ b7 @0 M: C/ x
  15.      
    " ~* {- A. \) `$ `! e% x/ b$ ^' P
  16. printf("%d\n",i);3 G8 f# Z! K1 r& D8 u6 \6 q6 c3 I7 W

  17. / U1 t: {( {6 j* z/ X8 G4 }, P9 ^
  18.      3 ^8 ~6 E7 n) b( o) g, W" U
  19. return 0;
    4 j, ~, O/ O1 x
  20. 1 @# A7 d; F  F7 q) a9 h$ _, @
  21.      
    . a6 _6 q: T( S; c
  22. }
复制代码
   
* M: S$ m6 m6 a3 M9 Y
参考答案
本题并不简单的是考前缀++或反缀++,本题主要考的是&&和||的短路求值的问题。2 A; Z# _/ F: e5 A, `- \% R! I
所谓短路求值:对于(条件1 && 条件2),如果“条件1”是false,那“条件2”的表达式会被忽略了。对于(条件1 || 条件2),如果“条件1”为true,而“条件2”的表达式则被忽略了。, a; {$ q5 H8 e5 g
所以,我相信你会知道本题的答案是什么了。
4 c# K5 @& \3 O. e- j" |, L
" t  b4 s% o" G' B% ?  _
125 `1 q6 p) x9 @6 f& Z5 j
; ?# ^6 `  ?; ^4 ?% F
下面的C程序是合法的吗?如果是,那么输出是什么?
  1. #includeint main(){int a=3, b = 5;printf(&a["Ya!Hello! how is this? %s\n"], &b["junk/super"]);printf(&a["WHAT%c%c%c %c%c %c !\n"], 1["this"],2["beauty"],0["tool"],0["is"],3["sensitive"],4["CCCCCC"]);return 0;}
    $ D8 B) y2 A( g
复制代码

) j! d* E5 G; l0 n
# ~' T5 z) y8 E" O. X6 i5 l1 L
参考答案
本例是合法的,输出为:"Hello! how is this? super That is C !"$ V3 [3 m; K) _; ~/ F7 D
本例主要展示了一种另类的用法。下面的两种用法是相同的:• "hello"[2]• 2["hello"]( ?, |6 J( o- O  M6 o
如果你知道:a 其实就是 *(a+i)也就是 *(i+a),所以如果写成 i[a] 应该也不难理解了。+ O0 k0 }: s7 D
: f# B- |& A/ S; L, v6 @9 P3 y  I
13
1 E/ r4 \' o8 h, k. P  E; h$ V

1 l% S6 {7 ]3 G0 x0 @0 m7 K: K
请问下面的程序输出什么?(假设:输入"Hello, World")
  1. #include  T/ u1 c$ S9 f. i4 Y
  2. 4 [7 T8 v! ^- J+ ^2 @2 u
  3.      - ^$ ^0 }, o+ e2 w  W! e, ?  E
  4. int main()
    3 s/ }9 K( ^; V+ ]% }3 P
  5. ( {2 O) V2 d1 D1 m9 F( K
  6.      0 `1 B$ X0 D; {9 x) h
  7. {0 A  z! ~1 V* q

  8. % x( r! z* o  R0 Z8 [) M
  9.      
    " B5 O3 A& d6 b+ d" h
  10. char dummy[80];
    7 c5 P) d+ D7 x* F' z) r

  11. 8 N8 M) |0 M- [' M
  12.      
    4 `) m+ P9 Z9 z+ N% `5 l5 G
  13. printf("Enter a string:\n");
    $ Q! x- p4 _2 X
  14. " B% \) ~  E5 b0 T
  15.      
    : k4 y- R! D% @6 [
  16. scanf("%[^r]",dummy);
    & v- g: }( E6 d

  17. ( u: D+ T( w0 e: m% q
  18.      ! @+ h* s+ ]) C
  19. printf("%s\n",dummy);: y6 Z3 P0 P8 j+ h" i, Z

  20. ! r; j1 |7 I% ]# q0 E) f
  21.      
    - G( r6 p, m: f& e$ n. {$ f
  22. return 0;
    * J' t$ G# T) D2 c: P9 b6 u; n/ W

  23.   B- d8 b  {. J2 j1 T$ h
  24.      
    ; U$ f# t" [( Y% @; d
  25. }
复制代码
9 x1 F  }  R* P* C& [0 u
参考答案
本例的输出是"Hello, Wo"。scanf中的"%[^r]"是从中作梗的东西,意思是遇到字符r就结束了。; N2 v) F) d& E" k& k4 E5 r/ G

7 m/ G  d0 s! n+ C  q
14
$ c+ d8 ~$ z" S0 z6 ~4 p

: s. r. r' E7 K8 q$ C/ K
下面的程序试图使用"位操作"来完成"乘5"的操作,不过这个程序中有个BUG,你知道是什么吗?6 t$ i& o/ g$ `; S3 l6 l+ ^" E
  1. #include  E- ?% I7 q+ d6 r
  2. + j8 c( e( H  i* v
  3.      - X: f4 }) `2 v, h- k8 x' H
  4. #define PrintInt(expr) printf("%s : %d\n",#expr,(expr))
    , p5 ]4 i( p% N* b

  5. ' }! n' ~6 }) B; w
  6.      
    8 _% y/ d8 s# t; i' O/ c
  7. int FiveTimes(int a)% |: C4 \& Y2 J
  8. 4 s+ q/ Y* Y! L3 w
  9.      
    # X2 Y/ l' m/ Z7 m
  10. {. E1 [5 k' b1 z& l
  11. 5 s4 S% ^$ Z! q4 v( L3 b  v
  12.      
    & v; V1 ?% q4 x9 e/ t  j
  13. int t;
    ! U! V6 o; o$ N& W" }1 V8 Y. Y+ i

  14. , e, k: |# a9 r+ I1 O$ G
  15.      
    ) Y, M: {3 }% s" l3 L8 z
  16. t = a<<2 + a;
    6 j$ Q, d  a  N6 ]
  17. $ z# t* u, E) z6 b0 K
  18.      % t+ c& |, [6 Z9 A" z% J
  19. return t;3 j" B* \0 A9 ^
  20. % w* h) d, U# D* l( g  k+ s, C
  21.      
    ( F2 f& Y- h0 R, p
  22. }# e7 O( \0 f7 n1 ?) z- q

  23. ) T# `' H6 S5 a+ |+ K  P. }
  24.      8 x# x4 D+ q9 d! q
  25. int main()6 o3 r& E2 B/ s+ ?

  26. / M3 _8 k1 C7 C4 h
  27.      , C. @0 F. X, ^4 x& ~
  28. {
    - X8 Z: o7 a4 H. g! }

  29. - ^! N1 ]8 U$ ^
  30.      
    2 j& z  F4 Q/ h' o% T5 [
  31. int a = 1, b = 2,c = 3;( g  I* ?$ i" [( G
  32. 3 U% w3 z, X5 o: O, d& i2 Q: n
  33.      
    : M3 N" l$ R" ?. t" ?2 a
  34. PrintInt(FiveTimes(a));
    0 c" \' B/ X% _4 l/ e
  35. " `! L) t* O7 u+ ~6 P  ?) K# l
  36.      2 O& L; K9 C: T  `% F3 i- b5 _
  37. PrintInt(FiveTimes(b));4 ]8 u/ i4 n% k
  38. ) I. v2 C; w4 b+ Q
  39.      
      X4 m4 Z( s: H2 A6 X5 U
  40. PrintInt(FiveTimes(c));$ X- O, ]: u/ r7 g: w
  41. ( G# N! E9 E4 Y6 H
  42.      
    # C1 t; q% W+ Q' H
  43. return 0;
    ; y( t; o, ^' ]: u5 k# b9 e

  44. ' K9 o9 W+ p" m, p
  45.      <span style="color: rgb(51, 51, 51); font-family: monospace; font-size: 15px; white-space: pre-wrap; background-color: rgb(255, 255, 255);">}</span>
复制代码
  ' c) u* \; a- L% V' C. t8 ~% U

% G: W& e+ p+ y0 i  ?; h6 E% O

% I: [" E& }3 M! Q# Y8 r2 @0 O
参考答案本题的问题在于函数FiveTimes中的表达式"t = a<<2 + a;"。对于a<<2这个位操作,优先级要比加法要低,所以这个表达式就成了"t = a << (2+a)",于是我们就得不到我们想要的值。( o& t2 V6 z6 h  a
该程序修正如下:
  1. int FiveTimes(int a)
    - s! P9 A' p9 R6 |& a4 U

  2. : y1 o/ X8 V# g& }
  3.           4 h. Z) V6 s1 s8 c3 x4 M3 F4 y
  4. {* {# I4 L. C1 K/ l& S: V

  5. 7 _" Q8 f) B& T, P& u
  6.          
    7 A3 q4 n) V3 q9 ?9 R9 Q5 ~( m* C
  7.       int t;3 {, Z1 t4 @# ?/ d  ]

  8. 2 ?9 B3 z/ E8 X$ b
  9.           , U4 ^" `- n0 B$ `
  10.       t = (a<<2) + a;
    / |4 `4 W) D3 _( [

  11. # |  x  M1 P& F$ w
  12.          
    " Q  P2 Q* B3 G, j; T8 @" p
  13.       return t;
    2 G* M0 ^# H/ t5 I5 J

  14.   R, r0 J1 _1 a! k* ^( v
  15.          
    3 g' R0 ?9 l1 z; R
  16. }
复制代码
赞 收藏 评论1 发布时间:2020-11-26 20:12

举报

1个回答
xiang295187 回答时间:2020-11-27 15:33:05
感谢
关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
人形机器人运动控制、感知与智能配电
半导体创新技术与应用方向
EE架构与软件定义汽车
12V/48V 汽车智能配电(SPD)
区域控制单元(ZCU)与分区架构
关注我们
st-img 微信公众号
st-img 手机版