1.scanf("%*[^\n]"); scanf("%*c"); //清空缓冲区,在用 gets() 函数读取字符串的时候,有一些编译器会提示不安全,建议替换为 gets_s() 函数,就是因为 gets() 不能控制读取到的字符串的长度,风险极高。
2.使用 scanf() 的另外一种字符匹配方式,就是%[xxx] ,[ ] 包围起来的是需要读取的字符集合;scanf() 支持使用连字符- 来表示一个范围内的字符,例如 %[a-z]、%[0-9] 等;连字符左边的字符对应一个 ASCII 码,连字符右边的字符也对应一个 ASCII 码,位于这两个 ASCII 码范围以内的字符就是要读取的字符。注意,连字符左边的 ASCII 码要小于右边的,如果反过来,那么它的行为是未定义的。
3.scanf() 允许我们在%[ ] 中直接指定某些不能匹配的字符,具体方法就是在不匹配的字符前面加上^ ,例如:%[^\n] 表示匹配除换行符以外的所有字符,遇到换行符就停止读取;%[^0-9] 表示匹配除十进制数字以外的所有字符,遇到十进制数字就停止读取。读取一行不能包含十进制数字的字符串,并且长度不能超过 30:scanf("%30[^0-9\n]", str);
scanf() 允许把读取到的数据直接丢弃,不往变量中存放,具体方法就是在 % 后面加一个* ,例如:
%*d 表示读取一个整数并丢弃;%*[a-z] 表示读取小写字母并丢弃;%*[^\n] 表示将换行符以外的字符全部丢弃。
scanf() 控制字符串的完整写法为:
%{*} {width} type
其中,{ } 表示可有可无。各个部分的具体含义是:
type 表示读取什么类型的数据,例如 %d、%s、%[a-z]、%[^\n] 等;type 必须有。width 表示最大读取宽度,可有可无。* 表示丢弃读取到的数据,可有可无。
4.用户按下回车键时,getchar() 将读取到\n 字符,而 getch() 将读取到\r 字符。也就是说,对于不同的字符输入函数,回车键产生的字符不同,这个细节读者要引起注意。
5.'\0'? == 0, '0'==30
6.在C语言中,二维数组是按行排列的:二维数组可以看作是由一维数组嵌套而成的;如果一个数组的每个元素又是一个数组,那么它就是二维数组。当然,前提是各个元素的类型必须相同。根据这样的分析,一个二维数组也可以分解为多个一维数组,C语言允许这种分解。 例如,二维数组a[3][4] 可分解为三个一维数组,它们的数组名分别为 a[0]、a[1]、a[2]
7.void display_array(int arr[], int len);参数一并没有写成指针;插入和删除数组元素都要移动内存,甚至重新开辟一块内存,这是相当消耗资源的。如果一个程序中有大量的此类操作,那么程序的性能将堪忧,这有悖于「C语言非常高效」的初衷
8.普通数组(固定长度的数组)是在编译期间分配内存的,而变长数组是在运行期间分配内存的。变长数组是说数组的长度在定义之前可以改变,一旦定义了,就不能再改变了,所以变长数组的容量也是不能扩大或缩小的,它仍然是静态数组。
9.数组采用冒泡排序方法:未经优化的算法一定会进行 n-1 轮比较,经过优化的算法最多进行 n-1 轮比较。
|