获得本站免费赞助空间请点这里
返回列表 发帖

[Zend权威认证试题讲解]第十二章 -调试与性能管理

作为一个开发者,无论你经验多么丰富,或者无论你多么努力,你的程序中总会有bug。这是生命中一个必然的部分,如同死亡与缴税(尽管并没有后面两个那么严重)。! M* m* p" d. X, q6 ]+ C: q
要想解决bug,首先要能找到bug。事实上,许多开发者花费了无数小时茫然得盯着代码,只是因为他们没有把程序的容错能力摆在首位。忽略了这个部分,那么期望一个没有bug的程序就是——不可能的。4 Y% p5 \) G+ |" q
本章测试题将考察你对调试和性能管理相关知识的了解,以及如何用PHP做好这两件事。
$ n) l# z0 \4 t! ?; ^0 T7 d3 |% C1 f. h3 J  t1 P$ d* F" d

! ~  p: T" M+ _( S问题
" u0 `" g4 h) w' p8 n/ W. m
# c$ F* |0 O0 c1.以下脚本如何用三元操作替代?
3 c0 J  F. O* v, L

  1. <?php
  2. if ($a < 10) {
  3.     if ($b > 11) {
  4.         if ($c == 10 && $d != $c) {
  5.             $x = 0;
  6.         } else {
  7.             $x = 1;
  8.         }
  9.     }
  10. }
  11. ?>
复制代码

3 V( O- j! t6 o* m7 ~/ m. k. [A.$x = ($a A. < 10 || $b > 11 || $c == 1 && $d != $c) ? 0 : 1;
- ?' P: g- g* R8 A1 n) W+ VB.$x = ($a < 10 || $b > 11 || ($c == 1 && $d != $c)) ? 0 : 1;) f  _8 {7 O: F
C.$x = (($a < 10 && $b > 11) || ($c == 1 && $d != $c)) ? 0 : 1;
/ P( ]. w6 D- ~0 bD.$x = ($a < 10 && $b > 11 && $c == 1 && $d != $c) ? 1 : 0;
+ k" }. ~8 T3 N9 Z7 ]E.以上都不对: _) T$ C  t) G! `: |

/ v* Z  N; o$ S5 F# F6 \- L" ~! h
2.有一个脚本由于要从远程获取数据,因而运行速度很慢,以下那种方法能对其进行优化?(双选)' M9 g* ~% a0 q/ E: ]
7 g* J5 n  i( C. |
A.安装操作码缓存(opcode cache)
; o# f5 m; r7 n7 x# ^  K8 ^# r4 HB.优化或者升级你的网络连接
4 `9 k6 M+ d& a4 K0 K5 A2 W) E% k  ]! ]C.添置更多的硬件
0 \3 a, [% b9 DD.增加服务器的可用RAM: q: a$ ?  J+ i! O- a! `
E.使用连接缓存% p: Q8 ]/ y: {3 P0 {

' e5 e0 r0 i- N' `
( d8 ]% z5 Q( I4 M3.架设生产环境下的服务器时,需要做哪些步骤?(双选)
8 g6 X3 m8 F% m) s) ?$ S1 w4 [4 g  C* a) p5 T
A.关闭错误报告
/ K$ w/ S3 `. k! a5 ]B.打开错误日志
" x9 H" A9 N' Q$ s6 sC.关闭错误日志9 P4 w1 m" o3 M$ e; }( [7 J, o7 u
D.关闭错误显示
3 S% o( Z  ?+ \6 R8 k3 X( Z* aE.使用@抑错符
$ J; H: P0 t& g- W: h5 H/ z4 _) U) q6 L* b$ b/ }5 u8 A8 C# {

+ K. P  Z$ z$ Z0 Y$ [4.______操作符能对操作数的数据类型进行严格的比较?- Y5 q3 t; \7 I) q2 r# K6 g% X* i
- C' t+ I* M9 w8 `
答案:____________9 ]/ _" Y% e( w/ n% ?0 |% O! v

4 R! _% M+ l! d! A) P% G
- E" L3 N- u& Q& ^: t2 p5.操作码缓存(opcode cache)能做什么?& T3 \, ]4 y* X5 N9 z

5 n4 B# S+ D6 _5 a5 d& q- bA.把脚本编译成二进制对象,使它运行得更快9 n2 ]9 s# ~% y
B.代替Zend引擎加快解释器的运行
% i/ J8 d& y0 x' u' x8 P) ]% F+ NC.缓存脚本输出以提高执行效率. w- `, r+ w! U# a
D.缓存解析器产生的中间码,以提高运行效率! n. H1 M2 N. {& s# `
E.在内存中缓存脚本,减少从硬盘中读取的次数( G4 ^1 H5 `7 K% C& z% r' r

3 q1 m/ _% D6 g; |5 D3 q$ S7 Z
6.以下哪些情况容易造成系统资源枯竭?(双选)
& @$ w. b" g! h' p" @, v6 a3 c- F- F, [% \9 i7 o3 C
A.RAM太小% F% e4 \) K7 ]- D) ]# a9 N8 Y
B.使用了低带宽的连接
4 M4 \) i- N( ?0 dC.虚拟内存超过2GB! n/ @0 Y& x; f5 M; F1 n. l
D.允许同时运行太多的服务器进程
/ N  }5 R) F1 j, _+ \E.以上都不对1 K, n7 s! k4 B# g9 T, |

$ M' @- O6 @: c% Y$ v4 J! y' ~! j/ `6 E; Y# U! w! }
7.以下脚本缺了些什么?(双选) 1 w* L! d# @( ^3 e

  1. <?php
  2. $rs = database_query ("select * from mytable where id = " .
  3. $my_id);
  4. while ($a = database_get_data ($rs)) {
  5.     var_dump ($a);
  6. }
  7. ?>
复制代码

+ o. E& _2 q  L# J- f' g7 mA.参数出口(Parameter escapement)
. @0 a7 r- q- n  I- b& p. fB.输出格式化
( G; N# [0 M/ x- R* U7 S2 R' RC.错误检查0 ~( H$ d& T+ J
D.一个SQL查询! U" r( V* r3 m5 w2 G
E.以上都不对) i; S% y% N1 M+ o- v3 m/ h7 g( s# k

; R. W' n3 J5 i! o: _
0 w$ X- V9 t( w2 [% Z) ^8.以下那种错误类型无法被自定义的错误处理器捕捉到?(双选)
/ C( Z1 J9 i3 P  J$ G+ f5 E% D0 M9 a
A.E_WARNING) o0 C1 L6 p1 p) M6 i) t2 a
B.E_ERROR
! o& I" u+ H8 J; g2 g, x' m0 \& A5 GC.E_USER_ERROR& G5 m# S, W, J, t4 P1 J
D.E_PARSE5 m6 {) R/ ?! G- @* F/ f
E.E_NOTICE% f3 L' i- \6 G$ }7 K
, a, p" i% B+ |- h$ d

/ B3 w( a1 j- T2 F2 }9.当需要比较一个常量和一个变量时,如何才能保证不会错弄成赋值?+ [: v( ~! F; ]7 x
; \: R- a' N, N6 ^' \- Y$ h
A.把变量转换成int% P6 w7 m) S# G. \2 D8 L0 g
B.使用全等比较符(===)
1 j8 m) Y% X( h4 G7 I, qC.确保常量是第一个操作数. ?" c4 {& v# p" L# ?! Q; w/ o
D.使用三元运算符
$ M! G' d! U) P* C6 C( RE.用括号把操作包起来( T* D& l6 }; g' m& T  s
4 o8 T( d& o; u/ |

5 l* U+ a" G9 N10.要通过邮件给系统管理员发送错误信息,以下那种方法最简便?2 K/ x5 }1 f: q# p4 M' `- Q6 W* s
$ k" {+ f+ s$ [# O: i1 ^% r- c8 z
A.创建一个连接远程SMTP服务器的函数' t1 T5 Y. z# F) d& Z
B.使用mail函数
: D. r; ?" l7 ]( p! f8 i+ i# m( P# `C.使用error_log函数7 f, j4 |# O8 c
D.调用sendmial程序* J0 T% C3 Q/ a$ N: O
E.使用webservice/ {* A) D* W( U

; w) [# k# V, r5 l8 o: b- e
) X' Y3 f' E+ N1 D' r! g0 O11.能否仅调用一个函数就关闭脚本内所有的错误报告?
3 j0 G, w' d' Y1 v1 e! y6 p' G. E0 |0 U; `
A.能5 c" ?( ^2 j/ |
B.不能  b2 h0 ~5 _7 b4 ^% \0 R% Z5 I+ I* ^

  o6 f8 K+ |, e- t9 G! B- T
( S. T- W. M& y' D12.概要分析器(profiler)是做什么的?
6 \( V# {( ?3 u* o+ C
; x" j  |) t5 t( J9 CA.创建关于脚本结构的档案
4 Q7 ]* x% J5 o- \: [) c% |B.把脚本转化成UML图, [4 Y% A, Z/ x* z/ c" `- ?; A1 P
C.精确测算脚本不同部分的运行时间
7 n$ G+ k: ~8 U" AD.计算脚本通过web服务器执行时的维度5 o3 A. c, X. j$ X
E.扫描脚本,识别由常见错误导致的bug1 D1 {- K4 i2 X! i2 y
4 C; _0 d; ~) u# X8 O% g

; q2 T& J$ q% c# y9 ?13.______能帮助识别和解决bug。9 C2 Y% q- k! J0 F& ^% V

  y4 G/ J8 k" p) T答案:____________+ s7 g1 h' v, s

' J' U; f, b2 l7 X/ I4 n2 T# e  ^  N  W
14.trigger_error()和user_error()有什么区别?
! j# |; Q% Y' [; D; f- C
: p# @( z9 Q8 G# fA.trigger_error()允许脚本抛出系统级的错误" e! E5 ~  G' L/ u. d
B.user_error()允许脚本抛出系统级的错误4 H) J4 P( h1 e" ]9 o  F- }
C.user_error()不能被用在错误管理器中
2 M  j5 I+ t# Y6 w8 _* C+ XD.trigger_error只在PHP5中可用: T& E$ L4 a0 T" w: I
E.没有区别
. y7 f) s0 F- Q, `  b% L, K8 y- Y1 U% l$ k. N" Z8 \- J2 B

- `" i0 o' P+ g/ }# S3 T2 @15.______函数能返回脚本里任意行中调用的函数的名称。该函数同时还经常被用在调试中,用来判断错误是如何发生的。0 b# c7 l) ^5 N" z( t) y0 n
/ A+ W3 @, l0 {0 H% E' d
A.print_r
1 B6 ~9 ~  n) a$ n4 E. x% Y/ Z% Z1 AB.var_dump
9 S, G* v/ A( y. O# I3 yC.stack_dump
+ K6 h. W. j' Y% S( E. qD.debug_backtrace; T4 {6 d1 e0 u; U
E.以上都不对- r3 Q' T4 i0 ~3 B. X0 B/ x
2 q" p1 X% H7 w9 O! Y
答案
; s5 I) u: E0 Z
9 I' ~$ p7 ], u% L( o1.答案是E。三元操作符把每个if语句连到一起,作为&&操作的一部分。然而本题中,$x=1这个赋值只在第三个if为false时发生。如果第一个和第二个条件都不成立,$x=1就不会执行。这题对三元操作的应用有些极端,实际应用时,需要根据可读性来决定是否需要用三元运算符(本题这种情况就最好不要用)。
7 f% `% Y% b% [7 T( J, P% G+ W0 F2 F! e, P/ _6 Y" R) t
2.问题是由第三方数据源传输缓慢导致的,而你无法控制这个数据源。你也许能在网络连通性上做些工作(假设问题出在你这一边)。还可以对接收到的内容进行缓存,这样能减少获取重复数据的时间。因此,答案是B和E。
2 k; `0 V: s9 R! w8 O' m4 ~
5 p' V5 X8 ?, _" B) P2 z2 T# c9 g4 Q3.正确的选择是B和D。如果关闭错误报告、使用@抑错符和关闭错误日志,那么在你交付给客户的网站出现问题时,你将很难进行分析和调试。
% t/ p6 l7 G" z2 M  X5 ?3 E2 ?( X
4.这是在描述===操作符。# W0 E1 P! l/ Z6 d* k0 c! F

$ \, J9 w& T$ h5.正确答案是D。PHP脚本在执行时,将首先被解析成“中间”码(也叫opcode,操作码),然后解释器执行。操作码缓存出现在这两个步骤之间,对解析器的输出进行缓存。下次执行该脚本时,将缓存的输出直接送入解释器。这样就就不需要再解析一次了。
+ X7 ?  y9 G6 O& B, S9 Y7 [3 R, p5 F  e, c4 c3 Z5 m
6.正确答案是A和D。如果RAM太小,进程间将出现资源竞争,服务器将大量使用硬盘交换。同样的,如果允许过多进程同时执行,也会使服务器频繁进行交换,导致速度下降。# z$ x9 `1 Y1 X+ V" v$ Z& ~2 ]# S
9 z, d9 A5 ], ^) x5 ^* e3 U
7.正确答案是A和C。脚本不检验datebase_query()的调用是否成功,因此将持续执行下去,最终产生错误。此外,$my_id参数没有转义——可能导致代码注入(详见第11章)。
1 X! i" d* H* R3 M5 b$ p1 T5 v# X8 }5 n7 R5 j  k
8.答案B和D正确。出现解析错误往往表示脚本中有语法错误,自定义的错误管理器无法捕捉到它们的原因很明显:错误管理器在脚本里,而现在无法解析脚本,管理器也就无法执行。类似的,E_ERROR表示有致命的运行错误出现,比如内存耗尽。因此脚本会立刻被中断,因为解释器无法执行后面的代码。  ?, m' v9 Y- r( t

0 W3 c5 ?5 v3 m( r! ?. L9 b- r9.答案是C。比较操作是一个可交换的操作(就是说结果独立于操作数之外),而赋值不是。因此,比如说,$a==10和10==$a是等效的,而$a=10和10=$a却不是,而且后者会导致一个错误,因为这不是一个合法的操作。确保常量在操作符前面,能保证你不会错误得将比较变成赋值。
- Y" F% l# u8 ^* B: l. N9 D7 Y  v/ m5 P# P( L$ E/ o
10.答案是C。error_log函数能将信息送往一个指定的地址。尽管mail()也可以用,但error_log能自动给邮件添加标题,因此这才是最简单的方法。
! w. r: P, d& s$ P: S" ]0 E, v' Q9 Q% @- j" d, M
11.答案是不能。error_reporting函数能关闭所有运行时的错误报告,但对解析时的错误无效,因为解析错误发生在脚本执行之前。
% e5 ^+ u+ f- Z( i" E) E  Q! k' s- y5 K" X+ w, y% @3 B
12.显然,答案是C。概要分析器(profiler)能监视脚本的运行,并记录单个部分的运行时间。它可以用来找出和解决瓶颈。
: r. _* U' Q+ T( V# I8 ~: V7 A) @  H4 M/ i) Y$ K
13.这是对调试器的完美定义!你可以用调试软件监视脚本运行,同时分析系统资源消耗,从而发现和解决程序缺陷。5 h, V# V8 E7 D8 v

. l9 t# K/ W) G' k5 F9 h14.trigger_error()和user_error()之间没有区别。后者其实是前者的别名。
2 j7 K: ^$ r/ f) ~2 C* s$ \% X9 X9 y$ {2 e5 c9 n
15.答案是D。题目是在描述debug_backtrace函数,它返回一个由所有在代码的特定位置调用过的函数名组成的数组。

返回列表
【捌玖网络】已经运行: