滥用变量综合症

    1.假如我国国民生产总值的年增长率为10%,计算10年后我国国民经济生产总值与现在相比增长多少百分比。计算公式为:

              p=(1+r)^n                                                                                                                              

 r为年增长率,n为年数,p为与现在相比的倍数。                                                                                                    

    解:从附录D(库函数)可以查到: 可以用pow函数求x^y的值,调用pow函数的具体形式是pow(x,y)。在使用pow函数时需要在程序的开头用#include指令将  <math.h>头文件包含到本程序模块中。可以用下面的程序求出10年后国民生产总值是现在的多少倍。

     #include <stdio.h>                                                                                                
    #include <math.h>                                                                                                           
    int main()                                                                                                                                                               
    {float p,r,n;                                                                                                                                                                     
      r=0.1;                                                                                                                                                          
      n=10;                                                                                                                                                                
      p=pow(1+r,n);                                                                                                              
      printf("p=%f\n",p);                                                                                                                                                             
      return 0;                                                                                                                                                                            
     }                                                                                                                                              
    运行结果:                         
    p=2.593742    
即10年后国民生产总值是现在的2.593742倍。

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

 

     这个解答至少存在如下几方面的问题:
1.驴唇不对马嘴
    从小学开始,老师就会教导我们不要答非所问。这个程序犯的第一个错误就是答非所问。
    题目中要求“计算10年后我国国民经济生产总值与现在相比增长多少百分比”,然而程序给出的结果却是“10年后国民生产总值是现在的2.593742倍”。程序错没错,小学生都知道。
    写程序最基本的一个常识是,要满足功能要求。不能装疯卖傻,指东打西。
    把功能要求撇在一边,自说自话、自娱自乐且像盲人骑瞎马一样地写代码,是头脑不清的表现。这样的代码把小学老师多年的辛勤教诲毁之于一旦,是教小朋友学坏。

2.古怪的常数
    10%、10这两个数是问题给出的条件,这种数据通常应该写成符号常量的形式
      #define GROWTH_RATE ((double)10/(double)100)
      #define YEARS 10
    这是良好的编程习惯。这样的好处至少有以下三点:
    1).在某种程度上实现了数据与代码的分离,“把上帝的还给上帝,把魔鬼的交给魔鬼”。这是现代程序设计的一个基本思想。那种把数据和代码不分青红皂白地搅和在一起“乱炖”的写法,是缺乏基本编程素养的表现。
    2).代码更具有可读性。显然“r=GROWTH_RATE;”的写法要比“r=0.1;”要好的多。  
    3).便于测试。只要将
      #define YEARS 10
稍做修改就可以测试其他年(比如1年)后的情况。注意,这个修改是在预处理命令部分进行的,因此对main()中的代码没有任何影响。这从另一个角度表明了把数据与代码分离开的优越性。

3.滥用变量
    很容易看出,代码中的那个变量p是压根不必要的。这个p变量唯一起到的作用是记录“pow(1+r,n)” 的值完成输出,然而“pow(1+r,n)” 本身既然有值,为什么不直接输出呢?printf("p=%f\n",pow(1+r,n));不是很漂亮的一条语句吗?何必画蛇添足地定义一个p呢?
    同理,r与n这两个变量也是毫无必要的,因为代码根本就不需要这两个值改变,pow(1+0.1,(double)10)的作用和pow(1+r,n)完全一样。所以定义r与n这两个变量纯属于脱裤子放屁,多此一举,是糊里糊涂、莫名其妙的写法。
    或问,pow(1+r,n)写起来不是比 pow( 1 + 0.1 ,(double)10)更简洁么?不然。常量就是常量,变量就是变量,把常量的值赋值给变量,利用变量的值进行运算事实上增加了代码出错的风险,因为变量的值可能无意中被错误地被改变,而且毫无意义地浪费内存资源。用增加错误风险和浪费资源的代价来换取代码的简洁不是正路子。

4.数据类型的问题
    代码中的p、n、r被定义成了float类型,然而 0.1、pow(1+r,n)都是double类型,在
      r=0.1
      p=pow(1+r,n)  
    这两个赋值表达式中基本上必然会产生精度损失。这种精度牺牲非常无谓,没有任何回报
 
5.题解中说“将<math.h>头文件包含到本程序模块中”,抱歉,谭大爷,“<”和“>”怎么竟然成了文件名的一部分?这两个符号可以出现在文件名中吗?那是预处理命令的成分,根本不是文件名的组成成分

6.不规范
  C标准中提到main()的写法有两种
  int main(void){/**/}
  和
  int main(int argc,char *agrv[]){/**/}
  把“()”内的形参内容省略,不符合规范

 

  最后,给出一个参考代码:

 

  #include <stdio.h>
  #include <math.h>

  #define GROWTH_RATE ( (double)10 / (double)100 )
  #define YEARS       10

  int main( void )
  {

    printf ( "%d年后我国国民经济生产总值比现在增长 %f%%\n" ,
                YEARS ,
               ( pow ( 1. + GROWTH_RATE , ( double ) YEARS ) - 1. ) / 1. * 100.
            ) ;

    return 0;
  }

 

posted @ 2011-01-20 22:54  garbageMan  阅读(3236)  评论(64编辑  收藏  举报