友情提示:如果本网页打开太慢或显示不完整,请尝试鼠标右键“刷新”本网页!
第三电子书 返回本书目录 加入书签 我的书架 我的书签 TXT全本下载 『收藏到我的浏览器』

软件工程思想-第12部分

快捷操作: 按键盘上方向键 ← 或 → 可快速上下翻页 按键盘上的 Enter 键可回到本书目录页 按键盘上方向键 ↑ 可回到本页顶部! 如果本书没有阅读完,想下次继续接着阅读,可使用上方 "收藏到我的浏览器" 功能 和 "加入书签" 功能!

p…》Func();// p是“野指针”,程序出错
  }

6。2。4 使用const
在定义一个常量时,const比 #define更加灵活。用const定义的常量含有数据类型,该常量可以参与逻辑运算。例如:
constint LENGTH = 100;// LENGTH是int类型
constfloatMAX=100;// MAX是float类型
#defineLENGTH  100// LENGTH 无类型
#defineMAX 100// MAX 无类型

除了能定义常量外,const还有两个“保护”功能:
  一、强制保护函数的参数值不发生变化
以下程序中,函数f不会改变输入参数name的值,但是函数g和h都有可能改变name的值。
void f(String  s);// pass by value
void g(String &s);// pass by referance
void h(String *s);// pass by pointer
main()
  {
String  name=“Dog”;
f(name);// name的值不会改变
g(name);// name的值可能改变
h(name);// name的值可能改变
  }

对于一个函数而言,如果其‘&’或‘*’类型的参数只作输入用,不作输出用,那么应当在该参数前加上const,以确保函数的代码不会改变该参数的值(如果改变了该参数的值,编译器会出现错误警告)。因此上述程序中的函数g和h应该定义成:
void  g(const String &s);
void  h(const String *s);

  二、强制保护类的成员函数不改变任何数据成员的值
以下程序中,类stack的成员函数Count仅用于计数,为了确保Count不改变类中的任何数据成员的值,应将函数Count定义成const类型。
class Stack
  {
  public:
void push(int elem);
void pop(void);
intCount(void)  const;// const类型的函数
  private:
intnum;
intdata'100';
  };

int Stack::Count(void)  const
  {
++ num;// 编译错误,num值发生变化
  pop();// 编译错误,pop将改变成员变量的值
  return num;


6。2。5 其它建议
(1)不要编写一条过分复杂的语句,紧凑的C++/C代码并不见到能得到高效率的机器代码,却会降低程序的可理解性,程序出错误的几率也会提高。
(2)不要编写集多种功能于一身的函数,在函数的返回值中,不要将正常值和错误标志混在一起。
(3)不要将BOOL值TRUE和FALSE对应于1和0进行编程。大多数编程语言将FALSE定义为0,任何非0值都是TRUE。Visual C++将TRUE定义为1,而Visual Basic则将TRUE定义为…1。示例程序如下:
  BOOLflag;

if(flag){ // do something }// 正确的用法
if(flagTRUE){ // do something }// 危险的用法
if(flag1){ // do something }// 危险的用法
if(!flag){ // do something }// 正确的用法
if(flagFALSE) { // do something }// 不合理的用法
if(flag0){ // do something }// 不合理的用法

(4)小心不要将“= =”写成“=”,编译器不会自动发现这种错误。
(5)不要将123写成0123,后者是八进制的数值。
(6)将自己经常犯的编程错误记录下来,制成表格贴在计算机旁边。

6。3  小 结

C++/C程序设计如同少林寺的武功一样博大精深,我练了8年,大概只学到二三成。所以无论什么时候,都不要觉得自己的编程水平天下第一,看到别人好的技术和风格,要虚心学习。
本章的内容少得可怜,就象口渴时只给你一颗杨梅吃,你一定不过瘾。我借花献佛,推荐一本好书:Marshall P。 Cline著的《C++ FAQs》'Cline 1995'。你看了后一定会赞不绝口。
  会编写C++/C程序,不要因此得意洋洋,这只是程序员基本的技能要求而已。如果把系统分析和系统设计比作“战略决策”,那么编程充其量只是“战术”。如果指挥官是个大笨蛋,士兵再勇敢也会吃败仗。所以我们程序员不要只把眼光盯在程序上,要让自己博学多才。我们应该向北京胡同里的小孩们学习,他们小小年纪就能指点江山,评论世界大事。
奇*書网收集整理
第七章  测试与改错

  编程大师说:“任何一个程序,无论它多么小,总存在着错误。”
   初学者不相信大师的话,他问:“如果一个程序小得只执行一个简单的功能,那会怎样?”
   “这样的一个程序没有意义,”大师说,“但如果这样的程序存在的话,操作系统最后将失效,产生一个错误。”
   但初学者不满足,他问:“如果操作系统不失效,那么会怎样?”
   “没有不失效的操作系统,”大师说,“但如果这样的操作系统存在的话,硬件最后将失效,产生一个错误。”
   初学者仍不满足,再问:“如果硬件不失效,那么会怎样?”
  大师长叹一声道:“没有不失效的硬件。但如果这样的硬件存在的话,用户就会想让那个程序做一件不同的事,这件事也是一个错误。”
   没有错误的程序世间难求。'James 1999'
   
   错误是一种严重的程序缺陷。测试的目的是为了发现尽可能多的缺陷,并期望通过改错来把缺陷统统消灭,以期提高软件的质量。但关于测试与改错实在没有什么高明的方法值得大书特书,也不能表现出程序员的聪明才智。相反地,它们带来了更多的牢骚与痛苦。因此在教学和开发实践中,测试与改错总是被当作万般无奈的工作踢到角落里。
   医生可以把他的错误埋葬在地下了事,但程序员不能。我们必须要学会测试与改错,并且把测试与改错工作做好。
   
7。1 对测试的理解

   测试的道理并不深奥,计算机专业人员都应该明白。但就是这么简单的事,计算机专业的博士们也未必都已经理解。
   有一天,一位比我聪明,编程比我快,学习能力比我强的计算机专业博士生恭恭敬敬地请我坐好,并且史无前例地削了苹果请我吃,为的是向我请教“软件工程”问题。你必定以为这位仁兄好学之极。非也,我和他同事三年来从未探讨过“软件工程”问题。只因为他明天要去应聘,参加面试,生怕被人问倒,就央我当晚为他恶补一把“软件工程”。他还特地问我“什么是白盒测试和黑盒测试?应该由谁来执行?”(有公司曾经这样面试应聘者)当我解释完测试的道理时,他叹了一口气说:“这些玩意儿我读大学十年来都没搞过,怎么能讲得出道理来。唉,就去碰碰运气吧。”我有“兔死狐悲”的感觉。我们这一群博士生三年来尽干些自欺欺人的事,到毕业时学问既不深也不博。个个意志消沉,老气横秋。长此以往,总有一天招聘会的大门前将贴出标语“博士与狗不得入内”。
   以下是关于测试的几个重要观念。

7。1。1 测试的目的
   测试的目的是为了发现尽可能多的缺陷。
   这里缺陷是一种泛称,它可以指功能的错误,也可以指性能低下,易用性差等等。测试总是先假设程序中存在缺陷,再通过执行程序来发现并最终改正缺陷。理解测试的目的是个很重要的意识问题。如果说测试的目的是为了说明程序中没有缺陷,那么测试人员就会向这个目标靠拢,因而下意识地选用一些不易暴露错误的测试示例。这样的测试是虚假的。
   目前高校的科技成果鉴定会普遍存在类似的虚假现象。我在读硕士时就亲身经历过这样的事。我们的项目是研究集成电路制造过程中的成品率问题。当时国内大多数工厂的集成电路成品率只有百分之几,我编写的示例程序可以将集成电路的成品率优化到98%。示例效果是如此的好,以致一位评委(某厂的总工程师)不无讽刺地说:“采用你们的成果,我们可要发大财了。”这个项目就轻易地通过了鉴定,并且不久后获得了电子工业部科技进步二等奖。这就象在考试时通过作弊取得了好成绩而被表扬。我那时尚且纯真,羞愧之余,不禁对高校科研成果的水平和真实性大失所望(现在我已不再失望,因为很少抱希望)。
   一个成功的测试示例在于发现了至今尚未发现的缺陷。
   测试并不仅是个技术问题,更是个职业道德问题。
   
7。1。2 测试的心理要求
   测试主要是由人而不是由机器执行,这就不免与心理因素相关。为了测试的真实性,对测试的心理要求是“无情”。这似乎太残酷了。开发人员不能很好地测试自己的程序是因为做不到无情。而测试人员如果做到了无情却会引起开发人员的愤怒,遭人白眼。
   尽管已经明白了测试的目的是为了发现尽可能多的缺陷,但当测试人员真的发现了一堆缺陷时,却不可乐颠颠地跑去恭喜那个倒霉的开发者,否则会打架的。
   
7。1。3 测试的真理
   测试只能证明缺陷存在,而不能证明缺陷不存在。
   这个真理告诉我们,对于一个复杂的系统而言,无论采取什么样的测试手段都不能证明缺陷已经不复存在。“彻底地测试”只是一种理想。在实践中,测试要考虑时间、费用等限制,不允许无休止地测试。
   
7。1。4 测试与质量的关系
   测试有助于提高软件的质量,但是提高软件的质量不能依赖于测试。测试与质量的关系很象在考试中“检查”与“成绩”的关系。
   学习好的学生,在考试时通过认真检查能减少因疏忽而造成的答题错误,从而“提高”了考试成绩(取得他本来就该得的好成绩)。
   而学习差的学生,他原本就不会做题目,无论检查多么细心,也不能提高成绩。
   所以说,软件的高质量是设计出来的,而不是靠测试修补出来的。
   
 7。2 测试人员的选择

  测试需要开发人员参与吗?
  测试需要独立的测试小组吗?
  测试需要用户参与吗?
  让我们先看一看Microsoft公司关于测试的经验教训,再回答上述问题。

7。2。1 Microsoft公司的经验教训
  在80年代初期,Microsoft公司的许多软件产品出现了“Bug”。比如,在1981年与IBM PC机一起推出的BASIC软件,用户在用“。1”(或者其他数字)除以10时,就会出错。在FORTRAN软件中也存在破坏数据的“Bug”。由此激起了许多采用Microsoft操作系统的PC厂商的极大不满,而且很多个人用户也纷纷投诉。
  Microsoft公司的经理们发觉很有必要引进更好的内部测试与质量控制方法。但是遭到很多程序设计师甚至一些高级经理的坚决反对,他们固执地认为在高校学生、秘书或者外界合作人士的协助下,开发人员可以自己测试产品。在1984年推出Mac机的Multiplan(电子表格软件)之前,Microsoft曾特地请Arthur Anderson咨询公司进行测试。但是外界公司一般没有能力执行全面的软件测试。结果,一种相当厉害的破环数据的“Bug”迫使Microsoft公司为它的2万多名用户免费提供更新版本,代价是每个版本10美元,一共化了20万美元,可谓损失惨重。
  痛定思痛后,Microsoft公司的经理们得出一个结论:如果再不成立独立的测试部门,软件产品就不可能达到更高的质量标准。IBM和其它有着成功的软件开发历史的公司便是效法的榜样。但Microsoft公司并不照搬IBM的经验,而是有选择地采用了一些看起来比较先进的方法,如独立的测试小组,自动测试以及为关键性的构件进行代码复查等。Microsoft公司的一位开发部门主管戴夫·穆尔回忆说:“我们清楚不能再让开发部门自己测试了。我们需要有一个单独的小组来设计测试,运行测试,并把测试信息反馈给开发部门。这是一个伟大的转折点。”
  但是有了独立的测试小组后,并不等于万事大吉了。自从Microsoft公司在1984年与1986年之间扩大了测试小组后,开发人员开始“变懒”了。他们把代码扔在一边等着测试,忘了唯有开发人员自己才能阻止错误的发生、防患于未来。此时,Microsoft公司历史上第二次大灾难降临了。原定于1986年7月发行的Mac机的Word 3。0,千呼万唤方于1987年2月问世。这套软件竟然有700多处错误,有的错误可以破坏数据甚至摧毁程序。一下子就使Microsoft名声扫地。公司不得不为用户免费提供升级版本,费用超过了100万美元。'Cusumano 1995'

7。2。2 测试人员的分工
  从Microsoft公司的教训中可知,公司内部对产品的测试(称为α测试),需要开发人员与独立的测试小组共同参与。开发人员应该执行“白盒”测试,即测试源程序的逻辑结构以及实现细节(“白盒”是指看得见程序的内部结构)。而独立测试小组应该执行“黑盒”测试,即按照规格说明来测试程序是否符合要求(“黑盒”是指看不见程序的内部结构)。比如在测试一个模块时,“白盒”测试方法要对模块的所有代码进行单步跟踪测试。而“黑盒”测试方法只需测试模块的接口是否符合要求,它关心程序的外部表现而不是内部的实现细节。
  小型的软件公司可能没有条件设立独立的测试小组,也有可能测试小组人员不多而忙不过来。这时,可以让开发小组的成员相互测试对方的程序。
  这里要强调的是,α测试不能依赖于开发人员或者测试小组中的任意一方,必须是双方共同参与。“白盒测试”必须由开发者自己执行,因为别的测试人员无法了解到程序的内部实现细节。而“黑盒测试”必须由独立的测试人员执行,因为开发者难以做到客观、公正。开发者在测试自己的程序时存在一些弊病:
(1)开发者对自己的程序印象深刻,并总以为是正确的(自信是应该的)。倘若在设计时就存在理解错误,或因不良的编程习惯而流下隐患,那么他本人很难发现这类错误。
(2)开发者对程序的功能、接口十分熟悉,他自己几乎不可能因为使用不当而引发错误,这与大众用户的情况不太相似,所以自己测试程序难以具备典型性。
  (3)程序设计有如艺术设计,开发者总是喜欢欣赏程序的成功之处,而不愿看到失败之处。让开发者去做“蓄意破坏”的测试,就象杀自己的孩子一样难以接受。即便开发者非常诚实,但“珍爱程序”的心理让他在测试时不知不觉地带入了虚假成份。
  软件产品正式发行前,在公司外部邀请一些用户对产品进行测试,称为β测试。β测试的涉及面最广,最能反映用户的真实愿望,但花费的时间最长,不好控制。一般地,软件公司与β测试人员之间有一种互利的协议。即β测试人员无偿地为软件公司作测试,定期递交测试报告,提出批评与建议。而软件公司将向β测试人员免费赠送或者以很大的优惠价格发行软件的正式版本。

7。3 测试的主要内容与常用方法
   
  有一次文学考试,问高尔基是哪国人。一考生乐极而吟:“尔基啊尔基,你若不姓高,我怎知你是中国人。”这是一种瞎猜法。如果这种方法用于软件测试,人累死也测不出什么结果来。
  不论是对软件的模块还是整个系统,总有共同的内容要测试,如正确性测试,容错性测试,性能与效率测试,易用性测试,文档测试等。“白盒测试”是指开发人员从程序内部对上述内容进行测试,而“黑盒测试”是指独立的测试人员从程序外部对上述内容进行测试。很多软件工程教材讲述了各种各样的测试方法并例举了不少示例'Pressman 1997' 'Sommerville 1992' '杨文
返回目录 上一页 下一页 回到顶部 0 0
快捷操作: 按键盘上方向键 ← 或 → 可快速上下翻页 按键盘上的 Enter 键可回到本书目录页 按键盘上方向键 ↑ 可回到本页顶部!
温馨提示: 温看小说的同时发表评论,说出自己的看法和其它小伙伴们分享也不错哦!发表书评还可以获得积分和经验奖励,认真写原创书评 被采纳为精评可以获得大量金币、积分和经验奖励哦!