2007-9-23:
1.在调用函数时,若形参函数为数组与指针类型,函数调用时传递给形参的值应为指针或数组名。如例:
#include "stdio.h"
int jdg(char *a,char d);
void main()
{
char *s="abcd";
if(jdg(s,'d')) printf("The char is included in the string./n");
else printf("The char is not included in the string./n");
}
int jdg(char *a,char d)
{
while(*a)
{
if(*a==d) return 1;
else *a++;
}
return 0;
}
粗体标注部分不是输入*S,而是变量名S。
2.局部变量在进入代码块时生成,在退出代码块时消失。
3. C89标准中变量定义需在函数第一个开大括号与第一条语句之间。
4.全局变量保存在C编译程序专门开辟的固定内存区域。当程序中的多个函数都使用相同数据时,全局变量是合适的。然而,程序中应减少不必要的全局变量,因为全局变量在程序执行期内一直占据内存。
如果局部和全局变量同名,在声明局部变量的代码块中只引用局部变量,不影响同名全局变量。
5. 修饰符volatile把一个事实告知编译程序,说明变量的值可能以未在程序中明确表达的方法改变。const和volatile可以同时使用。例如,如果0X30定义为一个端口值,只受外部条件的修改,则以下声明将消除任何偶然副作用的影响:
const volatile char* port=(const volatile char *)0x30;
详见C语言大全P24。
6.extern,static用法见P25。
2007-9-27:
7.switch语句中case语句后若无break语句,则在满足条件的case语句后的所有case语句将不再判断直接执行直至switch结尾或遇见break语句。
8.strcmp()函数在字符串相等时,返回值0;
2007-9-29:
9.用指针放置指向数组首元素的指针时可使用语句。p=sample;(*p,sample[x])
10.在C语言中不能把整个数组做为传入函数的变元,只能用不带下标的数组名传入函数。在定义接受数组的函数的形参时,有三种方法。指针(如fun(int *p))定尺寸数组(如fun(int a[20]))无尺寸数组(fun(int a[])).在函数形参的声明中,数组尺寸无关紧要,因为C语言不进行边界检查。
11.字符串函数。#include “string.h”.
strcpy(s1,s2) s2拷贝到s1
strcat(s1,s2) s2连到s1末尾
strlen(s1) 返回s1的长度
strcmp(s1,s2) s1=s2时返回零值 s1>s2时返回大于零值 s1<s2返回小于零值
strchr(s1,ch) 返回指针,指向ch 在s1中的第一次出现
strstr(s1,s2) 返回指针,指向s2在s1中的第一次出现
12.#define CH constant语句后不能接分号。
13.函数toupper(*str)指从字符串str中取第一个字母转化成大写字母。
int atoi(const char *string) 它的参数是一个char指针,atoi(str)指将由数字组成的字符串str 转换成相应的数字。
包含在头文件stdlib.h中。
14.putchar()用来输出单个字符,如putchar(变量名).字符可用ASCII码表示.包含在stdio.h头文件中.
2007-10-1
15.不带下标的数组名字就是指向数组首元素的指针。如char p[0],p与&p[0]完全等价。
语句p==&p[0]为真。
16.通过使用%p printf()格式说明符显示的地址,使printf()以宿主计算机使用的格式显示地址。
17.在对指针进行加减运算时,指针增量后指向下一个与指针基类同型的元素,指针减量后指向上一个与其基类同型的元素。如int 型指针p的值为2000,在进行增量操作后,p的值变为2002,而不是2001,因为int型占双字节长。指针不能进行乘除操作,不能将两个指针相加,不能按位移,不能按位与,也不能向指针加、减浮点和双精度浮点量。
18.以指针数组做为函数形参时,调用时应置的值为指针数组名。
如fun(char *p[]),调用方法为 fun(p)。
2007-10-3
19.函数指针声明方法:如声明int (*p)(const char *,const char *);p 为函数指针名,所指向的函数带有两个const char *参数,并且返回int 型结果。包括p的括号不可缺少。
20.函数isdigit(char ch)的用法,判断字符ch是否为数字。如定义字符数组s1,char s1[80];
判定首字符是否为数字时,调用方法为isdigit(*s1);
21.当声明指针p是一个指向含10个整数数组的指针时,声明语句为:int (*p)[10];包围*p的括号是必须的。当p是增量指针时,它将指向后10个整数的开头;当p是减量指针时,它将指向前10个整数。p是一个二维整数数组。每行有10个元素。p可以作为二维数组下标引用。
22.一类危险的指针错误类型。
/* This program has a bug.*/
#include<string.h>
#include<stdio.h>
int main(void)
{
char *p1;
char s[80];
p1=s;
do{
gets(s);
while(*p1) printf(“%d”,*p1++);
}while(strcmp(s,”done”));
return 0;
}
该程序通过p1打印出与s中诸字符关联的ASCII值。问题是只对p进行了一次s的地址的赋值。第一轮循环中,p1指向s中首字符。第二轮循环时,因为未再置成s的起点,p值从第一轮的结束点继续。此时,p可能指向另一个串,另一个变量,甚至程序的某一段。正确编写的程序应如下代码所示。
/*This program is now correct.*/
#include<string.h>
#include<stdio.h>
int main(void)
{
char *p1;
char s[80];
do{
p1=s;
gets(s);
while(*p1)printf(“%d”,*p1++);
}while(strcmp(s,”done”));
return 0;
}
23.在使用指针前应确定它所指向的位置。
2007-10-4
24.main()函数中的命令行变元的使用方法:main(int argc,char *argv[]),argc,argv两个内设参量用于接受命令行变元,一个是argc,另一个是argv。argc是整型变量,其中放命令行中变元总数;因为程序名也计算在内,argc的值最小为1,形参argv是指针,指向由字符串指针组成的数组,数组中第个元素指向一个命令行变元。所有命令行变元都是字符串,任何数字都将由程序转换成相应的二进制格式。带命令行变元的程序在运行时,在命令行提示符下输入程序生成的可执行文件名后接命令行参数即可。在许多环境中,命令行变元之间必须用空格或制表符分隔,逗号和分号不是分隔符。命令行变元的具体使用规定,见操作系统手册。
2007-10-5
25.函数返回的值不必赋给一个变量。不用赋值句时,返回值就放弃了。
2007-10-6
26.字符串输入函数gets()与字符输入函数getchar() 同一函数中使用时,需将gets()函数置于前面。reasonless.
27.可以定义参数的类型和数量都可变的函数,最典型的例子是pringf().为了把传递给一个函数的未知变元数告诉编译程序,我们用三个圆点(…)结束函数形参的声明。如,下声明表示:函数至少接收两个整数变元。随后,可能还有0到多个其它变元.int func(int a,int b,…);
使用可变参数值的任何函数,至少必须有一个实际的参数。如下例是错误的。
int func(…); /*illegal*/
28.结构体的声明:
一般形式为:
struct tag{
type member-name;
type member-name;
.
.
.
}structure-variables;
其中 tag为结构体类型名。tag或structure-varialbes之一可以省略,但两者必留其一。
29.可以用单赋值语句把一个结构变量的全部内容赋给另一个同类结构变量,而不必逐个成员地多次赋值。
30.C语言具备访问字节中位的内设机制,称为位域(bit-field),通过它可以访问单个的位。结构中的位域的定义方法为:type name:length;
type 指定位域的类型,length指定位域的位数,位域的类型必须是int,signed或unsigned(C99还允许位域是BOOL型)。
位域定义如:struct status_type
{
unsigned:4;
unsigned cts:1;
unsigned dsr:1;
}status;
结构体中普通元素与位域元素混合是合法的。
位域变量也有自己的限制:不能取位域变量的地址;不能构造数组位域;位域变量不能跨越整数边界。
31.枚举的定义和结构类似,关键字enum表示开始定义。
枚举的一般形式是:enum tag{enumeration list} variable_list;
其中,枚举标记(tag)和变量表(variable_list)都是可选的(但至少要出现一个)。
枚举是一系列命名的整型常量。
32。getchar()使用时,输入先被缓冲,直到键入回车键时才被返回。也就是所谓的行缓冲输入。在使用时颇不方便。因此许多编译程序都提供了一些交互函数。如常见的函数有getch()和getche()。getch()函数在键击之后立即返回,不向屏幕回显字符。getche()函数与getch() 功能相同,但回显键字。在交互式程序中,当需要从键盘读字符时,常常要用getche()或getch()代替getchar()。在VC中函数名前加下划线。为_getch(),_getche()。
33.在使用gets()时必须小心,因为它不对接受输入的数组进行边界检查。因此,用户键入的字符可能多于数组能够容纳的字符。尽管对于用户要使用的示例程序和简单工具来说,gets()是杰出的,但在商业代码中要避免使用它。可以用fgets()函数代替它,该函数允许用户防止数组溢出。
2007-10-7
34.格式说明符%n的用法,%n不向printf()传递格式化信息,而是令printf()把自己到该点已打出的字符总数放到相应元指向的整型变量中。因此,%n对应的变元必须是整型指针。对printf()函数调用后,%n对应变元指向的变量中将含有一个整数值,表示出现%n时已经由该次printf()调用输出的字符数。
35.精度说明符详见P152。
2007-10-9
36.使用scanf()函数读入串时,函数发现第一个空白符即结束,不等回车键。这样就无法使用scanf()函数读入串“hello world”。因为读到hello后的空格即停止。
37.ANSI C标准向scanf()增加了一个新特性,称为扫描集合(scanset)。扫描集合定义了一组字符,当scanf()处理扫描集合时,将输入属于扫描集合定义的组的字符,这些字符将赋给由扫描集合的相应变元指向的字符数组。一对方括号中间的诸字符定义扫描集合,在开始的左方括号前必须用百分号作前导。
scanf(“%d%[abcdefg]%s”,&I,str,str2);
用连字符也可以说明一个连续范围,如%[A-Z]表示接收字符A到Z。
扫描集是区分大小写的。希望忽略字母的大小写时,应该分别定义大写和小写字母。
38.C语言的I/O系统给程序员提供了与设备无关的一致界面,即C的I/O系统在程序员和设备间提供了一级抽象。抽象被称为流,而实际设备则称为文件。共有两类流:文本的(text)和二进制的(binary)流。文件可以是磁盘文件、终端或打印机等。程序通过打开(open)操作把流与设备联系起来。
39.当以只读方式打开一个文件时,如果文件不存在,则fopen()失败,当以附加方式打开一个文件时,如果文件不存在,则生成之。而且,当以附加方式打开一个文件时,写向该文件的新数据将被添加到文件的结尾,而原有内容保持不变。当以写方式打开一个文件时,如果文件不存在,则生成之;如果文件存在,则会覆盖文件中的原有内容,生成新的文件。r+和w+方式的差别是,如果文件不存在,r+不会生成之,而w+则会生成之。而且,如果文件已经存在,则用w+打开会毁掉其内容,而用r+打开则安然无恙。