开卷笔记

作者: 编程应用  发布:2019-09-28

第8章 字符输入/输出和输入确认
1、输入输出缓冲分为两类:完全缓冲I/O和行缓冲I/O。对完全缓冲输入来说,缓冲区满时被清空(内容被发送至目的地)。这类缓冲通常出现在文件输入中,缓冲区的大小取决于系统。对行缓冲I/O来说,遇到一个换行字符时将被清空缓冲区。键盘输入是标准的行缓冲,因此按下回车键将清空缓冲区。
2、在多数UNIX系统上,在一行的开始键入Ctrl+D会导致传送文件尾信号。许多微型计算系统将一行的开始位置键入的Ctrl+Z识别为文件尾信号,还有一些则把任意位置的Ctrl+Z解释成文件尾信号。
3、UNIX、Linux和DOS都支持重定向输入和输出。输入重定向使您的程序能够使用文件代替键盘作为输入,输出重定向则使程序能够使用文件代替屏幕作为输出。
4、UNIX、Linux和DOS下使用两个重定向运算符<和>所遵循的规则:
<1>重定向运算符将一个可执行程序(包括标准的操作系统命令)与一个数据文件连接起来,该运算符不能用于一个数据文件与另一个数据文件的连接,也不能用于一个程序与另一个程序的连接。
<2>使用这些运算符时,输入不能来自一个以上的文件,输出也不能定向至一个以上的文件。
5、重定向输入和输出的方法:
下面令prog为可执行程序的名字,并令file1和file2为文件名,
<1>将输出重定向到一个文件:prog > file1
<2>将输入重定向为来自一个文件:prog < file2
<3>组合重定向:
prog < file2 > file1
prog > file1 < file2
这两种形式都使用file2作为输入,使用file1作为输出。
6、通常,系统使用行缓冲输入(line-buffered input),这意味着输入的内容在您按下回车键时被传输给程序。按下回车键的同时还将传输给一个编程时需要注意的换行字符。
如果混合使用scanf()和getchar(),那么当调用getchar()之前scanf()恰好在输入中留下一个换行符时,将会产生问题。如果知道这个问题,就可以在编程中解决它。

第九章 函数

第9章 函数
1、形式参量
也称形式参数。如同函数内部定义的变量一样,形式参量是局部变量,它们是函数所私有的。
2、在原型声明中使用的变量名并没有实际地创建变量,此处的变量名也可以省略,而只保留其数据类型。
3、当函数返回值的类型和声明的类型不相同时,实际返回值是当把指定要返回的值赋给一个具有所声明的返回类型的变量时得到的数值。
4、无返回值的函数应该被声明为void类型。在早期版本的C语言中,如果函数没有进行类型声明,则该函数具有默认的函数类型int。使用这种默认类型的原因是早期大多数C语言函数都是int类型的。但是C99标准不再支持函数的int类型的默认设置。
5、C允许一个函数调用其本身,这种调用过程被称作递归(recursion)。关于递归使用的几个基本要点:
<1>每一级的函数调用都有自己的变量。
<2>每一次函数调用都会有一次返回。
<3>递归函数中,位于递归调用前的语句和各级被调函数具有相同的执行顺序;位于递归调用后的语句的执行顺序和各个被调用函数的顺序相反。
<4>虽然每一级递归都有自己的变量,但是函数代码并不会得到复制。函数代码是一系列的计算机指令,函数调用就是从头执行这个指令集的一条命令。一个递归调用会使程序从头执行相应函数的指令集。
<5>递归函数中必须包含可以终止递归调用的语句。
6、最简单的递归形式是把递归调用语句放在函数结尾即恰在return语句之前。这种形式被称为尾递归(tail recursion)或结尾递归(end recursion)。
7、如果循环和递归都可以用来实现某函数功能,一般来讲选择循环更好一些。首先,因为每次递归调用都拥有自己的变量集合,所以就需要占用较多的内存;每次递归调用需要把新的变量集合存储在堆栈中。其次,由于进行每次函数调用需要花费一定的时间,所以递归的执行速度较慢。
8、把函数原型和常量定义放在一个头文件中是一个很好的编程习惯。
9、一般地,当需要改变调用函数中的某个参数值时,任何被调用的无返回值的C函数都需要使用地址参数来完成该任务。
10、*和指针名之间的空格是可选的。通常程序员在声明中使用空格,而在指向变量时将其省略。

9.1 函数概述

汗舒适用于完成特定任务的程序代码的自包含单元。
为什么使用函数
一:函数的使用可以省去重复代码的编写。
二:函数使得程序更加模块化,从而有利于程序的阅读、修改和完善。
编写函数代码之前首先需要考虑的是函数的功能以及函数和程序整体上的关系。

9.1.1 函数示例

  1. #include<stdio.h>
  2. #define WIDTH 40
  3. void starbar;
  4. int main
  5. {
  6. starbar();
  7. return 0;
  8. }
  9. void starbar
  10. {
  11. int count;
  12. for(count=0;count<WIDTH;count++)
  13. putchar;
  14. putchar;
  15. }

notice:
一:starbar标识符在不同位置被使用了3次:函数原型告知编译器其函数类型,函数调用导致该函数的执行,而函数定义则确切指定了该函数的具体功能。
二:函数同变量一样有多种类型。任何程序在使用函数之前都需要声明该函数的类型。函数后接分号表明该语句是进行函数的声明而不是函数的定义。
三:starbar()原型置于main()之前,也可以置于其内。
四:程序把starbar包含在同一个文件中,您也可以将它们放在不同的两个文件中。单文件形式比较容易编译,而使用两个文件则有利于在不同的程序中使用相同的函数。
五:starbar()中的变量count是一个局部变量。这意味着该变量只在starbar()中可用。

9.1.2 定义带有参数的函数:形式参量

可以对上树函数进行变化:

void show_n_char(char ch,int num)
{
int count;
for(count=0;count<WIDTH;count++)
putchar;
}

void show_n_char(char ch,int num):通知编译器show_n_char()使用名为ch和num的两个参数,并且声明了它们的类型。ch和num被称为形式参数和形式参量,它们是局部变量是函数所私有的。
在函数原型中可以根据您的喜好省略变量名:void show_n_char;
函数调用中,通过实际参数对ch和num赋值。形式参量是被调函数中的变量,而实际参数是调用函数分配给被调函数变量的特定数值。
因为被调函数使用的值是从调用函数中复制而来的,所以不管在被调函数中对复制数值进行什么操作,被调函数中的原数值不会受到任何影响。
可以使用return从函数中返回一个值。
但函数返回值的类型和声明的类型不相同时会有什么结果呢?
实际返回值是当把指定要返回的值赋给一个具有所声明的返回类型的变量时得到的数值。
return语句的另一个作用是终止执行函数,并把控制返回给调用函数的下一个语句。

9.1.3 函数类型

函数应该进行类型声明。同时其类型应和返回值类型相同。而无返回值的函数应该被声明为void类型。在早期版本中,如果函数没有进行类型声明,则该函数具有默认的函数类型int。
函数声明需要在使用函数前进行。
函数声明只是将函数类型告诉编译器,而函数定义部分则是函数的实际实现代码。

9.1.4 函数原型

调用函数首先把参数放在一个成为堆栈的临时存储区域里,然后被调函数从堆栈中读取这些参数。
函数原型是对语言的有力补充。它可以使编译器发现函数使用时可能出现的错误或疏漏。

9.2 递归

C允许一个函数调用其本身。这种调用过程被称作递归。
递归一般可以代替循环语句使用,使得程序结构优美,但其执行效率却没有循环语句高。

9.2.1 函数示例

  1. #include<stdio.h>
  2. void up_and_down;
  3. int main
  4. {
  5. up_and_down;
  6. return 0;
  7. }
  8. void up_and_down
  9. {
  10. printf("%d:n %pn",n,&n);
  11. if
  12. up_and_down;
  13. printf("%d:n %pn",n,&n);
  14. }

图片 1

每一级递归都使用它自己的私有变量n。调用是的地址和返回时的地址是相同的。
每一次函数调用都会有一次返回。当程序流执行到某一级递归的结尾处时,它会转移到前一级递归继续执行,是通过递归的每一级逐步返回。
递归函数中,位于递归调用前的语句和各级被调函数具有相同的执行顺序。
递归函数中,位于递归调用前的语句和各级被调函数具有相反的执行顺序。
虽然每一级递归都有自己的变量,但是函数代码并不会的得到复制。
递归函数中必须包含可以终止递归调用的语句。

最简单的递归形式是把尾递归语句放在函数结尾即恰在return语句之前。这种形式被称作尾递归或结尾递归。

9.2.2 递归的优缺点

优点:为某些编程问题提供了最简单的解决方法。
缺点:一些递归算法会很快耗尽计算机的内存资源。

9.3 多源代码文件程序的编译

9.3.1 UNIX

首先假定UNIX系统下安装了标准的UNIX C编译器cc。文件file1.c和file2.c中包含有C函数。下面的命令将把这两个文件编译在一起并生成可执行文件a.out
ccfile1.c file2.c
将生成两个目标文件file1.o和file2.o
使用下列命令编译第一个文件并将其链接到第二个文件的目标代码。
ccfile1.c file2.o

9.3.2 Linux

gccfile1.c file2.c
gccfile1.c file2.o

9.3.3 Windows

Windows系统下的编译器是面向工程的。工程描述了一个特定的程序所使用的资源。
运行多文件时,需要使用相应的菜单命令将源代码文件加入到一个工程之中。
如果把main()函数放在第一个文件中而把自定义函数放在第二个文件中实现,那么第一个文件仍需要使用函数原型。
如果把函数原型放在一个头文件中,就不必每次使用这些函数时输入其原型声明。

9.4 指针简介

指针是一个其数值为地址的变量。
int *ptr=& pooh; 把pooh的地址赋给ptr。ptr为一变量,而&pooh是一个常量。

9.4.1 间接运算符:*

对指针使用间接运算符,可以获取其指向地址存放的数值。

9.4.2 地址运算符:&

一元运算符&可以取得变量的存储地址。一个变量的地址可以被看作是该变量在内存中的位置。
%P是输出地址的说明符。

本文由金沙澳门官网送注册58发布于编程应用,转载请注明出处:开卷笔记

关键词: