切换到宽版
  • 9432阅读
  • 7回复

大家来看看,好东西 [复制链接]

上一主题 下一主题
离线绝世衰神
 
只看楼主 倒序阅读 0 发表于: 2008-02-01
  程序的灵魂—算法
一个程序应包括:
        对数据的描述。在程序中要指定数据的类型和数据的组织形式,即数据结构(data structure)。
        对操作的描述。即操作步骤,也就是算法(algorithm)。
Nikiklaus Wirth提出的公式:
数据结构+算法=程序
教材认为:
程序=算法+数据结构+程序设计方法+语言工具和环境
这4个方面是一个程序涉及人员所应具备的知识。
本课程的目的是使同学知道怎样编写一个C程序,进行编写程序的初步训练,因此,只介绍算法的初步知识。
2.1    算法的概念
做任何事情都有一定的步骤。为解决一个问题而采取的方法和步骤,就称为算法。
        计算机算法:计算机能够执行的算法。
        计算机算法可分为两大类:
        数值运算算法:求解数值;
        非数值运算算法:事务管理领域。
2.2    简单算法举例
【例2.1】求1×2×3×4×5。
最原始方法:
步骤1:先求1×2,得到结果2。
步骤2:将步骤1得到的乘积2乘以3,得到结果6。
步骤3:将6再乘以4,得24。
步骤4:将24再乘以5,得120。
这样的算法虽然正确,但太繁。
改进的算法:
S1: 使t=1
S2: 使i=2
S3: 使t×i, 乘积仍然放在在变量t中,可表示为t×i→t
S4: 使i的值+1,即i+1→i
S5: 如果i≤5, 返回重新执行步骤S3以及其后的S4和S5;否则,算法结束。
如果计算100!只需将S5:若i≤5改成i≤100即可。
如果该求1×3×5×7×9×11,算法也只需做很少的改动:
S1: 1→t
S2: 3→i
S3: t×i→t
S4: i+2→t
S5:若i≤11, 返回S3,否则,结束。
该算法不仅正确,而且是计算机较好的算法,因为计算机是高速运算的自动机器,实现循环轻而易举。
思考:若将 S5写成:S5:若i<11, 返回S3;否则,结束。
【例2.2】有50个学生,要求将他们之中成绩在80分以上者打印出来。
如果,n表示学生学号,ni表示第个学生学号;g表示学生成绩,gi表示第个学生成绩;
则算法可表示如下:
S1: 1→i
S2: 如果gi≥80,则打印ni和gi,否则不打印
S3: i+1→i
S4:若i≤50, 返回S2,否则,结束。
【例2.3】判定2000 — 2500年中的每一年是否闰年,将结果输出。
润年的条件:
1)        能被4整除,但不能被100整除的年份;
2)        能被100整除,又能被400整除的年份;
设y为被检测的年份,则算法可表示如下:
S1: 2000→y
S2:若y不能被4整除,则输出y“不是闰年”,然后转到S6
S3:若y能被4整除,不能被100整除,则输出y“是闰年”,然后转到S6
S4:若y能被100整除,又能被400整除,输出y“是闰年” 否则输出y“不是闰年”,然后转到S6
S5:输出y“不是闰年”。
S6:y+1→y
S7:当y≤2500时, 返回S2继续执行,否则,结束。

【例2.4】求 。
算法可表示如下:
S1: sigh=1
S2: sum=1
S3: deno=2
S4: sigh=(-1)×sigh
S5: term= sigh×(1/deno )
S6: term=sum+term
S7: deno= deno +1
S8:若deno≤100,返回S4;否则,结束。
【例2.5】对一个大于或等于3的正整数,判断它是不是一个素数。
算法可表示如下:
S1: 输入n的值
S2: i=2
S3: n被i除,得余数r
S4:如果r=0,表示n能被i整除,则打印n“不是素数”,算法结束;否则执行S5
S5: i+1→i
S6:如果i≤n-1,返回S3;否则打印n“是素数”;然后算法结束。
改进:
S6:如果i≤ ,返回S3;否则打印n“是素数”;然后算法结束。
2.3    算法的特性
        有穷性:一个算法应包含有限的操作步骤而不能是无限的。 
        确定性:算法中每一个步骤应当是确定的,而不能应当是含糊的、模棱两可的。
        有零个或多个输入。
        有一个或多个输出。
        有效性:算法中每一个步骤应当能有效地执行,并得到确定的结果。
对于程序设计人员,必须会设计算法,并根据算法写出程序。
2.4    怎样表示一个算法
2.4.1  用自然语言表示算法
除了很简单的问题,一般不用自然语言表示算法。
2.4.2  用流程图表示算法
流程图表示算法,直观形象,易于理解。

【例2.6】将例2.1求5!的算用流程图表示。

【例2.7】将例2.2的算用流程图表示。

【例2.8】将例2.3判定闰年的算用流程图表示。

【例2.9】将例2.4求 的算用流程图表示。
一个流程图包括:
1.        表示相应操作的框;
2.        带箭头的流程线;
3.        框内外必要的文字说明。
2.4.3  三种基本结构和改进的流程图
1.        顺序结构:

2.        选择结构:


3.        循环结构



三种基本结构的共同特点:
        只有一个入口;
        只有一个出口;
        结构内的每一部分都有机会被执行到;
        结构内不存在“死循环”。
2.4.4  用N-S流程图表示算法
1973年美国学者提出了一种新型流程图:N-S流程图。
顺序结构:

选择结构:

循环结构:


2.4.5  用伪代码表示算法
伪代码使用介于自然语言和计算机语言之间的文字和符号来描述算法。
2.4.6  用计算机语言表示算法
        我们的任务是用计算机解题,就是用计算机实现算法;
        用计算机语言表示算法必须严格遵循所用语言的语法规则。
【例2.20】求1×2×3×4×5用C语言表示。
main()
{int i,t;
t=1;
i=2;
while(i<=5)
{t=t*i;
i=i+1;
}
printf(“%d”,t);
}

【例2.21】求级数的值。
main()
{
int sigh=1;
float deno=2.0,sum=1.0,term;
while(deno<=100)
{ sigh= -sigh;
term= sigh/ deno;
sum=sum+term;
deno=deno+1;
}
printf(“%f”,sum);
}

2.5    结构化程序设计方法
            自顶向下;
            逐步细化;
            模块化设计;
            结构化编码。
[ 此贴被绝世衰神在2008-02-01 21:37重新编辑 ]
天生我材必有用
老鼠儿子会打洞
离线绝世衰神
只看该作者 1 发表于: 2008-02-01
在网上搜集到的,希望对大家有好处。
好的话就帮忙顶一下吧~
天生我材必有用
老鼠儿子会打洞
离线绝世衰神
只看该作者 2 发表于: 2008-02-01
3      数据类型、运算符与表达式
3.1    C语言的数据类型
在第一章中,我们已经看到程序中使用的各种变量都应预先加以定义,即先定义,后使用。对变量的定义可以包括三个方面:
•数据类型
    •存储类型
•作用域
在本章中,我们只介绍数据类型的说明。其它说明在以后各章中陆续介绍。所谓数据类型是按被定义变量的性质,表示形式,占据存储空间的多少,构造特点来划分的。在C语言中,数据类型可分为:基本数据类型,构造数据类型,指针类型,空类型四大类。

1.        基本数据类型:基本数据类型最主要的特点是,其值不可以再分解为其它类型。也就是说,基本数据类型是自我说明的。
2.        构造数据类型:构造数据类型是根据已定义的一个或多个数据类型用构造的方法来定义的。也就是说,一个构造类型的值可以分解成若干个“成员”或“元素”。每个“成员”都是一个基本数据类型或又是一个构造类型。在C语言中,构造类型有以下几种:
    •数组类型
    •结构体类型
    •共用体(联合)类型
3.        指针类型:指针是一种特殊的,同时又是具有重要作用的数据类型。其值用来表示某个变量在内存储器中的地址。虽然指针变量的取值类似于整型量,但这是两个类型完全不同的量,因此不能混为一谈。
4.        空类型:在调用函数值时,通常应向调用者返回一个函数值。这个返回的函数值是具有一定的数据类型的,应在函数定义及函数说明中给以说明,例如在例题中给出的max函数定义中,函数头为:int max(int a,int b);其中“int ”类型说明符即表示该函数的返回值为整型量。又如在例题中,使用了库函数sin,由于系统规定其函数返回值为双精度浮点型,因此在赋值语句s=sin (x);中,s 也必须是双精度浮点型,以便与sin函数的返回值一致。所以在说明部分,把s说明为双精度浮点型。但是,也有一类函数,调用后并不需要向调用者返回函数值,这种函数可以定义为“空类型”。其类型说明符为void。在后面函数中还要详细介绍。
在本章中,我们先介绍基本数据类型中的整型、浮点型和字符型。其余类型在以后各章中陆续介绍。
3.2    常量与变量
对于基本数据类型量,按其取值是否可改变又分为常量和变量两种。在程序执行过程中,其值不发生改变的量称为常量,其值可变的量称为变量。它们可与数据类型结合起来分类。例如,可分为整型常量、整型变量、浮点常量、浮点变量、字符常量、字符变量、枚举常量、枚举变量。在程序中,常量是可以不经说明而直接引用的,而变量则必须先定义后使用。
整型量包括整型常量、整型变量。
3.2.1  常量和符号常量
在程序执行过程中,其值不发生改变的量称为常量。
        直接常量(字面常量):
        整型常量:12、0、-3;
        实型常量:4.6、-1.23;
        字符常量:‘a’、‘b’。
        标识符:用来标识变量名、符号常量名、函数名、数组名、类型名、文件名的有效字符序列。
        符号常量:用标示符代表一个常量。在C语言中,可以用一个标识符来表示一个常量,称之为符号常量。
符号常量在使用之前必须先定义,其一般形式为:
#define 标识符 常量
其中#define也是一条预处理命令(预处理命令都以"#"开头),称为宏定义命令(在后面预处理程序中将进一步介绍),其功能是把该标识符定义为其后的常量值。一经定义,以后在程序中所有出现该标识符的地方均代之以该常量值。
        习惯上符号常量的标识符用大写字母,变量标识符用小写字母,以示区别。
【例3.1】符号常量的使用。
#define PRICE 30
main()
{
  int num,total;
num=10;
total=num* PRICE;
printf(“total=%d”,total);
}

        用标识符代表一个常量,称为符号常量。
        符号常量与变量不同,它的值在其作用域内不能改变,也不能再被赋值。
        使用符号常量的好处是:
        含义清楚;
        能做到“一改全改”。
3.2.2  变量
其值可以改变的量称为变量。一个变量应该有一个名字,在内存中占据一定的存储单元。变量定义必须放在变量使用之前。一般放在函数体的开头部分。要区分变量名和变量值是两个不同的概念。

3.3    整型数据
3.3.1  整型常量的表示方法
整型常量就是整常数。在C语言中,使用的整常数有八进制、十六进制和十进制三种。
1)        十进制整常数:十进制整常数没有前缀。其数码为0~9。
以下各数是合法的十进制整常数:
237、-568、65535、1627;
以下各数不是合法的十进制整常数:
023 (不能有前导0)、23D (含有非十进制数码)。
在程序中是根据前缀来区分各种进制数的。因此在书写常数时不要把前缀弄错造成结果不正确。
2)        八进制整常数:八进制整常数必须以0开头,即以0作为八进制数的前缀。数码取值为0~7。八进制数通常是无符号数。
以下各数是合法的八进制数:
015(十进制为13)、0101(十进制为65)、0177777(十进制为65535);
以下各数不是合法的八进制数:
256(无前缀0)、03A2(包含了非八进制数码)、-0127(出现了负号)。
3)        十六进制整常数:十六进制整常数的前缀为0X或0x。其数码取值为0~9,A~F或a~f。
以下各数是合法的十六进制整常数:
0X2A(十进制为42)、0XA0 (十进制为160)、0XFFFF (十进制为65535);
以下各数不是合法的十六进制整常数:
5A (无前缀0X)、0X3H (含有非十六进制数码)。
4)        整型常数的后缀:在16位字长的机器上,基本整型的长度也为16位,因此表示的数的范围也是有限定的。十进制无符号整常数的范围为0~65535,有符号数为-32768~+32767。八进制无符号数的表示范围为0~0177777。十六进制无符号数的表示范围为0X0~0XFFFF或0x0~0xFFFF。如果使用的数超过了上述范围,就必须用长整型数来表示。长整型数是用后缀“L”或“l”来表示的。
例如:
十进制长整常数:
158L (十进制为158)、358000L (十进制为358000);
八进制长整常数:
012L (十进制为10)、077L (十进制为63)、0200000L (十进制为65536);
十六进制长整常数:
0X15L (十进制为21)、0XA5L (十进制为165)、0X10000L (十进制为65536)。
长整数158L和基本整常数158 在数值上并无区别。但对158L,因为是长整型量,C编译系统将为它分配4个字节存储空间。而对158,因为是基本整型,只分配2 个字节的存储空间。因此在运算和输出格式上要予以注意,避免出错。
无符号数也可用后缀表示,整型常数的无符号数的后缀为“U”或“u”。
例如:
358u,0x38Au,235Lu均为无符号数。
前缀,后缀可同时使用以表示各种类型的数。如0XA5Lu表示十六进制无符号长整数A5,其十进制为165。
3.3.2  整型变量
1.        整型数据在内存中的存放形式
如果定义了一个整型变量i:
int i;
i=10;

i  10

0    0    0    0    0    0    0    0    0    0    0    0    1    0    1    0

数值是以补码表示的:
        正数的补码和原码相同;
        负数的补码:将该数的绝对值的二进制形式按位取反再加1。
例如:
求-10的补码:
10的原码:
0    0    0    0    0    0    0    0    0    0    0    0    1    0    1    0
        取反:
1    1    1    1    1    1    1    1    1    1    1    1    0    1    0    1
再加1,得-10的补码:
1    1    1    1    1    1    1    1    1    1    1    1    0    1    1    0
由此可知,左面的第一位是表示符号的。
2.        整型变量的分类
1)        基本型:类型说明符为int,在内存中占2个字节。
2)        短整量:类型说明符为short int或short。所占字节和取值范围均与基本型相同。
3)        长整型:类型说明符为long int或long,在内存中占4个字节。
4)        无符号型:类型说明符为unsigned。
无符号型又可与上述三种类型匹配而构成:
        无符号基本型:类型说明符为unsigned int或unsigned。
        无符号短整型:类型说明符为unsigned short。
        无符号长整型:类型说明符为unsigned long。
各种无符号类型量所占的内存空间字节数与相应的有符号类型量相同。但由于省去了符号位,故不能表示负数。
有符号整型变量:最大表示32767
0    1    1    1    1    1    1    1    1    1    1    1    1    1    1    1
无符号整型变量:最大表示65535
1    1    1    1    1    1    1    1    1    1    1    1    1    1    1    1

    下表列出了Turbo C中各类整型量所分配的内存字节数及数的表示范围。
类型说明符    数的范围    字节数
int    -32768~32767          即-215~(215-1)    2
unsigned int    0~65535              即0~(216-1)    2
short int    -32768~32767          即-215~(215-1)    2
unsigned short int    0~65535              即0~(216-1)    2
long int    -2147483648~2147483647即-231~(231-1)    4
unsigned long    0~4294967295        即0~(232-1)    4

以13为例:
int型:
00    00    00    00    00    00    11    01
short int型:
00    00    00    00    00    00    11    01
long int型:
00    00    00    00    00    00    00    00    00    00    00    00    00    00    11    01
unsigned int型:
00    00    00    00    00    00    11    01
unsigned short int型:
00    00    00    00    00    00    11    01
unsigned long int型:
00    00    00    00    00    00    00    00    00    00    00    00    00    00    11    01

3.        整型变量的定义
变量定义的一般形式为:
类型说明符  变量名标识符,变量名标识符,...;
例如:
    int a,b,c; (a,b,c为整型变量)
    long x,y; (x,y为长整型变量)
unsigned p,q; (p,q为无符号整型变量)
在书写变量定义时,应注意以下几点:
        允许在一个类型说明符后,定义多个相同类型的变量。各变量名之间用逗号间隔。类型说明符与变量名之间至少用一个空格间隔。
        最后一个变量名之后必须以“;”号结尾。
        变量定义必须放在变量使用之前。一般放在函数体的开头部分。
【例3.2】整型变量的定义与使用。
main()
{
int a,b,c,d;
unsigned u;
a=12;b=-24;u=10;
c=a+u;d=b+u;
printf(“a+u=%d,b+u=%d\n”,c,d);
}

4.        整型数据的溢出
【例3.3】整型数据的溢出。
main()
{
  int a,b;
  a=32767;
  b=a+1;
  printf("%d,%d\n",a,b);
}

32767:
0    1    1    1    1    1    1    1    1    1    1    1    1    1    1    1
-32768
1    0    0    0    0    0    0    0    0    0    0    0    0    0    0    0
【例3.4】
main(){
  long x,y;
  int a,b,c,d;
  x=5;
  y=6;
  a=7;
  b=8;
  c=x+a;
  d=y+b;
  printf("c=x+a=%d,d=y+b=%d\n",c,d);
}

从程序中可以看到:x, y是长整型变量,a, b是基本整型变量。它们之间允许进行运算,运算结果为长整型。但c,d被定义为基本整型,因此最后结果为基本整型。本例说明,不同类型的量可以参与运算并相互赋值。其中的类型转换是由编译系统自动完成的。有关类型转换的规则将在以后介绍。
3.4    实型数据
3.4.1  实型常量的表示方法
实型也称为浮点型。实型常量也称为实数或者浮点数。在C语言中,实数只采用十进制。它有二种形式:十进制小数形式,指数形式。
1)        十进制数形式:由数码0~ 9和小数点组成。
例如:
0.0、25.0、5.789、0.13、5.0、300.、-267.8230
等均为合法的实数。注意,必须有小数点。
2)        指数形式:由十进制数,加阶码标志“e”或“E”以及阶码(只能为整数,可以带符号)组成。
其一般形式为:
a E n(a为十进制数,n为十进制整数)
其值为 a*10n。
如:
2.1E5 (等于2.1*105)
3.7E-2 (等于3.7*10-2)
0.5E7 (等于0.5*107)
-2.8E-2 (等于-2.8*10-2)
以下不是合法的实数:
345 (无小数点)
E7 (阶码标志E之前无数字)
-5 (无阶码标志)
53.-E3 (负号位置不对)
2.7E  (无阶码)
标准C允许浮点数使用后缀。后缀为“f”或“F”即表示该数为浮点数。如356f和356.是等价的。
【例3.5】说明了这种情况。
main(){
  printf("%f\n ",356.);
  printf("%f\n ",356);
  printf("%f\n ",356f);
}

3.4.2  实型变量
1.      实型数据在内存中的存放形式
实型数据一般占4个字节(32位)内存空间。按指数形式存储。实数3.14159在内存中的存放形式如下:
+    .314159    1
          数符          小数部分                    指数
        小数部分占的位(bit)数愈多,数的有效数字愈多,精度愈高。
        指数部分占的位数愈多,则能表示的数值范围愈大。
2.      实型变量的分类
实型变量分为:单精度(float型)、双精度(double型)和长双精度(long double型)三类。
在Turbo C中单精度型占4个字节(32位)内存空间,其数值范围为3.4E-38~3.4E+38,只能提供七位有效数字。双精度型占8 个字节(64位)内存空间,其数值范围为1.7E-308~1.7E+308,可提供16位有效数字。
类型说明符    比特数(字节数)    有效数字    数的范围
float    32(4)    6~7    10-37~1038         
double    64(8)    15~16    10-307~10308
long double     128(16)    18~19    10-4931~104932
    实型变量定义的格式和书写规则与整型相同。
例如:
     float x,y; (x,y为单精度实型量)
double a,b,c; (a,b,c为双精度实型量)
3.      实型数据的舍入误差
由于实型变量是由有限的存储单元组成的,因此能提供的有效数字总是有限的。如下例。
【例3.6】实型数据的舍入误差。
main()
{float a,b;
a=123456.789e5;
b=a+20
printf("%f\n",a);
printf("%f\n",b);
}

注意:1.0/3*3的结果并不等于1。
【例3.7】
main()
{
  float a;
  double b;
  a=33333.33333;
  b=33333.33333333333333;
  printf("%f\n%f\n",a,b);
}

        从本例可以看出,由于a 是单精度浮点型,有效位数只有七位。而整数已占五位,故小数二位后之后均为无效数字。
        b 是双精度型,有效位为十六位。但Turbo C 规定小数后最多保留六位,其余部分四舍五入。
3.4.3  实型常数的类型
实型常数不分单、双精度,都按双精度double型处理。
3.5    字符型数据
字符型数据包括字符常量和字符变量。
3.5.1  字符常量
字符常量是用单引号括起来的一个字符。
例如:
'a'、'b'、'='、'+'、'?'
都是合法字符常量。
在C语言中,字符常量有以下特点:
1)        字符常量只能用单引号括起来,不能用双引号或其它括号。
2)        字符常量只能是单个字符,不能是字符串。
3)        字符可以是字符集中任意字符。但数字被定义为字符型之后就不能参与数值运算。如'5'和5 是不同的。'5'是字符常量,不能参与运算。
3.5.2  转义字符
    转义字符是一种特殊的字符常量。转义字符以反斜线"\"开头,后跟一个或几个字符。转义字符具有特定的含义,不同于字符原有的意义,故称“转义”字符。例如,在前面各例题printf函数的格式串中用到的“\n”就是一个转义字符,其意义是“回车换行”。转义字符主要用来表示那些用一般字符不便于表示的控制代码。
常用的转义字符及其含义
转义字符    转义字符的意义    ASCII代码
    \n    回车换行    10
    \t    横向跳到下一制表位置    9
    \b    退格    8
    \r    回车    13
    \f    走纸换页    12
    \\    反斜线符"\"    92
    \'    单引号符    39
\”    双引号符    34
    \a    鸣铃    7
    \ddd    1~3位八进制数所代表的字符    
    \xhh    1~2位十六进制数所代表的字符    
广义地讲,C语言字符集中的任何一个字符均可用转义字符来表示。表中的\ddd和\xhh正是为此而提出的。ddd和hh分别为八进制和十六进制的ASCII代码。如\101表示字母"A" ,\102表示字母"B",\134表示反斜线,\XOA表示换行等。
【例3.8】转义字符的使用。
main()
{
  int a,b,c;
  a=5; b=6; c=7;
  printf(“  ab  c\tde\rf\n”);
printf(“hijk\tL\bM\n”);
}

3.5.3  字符变量
字符变量用来存储字符常量,即单个字符。
字符变量的类型说明符是char。字符变量类型定义的格式和书写规则都与整型变量相同。例如:
char a,b;
3.5.4  字符数据在内存中的存储形式及使用方法
每个字符变量被分配一个字节的内存空间,因此只能存放一个字符。字符值是以ASCII码的形式存放在变量的内存单元之中的。
如x的十进制ASCII码是120,y的十进制ASCII码是121。对字符变量a,b赋予'x'和'y'值:
a='x';
    b='y';
实际上是在a,b两个单元内存放120和121的二进制代码:
a:
0    1    1    1    1    0    0    0
b:
0    1    1    1    1    0    0    1

所以也可以把它们看成是整型量。C语言允许对整型变量赋以字符值,也允许对字符变量赋以整型值。在输出时,允许把字符变量按整型量输出,也允许把整型量按字符量输出。
整型量为二字节量,字符量为单字节量,当整型量按字符型量处理时,只有低八位字节参与处理。
【例3.9】向字符变量赋以整数。
main()
{
  char a,b;
  a=120;
  b=121;
  printf("%c,%c\n",a,b);
printf("%d,%d\n",a,b);
}
   
本程序中定义a,b为字符型,但在赋值语句中赋以整型值。从结果看,a,b值的输出形式取决于printf函数格式串中的格式符,当格式符为"c"时,对应输出的变量值为字符,当格式符为"d"时,对应输出的变量值为整数。
【例3.10】
main()
{
  char a,b;
  a='a';
  b='b';
  a=a-32;
  b=b-32;
  printf("%c,%c\n%d,%d\n",a,b,a,b);
}

本例中,a,b被说明为字符变量并赋予字符值,C语言允许字符变量参与数值运算,即用字符的ASCII 码参与运算。由于大小写字母的ASCII 码相差32,因此运算后把小写字母换成大写字母。然后分别以整型和字符型输出。
3.5.5  字符串常量
字符串常量是由一对双引号括起的字符序列。例如: "CHINA" , “C program” , "$12.5" 等都是合法的字符串常量。
字符串常量和字符常量是不同的量。它们之间主要有以下区别:
1)        字符常量由单引号括起来,字符串常量由双引号括起来。
2)        字符常量只能是单个字符,字符串常量则可以含一个或多个字符。
3)        可以把一个字符常量赋予一个字符变量,但不能把一个字符串常量赋予一个字符变量。在C语言中没有相应的字符串变量。这是与BASIC 语言不同的。但是可以用一个字符数组来存放一个字符串常量。在数组一章内予以介绍。
4)        字符常量占一个字节的内存空间。字符串常量占的内存字节数等于字符串中字节数加1。增加的一个字节中存放字符"\0" (ASCII码为0)。这是字符串结束的标志。
例如:
字符串 "C program" 在内存中所占的字节为:
C         p    r    o    g    r    a    m    \0
字符常量'a'和字符串常量"a"虽然都只有一个字符,但在内存中的情况是不同的。
'a'在内存中占一个字节,可表示为:
a
"a"在内存中占二个字节,可表示为:
a    \0
   
3.6    变量赋初值
在程序中常常需要对变量赋初值,以便使用变量。语言程序中可有多种方法为变量提供初值。本小节先介绍在作变量定义的同时给变量赋以初值的方法。这种方法称为初始化。在变量定义中赋初值的一般形式为:
    类型说明符 变量1= 值1,变量2= 值2,……;
例如:
int a=3;
int b,c=5;
    float x=3.2,y=3f,z=0.75;
char ch1='K',ch2='P';
应注意,在定义中不允许连续赋值,如a=b=c=5是不合法的。
【例3.11】
main()
{
  int a=3,b,c=5;
  b=a+c;
  printf("a=%d,b=%d,c=%d\n",a,b,c);
}

3.7    各类数值型数据之间的混合运算
变量的数据类型是可以转换的。转换的方法有两种,一种是自动转换,一种是强制转换。自动转换发生在不同数据类型的量混合运算时,由编译系统自动完成。自动转换遵循以下规则:
1)        若参与运算量的类型不同,则先转换成同一类型,然后进行运算。
2)        转换按数据长度增加的方向进行,以保证精度不降低。如int型和long型运算时,先把int量转成long型后再进行运算。
3)        所有的浮点运算都是以双精度进行的,即使仅含float单精度量运算的表达式,也要先转换成double型,再作运算。
4)        char型和short型参与运算时,必须先转换成int型。
5)        在赋值运算中,赋值号两边量的数据类型不同时,赋值号右边量的类型将转换为左边量的类型。如果右边量的数据类型长度左边长时,将丢失一部分数据,这样会降低精度,丢失的部分按四舍五入向前舍入。
下图表示了类型自动转换的规则。

【例3.12】
main(){
  float PI=3.14159;
  int s,r=5;
  s=r*r*PI;
  printf("s=%d\n",s);
}

本例程序中,PI为实型;s,r为整型。在执行s=r*r*PI语句时,r和PI都转换成double型计算,结果也为double型。但由于s为整型,故赋值结果仍为整型,舍去了小数部分。
强制类型转换
强制类型转换是通过类型转换运算来实现的。
其一般形式为:
    (类型说明符)  (表达式)
其功能是把表达式的运算结果强制转换成类型说明符所表示的类型。
例如:
    (float) a      把a转换为实型
        (int)(x+y)    把x+y的结果转换为整型
在使用强制转换时应注意以下问题:
1)        类型说明符和表达式都必须加括号(单个变量可以不加括号),如把(int)(x+y)写成(int)x+y则成了把x转换成int型之后再与y相加了。
2)        无论是强制转换或是自动转换,都只是为了本次运算的需要而对变量的数据长度进行的临时性转换,而不改变数据说明时对该变量定义的类型。
【例3.13】
main(){
  float f=5.75;
  printf("(int)f=%d,f=%f\n",(int)f,f);
}

    本例表明,f虽强制转为int型,但只在运算中起作用,是临时的,而f本身的类型并不改变。因此,(int)f的值为 5(删去了小数)而f的值仍为5.75。
3.8    算术运算符和算术表达式
    C语言中运算符和表达式数量之多,在高级语言中是少见的。正是丰富的运算符和表达式使C语言功能十分完善。这也是C语言的主要特点之一。
    C语言的运算符不仅具有不同的优先级,而且还有一个特点,就是它的结合性。在表达式中,各运算量参与运算的先后顺序不仅要遵守运算符优先级别的规定,还要受运算符结合性的制约,以便确定是自左向右进行运算还是自右向左进行运算。这种结合性是其它高级语言的运算符所没有的,因此也增加了C语言的复杂性。
3.8.1  C运算符简介
C语言的运算符可分为以下几类:
1.      算术运算符:用于各类数值运算。包括加(+)、减(-)、乘(*)、除(/)、求余(或称模运算,%)、自增(++)、自减(--)共七种。
2.      关系运算符:用于比较运算。包括大于(>)、小于(<)、等于(==)、 大于等于(>=)、小于等于(<=)和不等于(!=)六种。
3.      逻辑运算符:用于逻辑运算。包括与(&&)、或(||)、非(!)三种。
4.      位操作运算符:参与运算的量,按二进制位进行运算。包括位与(&)、位或(|)、位非(~)、位异或(^)、左移(<<)、右移(>>)六种。
5.      赋值运算符:用于赋值运算,分为简单赋值(=)、复合算术赋值(+=,-=,*=,/=,%=)和复合位运算赋值(&=,|=,^=,>>=,<<=)三类共十一种。
6.      条件运算符:这是一个三目运算符,用于条件求值(?:)。
7.      逗号运算符:用于把若干表达式组合成一个表达式(,)。
8.      指针运算符:用于取内容(*)和取地址(&)二种运算。
9.    求字节数运算符:用于计算数据类型所占的字节数(sizeof)。
10.  特殊运算符:有括号(),下标[],成员(→,.)等几种。
3.1.1    3.8.2  算术运算符和算术表达式
1.    1.      基本的算术运算符
        加法运算符“+”:加法运算符为双目运算符,即应有两个量参与加法运算。如a+b,4+8等。具有右结合性。
        减法运算符“-”:减法运算符为双目运算符。但“-”也可作负值运算符,此时为单目运算,如-x,-5等具有左结合性。
        乘法运算符“*”:双目运算,具有左结合性。
        除法运算符“/”:双目运算具有左结合性。参与运算量均为整型时,结果也为整型,舍去小数。如果运算量中有一个是实型,则结果为双精度实型。
〖例3.14〗
main(){
  printf("\n\n%d,%d\n",20/7,-20/7);
  printf("%f,%f\n",20.0/7,-20.0/7);
}

本例中,20/7,-20/7的结果均为整型,小数全部舍去。而20.0/7和-20.0/7由于有实数参与运算,因此结果也为实型。
        求余运算符(模运算符)“%”:双目运算,具有左结合性。要求参与运算的量均为整型。 求余运算的结果等于两数相除后的余数。
【例3.15】
main(){
  printf("%d\n",100%3);
}

      本例输出100除以3所得的余数1。
2.      算术表达式和运算符的优先级和结合性
表达式是由常量、变量、函数和运算符组合起来的式子。一个表达式有一个值及其类型, 它们等于计算表达式所得结果的值和类型。表达式求值按运算符的优先级和结合性规定的顺序进行。单个的常量、变量、函数可以看作是表达式的特例。
算术表达式是由算术运算符和括号连接起来的式子。
        算术表达式:用算术运算符和括号将运算对象(也称操作数)连接起来的、符合C语法规则的式子。
以下是算术表达式的例子:
a+b
(a*2)/c
(x+r)*8-(a+b)/7
++I
sin(x)+sin(y)
(++i)-(j++)+(k--)
        运算符的优先级:C语言中,运算符的运算优先级共分为15级。1级最高,15级最低。在表达式中,优先级较高的先于优先级较低的进行运算。而在一个运算量两侧的运算符优先级相同时,则按运算符的结合性所规定的结合方向处理。
        运算符的结合性:C语言中各运算符的结合性分为两种,即左结合性(自左至右)和右结合性(自右至左)。例如算术运算符的结合性是自左至右,即先左后右。如有表达式x-y+z则y应先与“-”号结合,执行x-y运算,然后再执行+z的运算。这种自左至右的结合方向就称为“左结合性”。而自右至左的结合方向称为“右结合性”。 最典型的右结合性运算符是赋值运算符。如x=y=z,由于“=”的右结合性,应先执行y=z再执行x=(y=z)运算。C语言运算符中有不少为右结合性,应注意区别,以避免理解错误。
3.      强制类型转换运算符
其一般形式为:
    (类型说明符)  (表达式)
其功能是把表达式的运算结果强制转换成类型说明符所表示的类型。
例如:
    (float) a      把a转换为实型
        (int)(x+y)    把x+y的结果转换为整型
4.      自增、自减运算符
自增1,自减1运算符:自增1运算符记为“++”,其功能是使变量的值自增1。
自减1运算符记为“--”,其功能是使变量值自减1。
自增1,自减1运算符均为单目运算,都具有右结合性。可有以下几种形式:
    ++i    i自增1后再参与其它运算。
    --i    i自减1后再参与其它运算。
    i++    i参与运算后,i的值再自增1。
    i--    i参与运算后,i的值再自减1。
在理解和使用上容易出错的是i++和i--。 特别是当它们出在较复杂的表达式或语句中时,常常难于弄清,因此应仔细分析。
【例3.16】
main(){
  int i=8;
  printf("%d\n",++i);
  printf("%d\n",--i);
  printf("%d\n",i++);
  printf("%d\n",i--);
  printf("%d\n",-i++);
  printf("%d\n",-i--);


i的初值为8,第2行i加1后输出故为9;第3行减1后输出故为8;第4行输出i为8之后再加1(为9);第5行输出i为9之后再减1(为8) ;第6行输出-8之后再加1(为9),第7行输出-9之后再减1(为8)。
【例3.17】
main(){
  int i=5,j=5,p,q;
  p=(i++)+(i++)+(i++);
  q=(++j)+(++j)+(++j);
  printf("%d,%d,%d,%d",p,q,i,j);
}

  这个程序中,对P=(i++)+(i++)+(i++)应理解为三个i相加,故P值为15。然后i再自增1三次相当于加3故i的最后值为8。而对于q 的值则不然,q=(++j)+(++j)+(++j)应理解为q先自增1,再参与运算,由于q自增1三次后值为8,三个8相加的和为24,j的最后值仍为8。
3.9    赋值运算符和赋值表达式
1.        赋值运算符
简单赋值运算符和表达式:简单赋值运算符记为“=”。由“= ”连接的式子称为赋值表达式。其一般形式为:
变量=表达式
例如:
    x=a+b
    w=sin(a)+sin(b)
y=i+++--j
赋值表达式的功能是计算表达式的值再赋予左边的变量。赋值运算符具有右结合性。因此
    a=b=c=5
可理解为
        a=(b=(c=5))
在其它高级语言中,赋值构成了一个语句,称为赋值语句。 而在C中,把“=”定义为运算符,从而组成赋值表达式。 凡是表达式可以出现的地方均可出现赋值表达式。
例如,式子:
x=(a=5)+(b=8)
是合法的。它的意义是把5赋予a,8赋予b,再把a,b相加,和赋予x,故x应等于13。
在C语言中也可以组成赋值语句,按照C语言规定,任何表达式在其未尾加上分号就构成为语句。因此如
x=8;a=b=c=5;
都是赋值语句,在前面各例中我们已大量使用过了。
2.        类型转换
如果赋值运算符两边的数据类型不相同,系统将自动进行类型转换,即把赋值号右边的类型换成左边的类型。具体规定如下:
1)    1)        实型赋予整型,舍去小数部分。前面的例子已经说明了这种情况。
2)    2)        整型赋予实型,数值不变,但将以浮点形式存放,即增加小数部分(小数部分的值为0)。
3)    3)        字符型赋予整型,由于字符型为一个字节,而整型为二个字节,故将字符的ASCII码值放到整型量的低八位中,高八位为0。整型赋予字符型,只把低八位赋予字符量。
【例3.18】
main(){
  int a,b=322;
  float x,y=8.88;
  char c1='k',c2;
  a=y;
  x=b;
  a=c1;
  c2=b;
  printf("%d,%f,%d,%c",a,x,a,c2);
}

本例表明了上述赋值运算中类型转换的规则。a为整型,赋予实型量y值8.88后只取整数8。x为实型,赋予整型量b值322, 后增加了小数部分。字符型量c1赋予a变为整型,整型量b赋予c2 后取其低八位成为字符型(b的低八位为01000010,即十进制66,按ASCII码对应于字符B)。
3.        复合的赋值运算符
在赋值符“=”之前加上其它二目运算符可构成复合赋值符。如+=,-=,*=,/=,%=,<<=,>>=,&=,^=,|=。
构成复合赋值表达式的一般形式为:
变量  双目运算符=表达式
它等效于
变量=变量 运算符 表达式
例如:
    a+=5      等价于a=a+5
    x*=y+7    等价于x=x*(y+7)
    r%=p      等价于r=r%p
复合赋值符这种写法,对初学者可能不习惯,但十分有利于编译处理,能提高编译效率并产生质量较高的目标代码。
3.10      逗号运算符和逗号表达式
    在C语言中逗号“,”也是一种运算符,称为逗号运算符。 其功能是把两个表达式连接起来组成一个表达式, 称为逗号表达式。
其一般形式为:
表达式1,表达式2
其求值过程是分别求两个表达式的值,并以表达式2的值作为整个逗号表达式的值。
【例3.19】
main(){
  int a=2,b=4,c=6,x,y;
  y=(x=a+b),(b+c);
  printf("y=%d,x=%d",y,x);
}

    本例中,y等于整个逗号表达式的值,也就是表达式2的值,x是第一个表达式的值。对于逗号表达式还要说明两点:
1)    1)        逗号表达式一般形式中的表达式1和表达式2 也可以又是逗号表达式。
例如:
       表达式1,(表达式2,表达式3)
形成了嵌套情形。因此可以把逗号表达式扩展为以下形式:
       表达式1,表达式2,…表达式n
整个逗号表达式的值等于表达式n的值。
2)    2)        程序中使用逗号表达式,通常是要分别求逗号表达式内各表达式的值,并不一定要求整个逗号表达式的值。
并不是在所有出现逗号的地方都组成逗号表达式,如在变量说明中,函数参数表中逗号只是用作各变量之间的间隔符。
3.11      小结
3.11.1 C的数据类型
基本类型,构造类型,指针类型,空类型
3.11.2 基本类型的分类及特点
                类型说明符    字节    数值范围
字符型    char    1    C字符集
基本整型    int    2    -32768~32767
短整型    short int    2    -32768~32767
长整型    long int    4    -214783648~214783647
无符号型    unsigned    2    0~65535
无符号长整型    unsigned long    4    0~4294967295
单精度实型    float    4    3/4E-38~3/4E+38
双精度实型    double    8    1/7E-308~1/7E+308
3.11.3 常量后缀
    L或l    长整型
    U或u  无符号数
F或f    浮点数
3.11.4 常量类型
    整数,长整数,无符号数,浮点数,字符,字符串,符号常数,转义字符。
3.11.5 数据类型转换
•自动转换:在不同类型数据的混合运算中,由系统自动实现转换,由少字节类型向多字节类型转换。不同类型的量相互赋值时也由系统自动进行转换,把赋值号右边的类型转换为左边的类型。
•强制转换:由强制转换运算符完成转换。
3.11.6 运算符优先级和结合性
    一般而言,单目运算符优先级较高,赋值运算符优先级低。算术运算符优先级较高,关系和逻辑运算符优先级较低。多数运算符具有左结合性,单目运算符、三目运算符、赋值运算符具有右结合性。
3.11.7 表达式
    表达式是由运算符连接常量、变量、函数所组成的式子。 每个表达式都有一个值和类型。表达式求值按运算符的优先级和结合性所规定的顺序进行。
天生我材必有用
老鼠儿子会打洞
离线绝世衰神
只看该作者 3 发表于: 2008-02-01
4      最简单的C程序设计—顺序程序设计
    从程序流程的角度来看,程序可以分为三种基本结构, 即顺序结构、分支结构、循环结构。 这三种基本结构可以组成所有的各种复杂程序。C语言提供了多种语句来实现这些程序结构。本章介绍这些基本语句及其在顺序结构中的应用,使读者对C程序有一个初步的认识, 为后面各章的学习打下基础。
4.1    C语句概述
C程序的结构:

C程序的执行部分是由语句组成的。 程序的功能也是由执行语句实现的。
C语句可分为以下五类:
1)      表达式语句
2)      函数调用语句
3)      控制语句
4)      复合语句
5)      空语句
1.      表达式语句:表达式语句由表达式加上分号“;”组成。
其一般形式为:
    表达式;
执行表达式语句就是计算表达式的值。
例如:
    x=y+z;  赋值语句;
    y+z;    加法运算语句,但计算结果不能保留,无实际意义;
    i++;    自增1语句,i值增1。
2.      函数调用语句:由函数名、实际参数加上分号“;”组成。
其一般形式为:
    函数名(实际参数表);
执行函数语句就是调用函数体并把实际参数赋予函数定义中的形式参数,然后执行被调函数体中的语句,求取函数值 (在后面函数中再详细介绍) 。
例如:
printf("C Program");调用库函数,输出字符串。
3.      控制语句:控制语句用于控制程序的流程,以实现程序的各种结构方式。它们由特定的语句定义符组成。C语言有九种控制语句。 可分成以下三类:
1)      条件判断语句:if语句、switch语句;
2)      循环执行语句:do while语句、while语句、for语句;
3)      转向语句:break语句、goto语句、continue语句、return语句。
4.      复合语句:把多个语句用括号{}括起来组成的一个语句称复合语句。
在程序中应把复合语句看成是单条语句,而不是多条语句。
例如:
    { x=y+z;
      a=b+c;
      printf(“%d%d”,x,a);
    }
是一条复合语句。
复合语句内的各条语句都必须以分号“;”结尾,在括号“}”外不能加分号。
5.      空语句:只有分号“;”组成的语句称为空语句。空语句是什么也不执行的语句。在程序中空语句可用来作空循环体。
例如
    while(getchar()!='\n')
    ;
本语句的功能是,只要从键盘输入的字符不是回车则重新输入。
这里的循环体为空语句。
4.2    赋值语句
赋值语句是由赋值表达式再加上分号构成的表达式语句。
其一般形式为:
    变量=表达式;
赋值语句的功能和特点都与赋值表达式相同。 它是程序中使用最多的语句之一。
在赋值语句的使用中需要注意以下几点:
1.      由于在赋值符“=”右边的表达式也可以又是一个赋值表达式,
因此,下述形式
        变量=(变量=表达式);
是成立的,从而形成嵌套的情形。
其展开之后的一般形式为:
        变量=变量=…=表达式;
例如:
    a=b=c=d=e=5;
按照赋值运算符的右接合性,因此实际上等效于:
    e=5;
    d=e;
    c=d;
    b=c;
    a=b;
2.      注意在变量说明中给变量赋初值和赋值语句的区别。
给变量赋初值是变量说明的一部分,赋初值后的变量与其后的其它同类变量之间仍必须用逗号间隔,而赋值语句则必须用分号结尾。
例如:
    int a=5,b,c;
3.      在变量说明中,不允许连续给多个变量赋初值。
如下述说明是错误的:
      int a=b=c=5
必须写为
      int a=5,b=5,c=5;
而赋值语句允许连续赋值。
4.      注意赋值表达式和赋值语句的区别。
赋值表达式是一种表达式,它可以出现在任何允许表达式出现的地方,而赋值语句则不能。
下述语句是合法的:
      if((x=y+5)>0) z=x;
语句的功能是,若表达式x=y+5大于0则z=x。
下述语句是非法的:
      if((x=y+5;)>0) z=x;
因为x=y+5;是语句,不能出现在表达式中。
4.3    数据输入输出的概念及在C语言中的实现
1)        所谓输入输出是以计算机为主体而言的。
2)      本章介绍的是向标准输出设备显示器输出数据的语句。
3)      在C语言中,所有的数据输入/输出都是由库函数完成的。因此都是函数语句。
4)      在使用C语言库函数时,要用预编译命令
#include
将有关“头文件”包括到源文件中。
使用标准输入输出库函数时要用到 “stdio.h”文件,因此源文件开头应有以下预编译命令:
#include< stdio.h >

#include ”stdio.h”
stdio是standard input &outupt的意思。
5)      考虑到printf和scanf函数使用频繁,系统允许在使用这两个函数时可不加
#include< stdio.h >

#include ”stdio.h”
4.4    字符数据的输入输出
4.4.1  putchar 函数(字符输出函数)
putchar 函数是字符输出函数,其功能是在显示器上输出单个字符。
其一般形式为:
putchar(字符变量)
例如:
    putchar('A');    (输出大写字母A)
    putchar(x);      (输出字符变量x的值)
putchar(‘\101’); (也是输出字符A)
putchar('\n');  (换行)
对控制字符则执行控制功能,不在屏幕上显示。
使用本函数前必须要用文件包含命令:
#include<stdio.h>

#include “stdio.h”
【例4.1】输出单个字符。
#include<stdio.h>
main(){
  char a='B',b='o',c='k';
  putchar(a);putchar(b);putchar(b);putchar(c);putchar('\t');
  putchar(a);putchar(b);
  putchar('\n');
  putchar(b);putchar(c);
}

4.4.2  getchar函数(键盘输入函数)
getchar函数的功能是从键盘上输入一个字符。
其一般形式为:
    getchar();
通常把输入的字符赋予一个字符变量,构成赋值语句,如:
    char c;
        c=getchar();
【例4.2】输入单个字符。
#include<stdio.h>
void main(){
  char c;
  printf("input a character\n");
  c=getchar();
  putchar(c);
}

使用getchar函数还应注意几个问题:
1)      getchar函数只能接受单个字符,输入数字也按字符处理。输入多于一个字符时,只接收第一个字符。
2)      使用本函数前必须包含文件“stdio.h”。
3)      在TC屏幕下运行含本函数程序时,将退出TC 屏幕进入用户屏幕等待用户输入。输入完毕再返回TC屏幕。
4)      程序最后两行可用下面两行的任意一行代替:
putchar(getchar());
printf(“%c”,getchar());
4.5    格式输入与输出
4.5.1  printf函数(格式输出函数)
printf函数称为格式输出函数,其关键字最末一个字母f即为“格式”(format)之意。其功能是按用户指定的格式,把指定的数据显示到显示器屏幕上。在前面的例题中我们已多次使用过这个函数。
1.    printf函数调用的一般形式
printf函数是一个标准库函数,它的函数原型在头文件“stdio.h”中。但作为一个特例,不要求在使用 printf 函数之前必须包含stdio.h文件。
printf函数调用的一般形式为:
    printf(“格式控制字符串”,输出表列)
其中格式控制字符串用于指定输出格式。格式控制串可由格式字符串和非格式字符串两种组成。格式字符串是以%开头的字符串,在%后面跟有各种格式字符,以说明输出数据的类型、形式、长度、小数位数等。如:
“%d”表示按十进制整型输出;
“%ld”表示按十进制长整型输出;
“%c”表示按字符型输出等。
非格式字符串在输出时原样照印,在显示中起提示作用。
输出表列中给出了各个输出项,要求格式字符串和各输出项在数量和类型上应该一一对应。
【例4.3】
main()
{
  int a=88,b=89;
  printf("%d %d\n",a,b);
  printf("%d,%d\n",a,b);
  printf("%c,%c\n",a,b);
  printf("a=%d,b=%d",a,b);
}

本例中四次输出了a,b的值,但由于格式控制串不同,输出的结果也不相同。第四行的输出语句格式控制串中,两格式串%d 之间加了一个空格(非格式字符),所以输出的a,b值之间有一个空格。第五行的printf语句格式控制串中加入的是非格式字符逗号,因此输出
的a,b值之间加了一个逗号。第六行的格式串要求按字符型输出 a,b值。第七行中为了提示输出结果又增加了非格式字符串。
2.    格式字符串
在Turbo C中格式字符串的一般形式为:
      [标志][输出最小宽度][.精度][长度]类型
  其中方括号[]中的项为可选项。
各项的意义介绍如下:
1)      类型:类型字符用以表示输出数据的类型,其格式符和意义如下表所示:
格式字符    意            义
d    以十进制形式输出带符号整数(正数不输出符号)
o    以八进制形式输出无符号整数(不输出前缀0)
x,X    以十六进制形式输出无符号整数(不输出前缀Ox)
u    以十进制形式输出无符号整数
f    以小数形式输出单、双精度实数
e,E    以指数形式输出单、双精度实数
g,G    以%f或%e中较短的输出宽度输出单、双精度实数
c    输出单个字符
s    输出字符串
2)      标志:标志字符为-、+、#、空格四种,其意义下表所示:
标 志    意        义
-    结果左对齐,右边填空格
+    输出符号(正号或负号)
空格    输出值为正时冠以空格,为负时冠以负号
#    对c,s,d,u类无影响;对o类,在输出时加前缀o;对x类,在输出时加前缀0x;对e,g,f 类当结果有小数时才给出小数点
3)      输出最小宽度:用十进制整数来表示输出的最少位数。若实际位数多于定义的宽度,则按实际位数输出,若实际位数少于定义的宽度则补以空格或0。
4)      精度:精度格式符以“.”开头,后跟十进制整数。本项的意义是:如果输出数字,则表示小数的位数;如果输出的是字符,则表示输出字符的个数;若实际位数大于所定义的精度数,则截去超过的部分。
5)  长度:长度格式符为h,l两种,h表示按短整型量输出,l表示按长整型量输出。
【例4.4】
main()
{
  int a=15;
  float b=123.1234567;
  double c=12345678.1234567;
  char d='p';
  printf("a=%d,%5d,%o,%x\n",a,a,a,a);
  printf("b=%f,%lf,%5.4lf,%e\n",b,b,b,b);
  printf("c=%lf,%f,%8.4lf\n",c,c,c);
  printf("d=%c,%8c\n",d,d);
}

    本例第七行中以四种格式输出整型变量a的值,其中“%5d ”要求输出宽度为5,而a值为15只有两位故补三个空格。 第八行中以四种格式输出实型量b的值。其中“%f”和“%lf ”格式的输出相同,说明“l”符对“f”类型无影响。“%5.4lf”指定输出宽度为5,精度为4,由于实际长度超过5故应该按实际位数输出,小数位数超过4位部分被截去。第九行输出双精度实数,“%8.4lf ”由于指定精度为4位故截去了超过4位的部分。第十行输出字符量d,其中“%8c ”指定输出宽度为8故在输出字符p之前补加7个空格。
使用printf函数时还要注意一个问题,那就是输出表列中的求值顺序。不同的编译系统不一定相同,可以从左到右,也可从右到左。Turbo C是按从右到左进行的。请看下面两个例子:
【例4.5】
main(){
  int i=8;
  printf("%d\n%d\n%d\n%d\n%d\n%d\n",++i,--i,i++,i--,-i++,-i--);
}

【例4.6】
main(){
  int i=8;
  printf("%d\n",++i);
  printf("%d\n",--i);
  printf("%d\n",i++);
  printf("%d\n",i--);
printf("%d\n",-i++);
  printf("%d\n",-i--);
}

这两个程序的区别是用一个printf语句和多个printf 语句输出。但从结果可以看出是不同的。为什么结果会不同呢?就是因为printf函数对输出表中各量求值的顺序是自右至左进行的。在第一例中,先对最后一项“-i--”求值,结果为-8,然后i自减1后为7。 再对“-i++”项求值得-7,然后i自增1后为8。再对“i--”项求值得8,然后i再自减1后为7。再求“i++”项得7,然后i再自增1后为8。 再求“--i”项,i先自减1后输出,输出值为7。 最后才求输出表列中的第一项“++i”,此时i自增1后输出8。
但是必须注意,求值顺序虽是自右至左,但是输出顺序还是从左至右,因此得到的结果是上述输出结果。
4.5.2  scanf函数(格式输入函数)
scanf函数称为格式输入函数,即按用户指定的格式从键盘上把数据输入到指定的变量之中。
1.    scanf函数的一般形式
scanf函数是一个标准库函数,它的函数原型在头文件“stdio.h”中,与printf函数相同,C语言也允许在使用scanf函数之前不必包含stdio.h文件。
scanf函数的一般形式为:
    scanf(“格式控制字符串”,地址表列);
其中,格式控制字符串的作用与printf函数相同,但不能显示非格式字符串,也就是不能显示提示字符串。地址表列中给出各变量的地址。地址是由地址运算符“&”后跟变量名组成的。
例如:
&a, &b
分别表示变量a和变量b 的地址。
这个地址就是编译系统在内存中给a,b变量分配的地址。在C语言中,使用了地址这个概念,这是与其它语言不同的。 应该把变量的值和变量的地址这两个不同的概念区别开来。变量的地址是C编译系统分配的,用户不必关心具体的地址是多少。
变量的地址和变量值的关系如下:
在赋值表达式中给变量赋值,如:
    a=567
则,a为变量名,567是变量的值,&a是变量a的地址。
但在赋值号左边是变量名,不能写地址,而scanf函数在本质上也是给变量赋值,但要求写变量的地址,如&a。 这两者在形式上是不同的。&是一个取地址运算符,&a是一个表达式,其功能是求变量的地址。
【例4.7】
main(){
  int a,b,c;
  printf("input a,b,c\n");
  scanf("%d%d%d",&a,&b,&c);
  printf("a=%d,b=%d,c=%d",a,b,c);
}

在本例中,由于scanf函数本身不能显示提示串,故先用printf语句在屏幕上输出提示,请用户输入a、b、c的值。执行scanf语句,则退出TC屏幕进入用户屏幕等待用户输入。用户输入7  8  9后按下回车键,此时,系统又将返回TC屏幕。在scanf语句的格式串中由于没有非格式字符在“%d%d%d”之间作输入时的间隔,因此在输入时要用一个以上的空格或回车键作为每两个输入数之间的间隔。如:
  7 8 9

7
  8
  9
2.    格式字符串
格式字符串的一般形式为:
%[*][输入数据宽度][长度]类型
其中有方括号[]的项为任选项。各项的意义如下:
1)      类型:表示输入数据的类型,其格式符和意义如下表所示。
格式    字符意义
d    输入十进制整数
o    输入八进制整数
x    输入十六进制整数
u    输入无符号十进制整数
f或e    输入实型数(用小数形式或指数形式)
c    输入单个字符
s    输入字符串
2)      “*”符:用以表示该输入项,读入后不赋予相应的变量,即跳过该输入值。
    如:
scanf("%d %*d %d",&a,&b);
当输入为:1  2  3时,把1赋予a,2被跳过,3赋予b。
3)      宽度:用十进制整数指定输入的宽度(即字符数)。
例如:
    scanf("%5d",&a);
输入:12345678
只把12345赋予变量a,其余部分被截去。
又如:
        scanf("%4d%4d",&a,&b);
输入:12345678
将把1234赋予a,而把5678赋予b。
4)      长度:长度格式符为l和h,l表示输入长整型数据(如%ld) 和双精度浮点数(如%lf)。h表示输入短整型数据。
使用scanf函数还必须注意以下几点:
1)      scanf函数中没有精度控制,如:scanf("%5.2f",&a);是非法的。不能企图用此语句输入小数为2位的实数。
2)      scanf中要求给出变量地址,如给出变量名则会出错。如 scanf("%d",a);是非法的,应改为scnaf("%d",&a);才是合法的。
3)    在输入多个数值数据时,若格式控制串中没有非格式字符作输入数据之间的间隔则可用空格,TAB或回车作间隔。C编译在碰到空格,TAB,回车或非法数据(如对“%d”输入“12A”时,A即为非法数据)时即认为该数据结束。
4)      在输入字符数据时,若格式控制串中无非格式字符,则认为所有输入的字符均为有效字符。
例如:
              scanf("%c%c%c",&a,&b,&c);
输入为:
                  d  e  f
则把'd'赋予a, ' ' 赋予b,'e'赋予c。
只有当输入为:
                  def
时,才能把'd'赋于a,'e'赋予b,'f'赋予c。
如果在格式控制中加入空格作为间隔,
如:
scanf ("%c %c %c",&a,&b,&c);
则输入时各数据之间可加空格。
【例4.8】
main(){
  char a,b;
  printf("input character a,b\n");
  scanf("%c%c",&a,&b);
  printf("%c%c\n",a,b);
}

由于scanf函数"%c%c"中没有空格,输入M  N,结果输出只有M。而输入改为MN时则可输出MN两字符。
【例4.9】
main(){
  char a,b;
  printf("input character a,b\n");
  scanf("%c %c",&a,&b);
  printf("\n%c%c\n",a,b);
}

本例表示scanf格式控制串"%c %c"之间有空格时,输入的数据之间可以有空格间隔。
5)      如果格式控制串中有非格式字符则输入时也要输入该非格式字符。
      例如:
scanf("%d,%d,%d",&a,&b,&c);
  其中用非格式符“ , ”作间隔符,故输入时应为:
  5,6,7
又如:
    scanf("a=%d,b=%d,c=%d",&a,&b,&c);
则输入应为:
          a=5,b=6,c=7
6)      如输入的数据与输出的类型不一致时,虽然编译能够通过,但结果将不正确。
【例4.10】
main(){
  int a;
  printf("input a number\n");
  scanf("%d",&a);
  printf("%ld",a);
}

    由于输入数据类型为整型,而输出语句的格式串中说明为长整型,因此输出结果和输入数据不符。如改动程序如下:
【例4.11】
main(){
    long a;
    printf("input a long integer\n");
    scanf("%ld",&a);
    printf("%ld",a);
}

运行结果为:
    input a long integer
    1234567890
1234567890
当输入数据改为长整型后,输入输出数据相等。
【例4.12】
main(){
  char a,b,c;
  printf("input character a,b,c\n");
  scanf("%c %c %c",&a,&b,&c);
  printf("%d,%d,%d\n%c,%c,%c\n",a,b,c,a-32,b-32,c-32);
}

    输入三个小写字母,输出其ASCII码和对应的大写字母。
【例4.13】
main(){
int a;
long b;
float f;
double d;
char c;
printf("\nint:%d\nlong:%d\nfloat:%d\ndouble:%d\nchar:%d\n",sizeof(a),sizeof(b),sizeof(f),sizeof(d),sizeof(c));
}

    输出各种数据类型的字节长度。
4.6    顺序结构程序设计举例
【例4.14】输入三角形的三边长,求三角形面积。
已知三角形的三边长a,b,c,则该三角形的面积公式为:
    ,
其中s = (a+b+c)/2
源程序如下:
#include<math.h>
main()
{
float a,b,c,s,area;
scanf(“%f,%f,%f”,&a,&b,&c);
s=1.0/2*(a+b+c);
area=sqrt(s*(s-a)*(s-b)*(s-c));
printf(“a=%7.2f,b=%7.2f,c=%7.2f,s=%7.2f\n”,a,b,c,s);
printf(“area=%7.2f\n”,area);
}

【例4.15】求ax2+bx+c=0方程的根,a,b,c由键盘输入,设b2-4ac>0。
求根公式为:
         
令 ,
则x1=p+q
x2=p-q
源程序如下:
#include<math.h>
main()
{
  float a,b,c,disc,x1,x2,p,q;
  scanf(“a=%f,b=%f,c=%f”,&a,&b,&c);
  disc=b*b-4*a*c;
  p=-b/(2*a);
q=sqrt(disc)/(2*a);
x1=p+q;x2=p-q;
  printf(“\nx1=%5.2f\nx2=%5.2f\n”,x1,x2);
}
天生我材必有用
老鼠儿子会打洞
离线绝世衰神
只看该作者 4 发表于: 2008-02-01
分支结构程序
5.1    关系运算符和表达式
在程序中经常需要比较两个量的大小关系,以决定程序下一步的工作。比较两个量的运算符称为关系运算符。
5.1.1  关系运算符及其优先次序
在C语言中有以下关系运算符:
1)      <  小于
2)      <=  小于或等于
3)      >  大于
4)      >=  大于或等于
5)      ==  等于
6)      !=  不等于
关系运算符都是双目运算符,其结合性均为左结合。关系运算符的优先级低于算术运算符,高于赋值运算符。在六个关系运算符中,<,<=,>,>=的优先级相同,高于==和!=,==和!=的优先级相同。
5.1.2  关系表达式
关系表达式的一般形式为:
    表达式 关系运算符  表达式
例如:
a+b>c-d
x>3/2
‘a’+1<c
-i-5*j==k+1
都是合法的关系表达式。由于表达式也可以又是关系表达式。 因此也允许出现嵌套的情况。例如:
a>(b>c)
a!=(c==d)
等。
关系表达式的值是真”和“假”,用“1”和“0”表示。
如:
  5>0的值为“真”,即为1。
(a=3)>(b=5)由于3>5不成立,故其值为假,即为0。
【例5.1】
main(){
  char c='k';
  int i=1,j=2,k=3;
  float x=3e+5,y=0.85;
  printf("%d,%d\n",’a’+5<c,-i-2*j>=k+1);
  printf("%d,%d\n",1<j<5,x-5.25<=x+y);
  printf("%d,%d\n",i+j+k==-2*j,k==j==i+5);
}

在本例中求出了各种关系运算符的值。字符变量是以它对应的ASCII码参与运算的。对于含多个关系运算符的表达式,如k==j==i+5,根据运算符的左结合性,先计算k==j,该式不成立,其值为0,再计算0==i+5,也不成立,故表达式值为0。
5.2    逻辑运算符和表达式
5.2.1  逻辑运算符极其优先次序
C语言中提供了三种逻辑运算符:
1)      &&  与运算
2)      ||  或运算
3)      !  非运算
与运算符&&和或运算符||均为双目运算符。具有左结合性。非运算符!为单目运算符,具有右结合性。逻辑运算符和其它运算符优先级的关系可表示如下:
!(非)→&&(与)→||(或)
“&&”和“||”低于关系运算符,“!”高于算术运算符。

按照运算符的优先顺序可以得出:
a>b && c>d  等价于    (a>b)&&(c>d)
          !b==c||d<a    等价于    ((!b)==c)||(d<a)
          a+b>c&&x+y<b  等价于    ((a+b)>c)&&((x+y)<b)
5.2.2  逻辑运算的值
逻辑运算的值也为“真”和“假”两种,用“1”和“0 ”来表示。其求值规则如下:
1.    与运算 &&:参与运算的两个量都为真时,结果才为真,否则为假。
例如:
5>0 && 4>2
由于5>0为真,4>2也为真,相与的结果也为真。
2.    或运算||:参与运算的两个量只要有一个为真,结果就为真。 两个量都为假时,结果为假。
例如:
5>0||5>8
由于5>0为真,相或的结果也就为真。
3.    非运算!:参与运算量为真时,结果为假;参与运算量为假时,结果为真。
例如:
!(5>0)
的结果为假。
虽然C编译在给出逻辑运算值时,以“1”代表“真”,“0 ”代表“假”。但反过来在判断一个量是为“真”还是为“假”时,以“0”代表“假”,以非“0”的数值作为“真”。例如:
由于5和3均为非“0”因此5&&3的值为“真”,即为1。
又如:
5||0的值为“真”,即为1。
5.2.3  逻辑表达式
逻辑表达式的一般形式为:
    表达式  逻辑运算符  表达式
其中的表达式可以又是逻辑表达式,从而组成了嵌套的情形。
例如:
    (a&&b)&&c
根据逻辑运算符的左结合性,上式也可写为:
    a&&b&&c
逻辑表达式的值是式中各种逻辑运算的最后值,以“1”和“0”分别代表“真”和“假”。
【例5.2】
main(){
    char c='k';
    int i=1,j=2,k=3;
    float x=3e+5,y=0.85;
    printf("%d,%d\n",!x*!y,!!!x);
    printf("%d,%d\n",x||i&&j-3,i<j&&x<y);
    printf("%d,%d\n",i==5&&c&&(j=8),x+y||i+j+k);
}
   
本例中!x和!y分别为0,!x*!y也为0,故其输出值为0。由于x为非0,故!!!x的逻辑值为0。对x|| i && j-3式,先计算j-3的值为非0,再求i && j-3的逻辑值为1,故x||i&&j-3的逻辑值为 1。对i<j&&x<y式,由于i<j的值为1,而x<y为0故表达式的值为1,0相与,最后为0,对i==5&&c&&(j=8)式,由于i==5为假,即值为0,该表达式由两个与运算组成,所以整个表达式的值为0。对于式x+ y||i+j+k由于x+y的值为非0,故整个或表达式的值为1。
5.3    if语句
用if语句可以构成分支结构。它根据给定的条件进行判断,以决定执行某个分支程序段。C语言的if语句有三种基本形式。
5.3.1  if语句的三种形式
1.      第一种形式为基本形式:if
    if(表达式) 语句
其语义是:如果表达式的值为真,则执行其后的语句,否则不执行该语句。其过程可表示为下图。

【例5.3】
main(){
    int a,b,max;
    printf("\n input two numbers:  ");
    scanf("%d%d",&a,&b);
    max=a;
    if (max<b) max=b;
    printf("max=%d",max);
}
 
    本例程序中,输入两个数a,b。把a先赋予变量max,再用if语句判别max和b的大小,如max小于b,则把b赋予max。因此max中总是大数,最后输出max的值。
2.      第二种形式为: if-else
if(表达式) 
          语句1; 
        else 
          语句2;
  其语义是:如果表达式的值为真,则执行语句1,否则执行语句2 。
其执行过程可表示为下图。


【例5.4】
main(){
    int a, b;
    printf("input two numbers:    ");
    scanf("%d%d",&a,&b);
    if(a>b)
      printf("max=%d\n",a);
    else
      printf("max=%d\n",b);
}
 
    输入两个整数,输出其中的大数。
改用if-else语句判别a,b的大小,若a大,则输出a,否则输出b。
3.      第三种形式为if-else-if形式
前二种形式的if语句一般都用于两个分支的情况。当有多个分支选择时,可采用if-else-if语句,其一般形式为:
if(表达式1)
        语句1;
    else  if(表达式2) 
        语句2;
    else  if(表达式3) 
        语句3;
        … 
    else  if(表达式m) 
        语句m;
    else
        语句n;
其语义是:依次判断表达式的值,当出现某个值为真时,则执行其对应的语句。然后跳到整个if语句之外继续执行程序。 如果所有的表达式均为假,则执行语句n。然后继续执行后续程序。 if-else-if语句的执行过程如图3—3所示。

【例5.5】
#include"stdio.h"
main(){
    char c;
    printf("input a character:    ");
    c=getchar();
    if(c<32)
      printf("This is a control character\n");
    else if(c>='0'&&c<='9')
      printf("This is a digit\n");
    else if(c>='A'&&c<='Z')
      printf("This is a capital letter\n");
    else if(c>='a'&&c<='z')
      printf("This is a small letter\n");
    else
      printf("This is an other character\n");
}

    本例要求判别键盘输入字符的类别。可以根据输入字符的ASCII码来判别类型。由ASCII码表可知ASCII值小于32的为控制字符。在“0”和“9”之间的为数字,在“A”和“Z”之间为大写字母, 在“a”和“z”之间为小写字母,其余则为其它字符。这是一个多分
支选择的问题,用if-else-if语句编程,判断输入字符ASCII码所在的范围,分别给出不同的输出。例如输入为“g”,输出显示它为小写字符。
4.      在使用if语句中还应注意以下问题:
1)      在三种形式的if语句中,在if关键字之后均为表达式。 该表达式通常是逻辑表达式或关系表达式, 但也可以是其它表达式,如赋值表达式等,甚至也可以是一个变量。
例如:
    if(a=5) 语句;
if(b) 语句;
都是允许的。只要表达式的值为非0,即为“真”。
如在:
if(a=5)…;
中表达式的值永远为非0,所以其后的语句总是要执行的,当然这种情况在程序中不一定会出现,但在语法上是合法的。
又如,有程序段:
    if(a=b)
                printf("%d",a);
              else
                printf("a=0");
本语句的语义是,把b值赋予a,如为非0则输出该值,否则输出“a=0”字符串。这种用法在程序中是经常出现的。
2)      在if语句中,条件判断表达式必须用括号括起来,在语句之后必须加分号。
3)      在if语句的三种形式中,所有的语句应为单个语句,如果要想在满足条件时执行一组(多个)语句,则必须把这一组语句用{}括起来组成一个复合语句。但要注意的是在}之后不能再加分号。
例如:
    if(a>b)
{a++;
          b++;}
else
{a=0;
      b=10;}
5.3.2  if语句的嵌套
当if语句中的执行语句又是if语句时,则构成了if 语句嵌套的情形。
其一般形式可表示如下:
    if(表达式) 
        if语句; 
或者为
        if(表达式) 
          if语句; 
        else 
          if语句;
在嵌套内的if语句可能又是if-else型的,这将会出现多个if和多个else重叠的情况,这时要特别注意if和else的配对问题。
例如:
    if(表达式1)
        if(表达式2)
            语句1;
        else
语句2;
其中的else究竟是与哪一个if配对呢?
应该理解为:
  if(表达式1)
        if(表达式2)
          语句1;
      else
           语句2;
还是应理解为:
    if(表达式1)
        if(表达式2)
            语句1;
    else
       语句2;
为了避免这种二义性,C语言规定,else 总是与它前面最近的if配对,因此对上述例子应按前一种情况理解。
【例5.6】
main(){
    int a,b;
    printf("please input A,B:    ");
    scanf("%d%d",&a,&b);
    if(a!=b)
    if(a>b)  printf("A>B\n");
    else    printf("A<B\n");
    else    printf("A=B\n");
}

    比较两个数的大小关系。
    本例中用了if语句的嵌套结构。采用嵌套结构实质上是为了进行多分支选择,实际上有三种选择即A>B、A<B或A=B。这种问题用if-else-if语句也可以完成。而且程序更加清晰。因此,在一般情况下较少使用if语句的嵌套结构。以使程序更便于阅读理解。
【例5.7】
main(){
    int a,b;
    printf("please input A,B:      ");
    scanf("%d%d",&a,&b);
    if(a==b) printf("A=B\n");
    else if(a>b)  printf("A>B\n");
    else  printf("A<B\n");
}

5.3.3  条件运算符和条件表达式
    如果在条件语句中,只执行单个的赋值语句时, 常可使用条件表达式来实现。不但使程序简洁,也提高了运行效率。
条件运算符为?和:,它是一个三目运算符,即有三个参与运算的量。
由条件运算符组成条件表达式的一般形式为:
    表达式1?  表达式2: 表达式3
其求值规则为:如果表达式1的值为真,则以表达式2 的值作为条件表达式的值,否则以表达式2的值作为整个条件表达式的值。
条件表达式通常用于赋值语句之中。
例如条件语句:
    if(a>b)  max=a;
        else max=b;
可用条件表达式写为
    max=(a>b)?a:b;
执行该语句的语义是:如a>b为真,则把a赋予max,否则把b 赋予max。
使用条件表达式时,还应注意以下几点:
1)      条件运算符的运算优先级低于关系运算符和算术运算符,但高于赋值符。
因此
    max=(a>b)?a:b
可以去掉括号而写为
    max=a>b?a:b
2)      条件运算符?和:是一对运算符,不能分开单独使用。
3)      条件运算符的结合方向是自右至左。
例如:
a>b?a:c>d?c:d
应理解为
a>b?a:(c>d?c:d)
这也就是条件表达式嵌套的情形,即其中的表达式3又是一个条件表达式。
【例5.8】
main(){
    int a,b,max;
    printf("\n input two numbers:  ");
    scanf("%d%d",&a,&b);
    printf("max=%d",a>b?a:b);
}

用条件表达式对上例重新编程,输出两个数中的大数。
5.4    switch语句
C语言还提供了另一种用于多分支选择的switch语句, 其一般形式为:
    switch(表达式){ 
        case常量表达式1:  语句1;
        case常量表达式2:  语句2;
        … 
        case常量表达式n:  语句n;
        default        :  语句n+1;
        }
    其语义是:计算表达式的值。 并逐个与其后的常量表达式值相比较,当表达式的值与某个常量表达式的值相等时,即执行其后的语句,然后不再进行判断,继续执行后面所有case后的语句。如表达式的值与所有case后的常量表达式均不相同时,则执行default后
的语句。
【例4.9】
main(){
    int a;
    printf("input integer number:      ");
    scanf("%d",&a);
    switch (a){
    case 1:printf("Monday\n");
    case 2:printf("Tuesday\n");
    case 3:printf("Wednesday\n");
    case 4:printf("Thursday\n");
    case 5:printf("Friday\n");
    case 6:printf("Saturday\n");
    case 7:printf("Sunday\n");
    default:printf("error\n");
    }
}

本程序是要求输入一个数字,输出一个英文单词。但是当输入3之后,却执行了case3以及以后的所有语句,输出了Wednesday 及以后的所有单词。这当然是不希望的。为什么会出现这种情况呢?这恰恰反应了switch语句的一个特点。在switch语句中,“case 常量表达式”只相当于一个语句标号, 表达式的值和某标号相等则转向该标号执行,但不能在执行完该标号的语句后自动跳出整个switch 语句,所以出现了继续执行所有后面case语句的情况。 这是与前面介绍的if语句完全不同的,应特别注意。为了避免上述情况,C语言还提供了一种break语句,专用于跳出switch语句,break 语句只有关键字break,没有参数。在后面还将详细介绍。修改例题的程序,在每一case语句之后增加break 语句, 使每一次执行之后均可跳出switch语句,从而避免输出不应有的结果。
【例4.10】
main(){
    int a;
    printf("input integer number:    ");
    scanf("%d",&a);
    switch (a){
      case 1:printf("Monday\n");break;
      case 2:printf("Tuesday\n"); break;
      case 3:printf("Wednesday\n");break;
      case 4:printf("Thursday\n");break;
      case 5:printf("Friday\n");break;
      case 6:printf("Saturday\n");break;
      case 7:printf("Sunday\n");break;
      default:printf("error\n");
    }
}

在使用switch语句时还应注意以下几点:
1)      在case后的各常量表达式的值不能相同,否则会出现错误。
2)      在case后,允许有多个语句,可以不用{}括起来。
3)      各case和default子句的先后顺序可以变动,而不会影响程序执行结果。
4)      default子句可以省略不用。
5.5    程序举例
【例4.11】输入三个整数,输出最大数和最小数。
main(){
    int a,b,c,max,min;
    printf("input three numbers:    ");
    scanf("%d%d%d",&a,&b,&c);
    if(a>b)
      {max=a;min=b;}
    else
      {max=b;min=a;}
    if(max<c)
      max=c;
    else
      if(min>c)
    min=c;
    printf("max=%d\nmin=%d",max,min);
}

本程序中,首先比较输入的a,b的大小,并把大数装入max,小数装入min中,然后再与c比较,若max小于c,则把c赋予max;如果c小于min,则把c赋予min。因此max内总是最大数,而min内总是最小数。最后输出max和min的值即可。
【例4.12】计算器程序。用户输入运算数和四则运算符,输出计算结果。
main(){
    float a,b;
    char c;
    printf("input expression: a+(-,*,/)b \n");
    scanf("%f%c%f",&a,&c,&b);
    switch(c){
      case '+': printf("%f\n",a+b);break;
      case '-': printf("%f\n",a-b);break;
      case '*': printf("%f\n",a*b);break;
      case '/': printf("%f\n",a/b);break;
      default: printf("input error\n");
    }
}

    本例可用于四则运算求值。switch语句用于判断运算符,然后输出运算值。当输入运算符不是+,-,*,/时给出错误提示。
天生我材必有用
老鼠儿子会打洞
离线yonghu86cs
只看该作者 5 发表于: 2008-02-20
大牛
离线冷月佩儿
只看该作者 6 发表于: 2008-05-20
抗震救灾
无论怎么样倡导顶的精神,哈哈






------------------分-------------割--------------线------------------------
  网站优化 真封神私服 及时雨外挂
离线fjcym
只看该作者 7 发表于: 2008-05-20
辛苦了
快速回复
限100 字节
 
上一个 下一个