现在的位置: 首页 > 综合 > 正文

乱做习题你伤不起啊

2012年09月09日 ⁄ 综合 ⁄ 共 1572字 ⁄ 字号 评论关闭

题目:从键盘输入一个小于1000的正数,要求输出它的平方根(如平方根不是整数,则输出其整数部分)。要求在输入数据后先对其检查是否为小于1000的正数。若不是,则要求重新输入。

#include <stdio.h>

#include <math.h>

#define M 1000

int main( void )

{

  int i , k ;

  printf("请输入一个小于%d的整数i:",M);

  scanf("%d",&i);

  if(i>M)

  {printf("输入的数据不符合要求,请重新输入一个小于%d的整数i:",M);

   scanf("%d",&i);

  }

  k=sqrt(i);

  printf("%d的平方根的整数部分是%d\n",i,k);

  return 0;

}——谭浩强 ,《C程序设计(第四版)学习辅导》,清华大学出版社,2010年7月,p25~26

首先说说题目。编程的题目一般有两种形式:要么描述程序的行为,仅仅要求编程者设计代码;要么纯粹地只描述问题,程序的行为及代码都由编程者设计。前者相当于给出了软件规格说明(Software Specification)。后者则相当于提出了一个软件需求。这个题目无疑属于前一种情况。

软件规格说明应当对软件应满足的要求,以可验证的方式作出完全、精确的描述。

但是题目中的“从键盘输入一个小于1000的正数”却并不是一个完全、精确的描述。程序员在看到这个要求之后不可能知道这个数据究竟应该具有什么样的性质,这个“正数”究竟是整数还是小数?如果不清楚这个,在代码中就无法在确定这个数据的类型。当然也不可能完成程序。

那么,自作聪明地假设一个怎么样?对不起,这是一种职业恶习,完全背离程序员的职业的基本准则。如果学习编程的结果是养成了一种职业恶习,显然与学习编程的初衷南辕北辙。因此这样的题目简直就是打着红旗反红旗。

描述程序的行为的题目中可能涉及到输入。输入是由程序用户完成的,用户的输入可能正确也可能有错误。

如果考虑到程序的强健性,题目通常要求程序考虑用户输入有错误的情况。如果不考虑程序的强健性,那么代码可以只考虑用户输入没有错误的情况。通常,题目要么要求编程者考虑强健性,要么不考虑强健性。

从题目中的“检查是否为小于1000的正数”来看,题目显然是要求程序具有一定的强健性。然而题目却没有说明在输入不满足的情况下程序应有的行为——即第二次输入不小于1000的正数时程序的行为,所以这个题目本身就是不完整的。

既然要求考虑健壮性,就应该把这个意图贯彻始终。不能虎头蛇尾,前后自相矛盾。因而针对用户输入不满足的“正数”的情况下程序的行为,题目也应该给出相应的说明。然而题目中对此却只字未提,毫无疑问,这个题目本身就是一个不合格的题目。

求解烂题危害很大,因为烂题本身就是违背程序员根本职业要求——周密、严谨。解这样的题目,一无所获不说,反而有伤自身的素质,而得到的代码也必然似是而非,经不起推敲。

测试一下前面引文中的代码就不难发现,当输入“-1”时,程序立刻崩溃——这个程序无比脆弱。然而自相矛盾的是题目却暗示需要考虑程序的健壮性。

此外当第一次输入大于等于1000的数,且第二次依然输入大于等于1000的数的情况下,程序依然能给出结果。代码中的那句if语句在这种情况下竟然毫无意义。这样的代码毫无价值。

结论就:路边的野花不要采,书上的滥题不要做。初学者,乱做习题你伤不起啊!!!!!!!
此外需要指出的是,代码中的

“k=sqrt(i);”
也是一种武断的错误写法,它是建立在sqrt(i)得到的值一定大于或等于i的平方根这个假设之上的,然而这个假设没有任何依据。

“要求输出它的平方根(如平方根不是整数,则输出其整数部分)”,这句话也说的缺乏素质,至少不够简洁。无非就是输出它平方根的整数部分么,如此简单的意思怎么会说的那么复杂且啰嗦不清呢?

抱歉!评论已关闭.