C语言复习笔记

## **代码语言**

1、一个说明或一个语句占一行,例如:包含头文件、一个可执行语句结束都需要换行;

2、函数体内的语句要有明显缩进,通常以按一下Tab键为一个缩进;

3、括号要成对写,如果需要删除的话也要成对删除;

4、当一句可执行语句结束的时候末尾需要有分号;

5、代码中所有符号均为英文半角符号。

## **程序解释**

多行注释:  /* 注释内容 */                               单行注释:  //注释一行

## **有名有姓的C**

**标识符**可以是**字母(A~Z,a~z)**、**数字(0~9)**、**下划线_**组成的字符串,并且**第一个字符必须是字母或下划线**。在使用标识符时还有注意以下几点:

(1)标识符的长度最好**不要超过8位**

(2)标识符是**严格区分大小写**的

(3)标识符最好选择**有意义的英文单词**组成做到"见名知意",不要使用中文。

(4)标识符**不能是C语言的关键字**。

## **变量及赋值**

在定义中不允许连续赋值,如int a=b=c=5;是不合法的。

## **基本数据类型**

C语言中,数据类型可分为:基本数据类型,构造数据类型,指针类型,空类型四大类。

**整型数据是指不带小数的数字**。

int整型     short int短整型(int可省略)      long int长整型(int可省略)     unsigned int无符号整型     unsigned short int无符号短整型(int可省略)     unsigned long int无符号长整型(int可以省略)

**浮点数据是指带小数的数字**。

float单精度型     double双精度型     long double长双精度型

C语言中不存在字符串变量,字符串只能存在字符数组中

## 格式化输出语句

%d带符号十进制整数     %c单个字符     %s字符串     %f 6位小数

如果要输出多个变量的并指定变量的位置时候,格式符还可以连用,变量之间需要用逗号隔开;格式符的个数要与变量、常量或者表达式的个数一一对应   

## 不可改变的常量

**直接常量**也称为字面量,是可以直接拿来使用,无需说明的量,比如:

- 整型常量:13、0、-13;

- 实型常量:13.33、-24.4;

- 字符常量:‘a’、‘M’

- 字符串常量:”I love imooc!”

 #define 标识符 常量值 

**符号常量**的标示符一般习惯使用大写字母,变量的标示符一般习惯使用小写字母,加以区分。

## **自动类型转换**

发生在不同数据类型运算时,在编译的时候自动完成。字节小的可以向字节大的自动转换,但字节大的不能向字节小的自动转换。

## **强制类型转换**

一般形式:(数据类型)(表达式)

1.数据类型和表达式都必须**加括号**

2.是在本次运算中**临时性转换**

3.强制转换后的运算结果**不遵循四舍五入原则**

## 运算符号

  ※ 算术运算符 + - * / % ++ --

   ※ 赋值运算符 =

   ※ 关系运算符 >   >=   <   <=   ==   !=  关系表达式的值是“真”和“假”,在C程序用整数1和0表示。

注意:>=,<=,==,!=这种符号之间不能存在空格。

   ※ 逻辑运算符 &&逻辑与   ||逻辑或   !逻辑非

1. 与运算(&&)  全真则真,一假则假

2. 或运算(||)   一真则真,全假则假

3. 非运算(!)   参与运算的变量**为真时**,结果**为假**;参与运算量**为假时**,结果**为真**。例如:!(5>8),运算结果为真。

   ※ 三目运算符  格式:表达式1?表达式2:表达式3;

## 运算符大比拼之优先级比较

1.()2.! +(正号) -(负号) ++ --  3. * / %  4. + - 5. < <= >= > 6. ==  != 7.&& 8.|| 9. ?: 10. =  +=  -=  *=  /=  %=

## 简单if语句                       

基本结构                                                             

`if(表达式)`

`{`

​    `执行代码块;`

`}`

## 简单if-else语句

基本结构

`if(表达式)`

`{`

​    `执行代码块1;`

`}`

`else`

`{`

​    `执行代码块2;`

`}`

## 多重if-else语句

![image20221104204547458.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/376026fd-c301-4605-ac16-1a2139f821eb.png)
## 嵌套if-else语句

![image20221104204609985.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/312441e4-8519-40f5-8937-97d386fc861d.png)
### while循环

C语言while循环的结构![image20221011142114631.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/303f6638-7cf3-4176-a6a9-ff3236f3b1bd.png)
使用while语句应注意以下几点:

1、while语句中的**表达式一般是关系表达或逻辑表达式**,当表达式的值为假时不执行循环体,反之则循环体一直执行。

2、一定要记着**在循环体中改变循环变量的值**,否则会出现死循环(无休止的执行)。

3、循环体如果包括有一个以上的语句,则**必须用{}括起来**,组成复合语句。

## do-while循环

C语言中的do-while循环![image20221011143410887.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/76f123d5-8577-4e29-8f04-e22d39f2aeb6.png)
**do-while循环至少要执行一次循环语句**

## for循环

![image20221104205026221.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/51ba7bae-65b3-4ee1-b3b5-bdf6a8eabde0.png)

for循环中的分号一定要写

**注意**:

1、for循环中的“表达式1、2、3”均可可以缺省,但**分号(;)不能缺省**。

2、省略“表达式1(循环变量赋初值)”,**表示不对循环变量赋初始值**。

3、省略“表达式2(循环条件)”,不做其它处理,**循环一直执行(死循环)**。

4、省略“表达式3(循环变量增量)”,不做其他处理,**循环一直执行(死循环)**。

5、表达式1可以是设置循环变量的初值的赋值表达式,**也可以是其他表达式**。

6、表达式1和表达式3可以是一个简单表达式**也可以是多个表达式以逗号分割**。

7、表达式2一般是**关系表达式或逻辑表达式**,但**也可是数值表达式或字符表达式**,只要其**值非零**,就执行循环体。

8、各表达式中的变量一定要在for循环之前定义。

## 三种循环比较

1、在**知道循环次数**的情况下更适合**使用for循环**;

2、在**不知道循环次数**的情况下适合**使用while或者do-while循环**,如果有可能**一次都不循环**应考虑使用**while循环**,如果**至少循环一次**应考虑使用**do-while循环**。

但是从本质上讲,**while,do-while和for循环之间是可以相互转换的**,

## break语句

1、在没有循环结构的情况下,break**不能用在单独的if-else语句中**。

2、在多层循环中,一个**break语句只跳出当前循环**。

## continue语句

作用是**结束本次循环开始执行下一次循环**。

**break语句与continue语句的区别是:break是跳出当前整个循环,continue结束本次循环开始下一次循环。** 

## switch语句

![image20221104233326769.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/7fd4f0b3-8c81-4451-b997-35a93cf04b35.png)
在使用switch语句时还应注意以下几点:

1、在case后的**各常量表达式的值不能相同**,否则会出现错误。

2、在case子句后如果没有break;会一直往后执行一直到遇到break;才会跳出switch语句。

3、switch后面的表达式语句只能是**整型或者字符类型**。

4、在case后,**允许有多个语句**,可以不用{}括起来。

5、各case和default子句的先后顺序可以变动,而不会影响程序执行结果。

6、default子句可以省略不用。

## goto语句

goto语句是一种无条件分支语句,goto 语句的使用格式为:

goto 语句标号;

其中语句标号是一个标识符,该标识符一般用英文大写并遵守标识符命名规则,这个标识符加上一个“:”一起出现在函数内某处,执行goto语句后,程序将跳转到该标号处并执行其后的语句。

goto语句通常不用,主要因为它将使程序层次不清,且不易读,但在特定情况下,可以使用goto语句来提高程序的执行速度,所以还是少用为妙。

## 自创函数

自定义函数的一般形式:![5492adbb0001a2d802890112.jpg](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/5e391cae-aef1-4d22-8333-a319cdbb1473.jpg)

`*自定义函数名不能与关键字冲突`

`*参数列表,之后调用函数时输入的参数要与参数列表中的一一对应`

注意:

1、[]包含的内容可以省略,数据类型说明省略,默认是int类型函数;参数省略表示该函数是无参函数,参数不省略表示该函数是有参函数;

2、函数名称遵循标识符命名规范;

3、**自定义函数尽量放在main函数之前**,如果要放在main函数后面的话,需要在main函数之前先声明自定义函数,声明格式为:[数据类型说明] 函数名称([参数]);

## 函数调用

在C语言中,函数调用的一般形式为:函数名([参数]);

`自创函数的返回值会作为后续函数调用的整体输出值`

注意:

1、对无参函数调用的时候可以将[]包含的省略。

2、[]中可以是常数,变量或其它构造类型数据及表达式,各参数之间用逗号分隔。

## 有参与无参

在函数中不需要函数参数的称之为无参函数,在函数中需要函数参数的称之为有参函数

![image20221018151324796.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/8efa7b22-e071-45ad-92d1-958fd5af9cda.png)

有参函数和无参函数的唯一区别在于:函数()中多了一个参数列表。

有参函数更为灵活,输出的图形可以随着n的改变而随意变动,只要在main函数中传递一个参数就可以了;而在无参函数中输出的相对就比较固定,当需要改动的时候还需要到自定义的方法内改变循环变量的值。

## 形参与实参

形参是在定义函数名和函数体的时候使用的参数,目的是用来接收调用该函数时传入的参数;实参是在调用时传递该函数的参数。

**形参只有在函数内部有效**。函数调用结束返回主调函数后则不能再使用该形参变量。
实参可以是常量、变量、表达式、函数等,**无论实参是何种类型的量,在进行函数调用时,它们都必须具有<u>确定的值</u>**,以便把这些值传送给形参。因此应预先用赋值等办法使实参获得确定值。
在参数传递时,实参和形参在**数量上,类型上,顺序上应严格一致**,否则会发生类型不匹配”的错误。

## 函数的返回值

函数被调用之后,执行函数体中的程序段所取得的并返回给主调函数的值。

函数的返回值要注意以下几点:

1. 函数的值只能通过return语句返回主调函数。return语句的一般形式为:

   **return 表达式**   或者为:  **return (表达式)**;

2. 函数值的类型和函数定义中函数的类型应保持一致。如果两者不一致,则**以函数返回类型为准**,自动进行类型转换。

3. 没有返回值的函数,返回类型为void。

   <u>注意:void函数中可以有执行代码块,但是不能有返回值,另void函数中如果有return语句,该语句只能起到结束函数运行的功能。其格式为:return;</u>

   **自定义的函数中可以有多个return语句,但是只能返回一个值**

   

## 递归函数

递归就是一个函数在它的函数体内调用它自身。执行递归函数将反复调用其自身,每调用一次就进入新的一层。递归函数核心注意,反复调用自身,有相同运算规律。

递归函数特点:

每一级函数调用时都有自己的变量,但是函数代码并不会得到复制,如计算5的阶乘时每递推一次变量都不同;
每次调用都会有一次返回,如计算5的阶乘时每递推一次都返回进行下一次;
递归函数中,位于递归调用前的语句和各级被调用函数具有相同的执行顺序;
递归函数中,位于递归调用后的语句的执行顺序和各个被调用函数的顺序相反;
递归函数中必须有终止语句。
一句话总结递归:**自我调用且有完成状态。**

## 局部与全局

**局部变量也称为内部变量**。局部变量是在函数内作定义说明的。其**作用域仅限于函数内**, 离开该函数后再使用这种变量是非法的。在复合语句中也可定义变量,其作用域只在复合语句范围内。

**全局变量也称为外部变量**,它是在函数外部定义的变量。它不属于哪一个函数,它属于一个源程序文件。其**作用域是整个源程序**。

## 数组

数组是一块连续的,大小固定并且里面的数据类型一致的内存空间。如何声明一个数组:

数据类型 数组名称[长度];

数组初始化是有三种形式的,分别是:

1、 数据类型 数组名称[长度n] = {元素1,元素2…元素n};

2、 数据类型 数组名称[] = {元素1,元素2…元素n};

3、 数据类型 数组名称[长度n]; 数组名称[0] = 元素1; 数组名称[1] = 元素2; 数组名称[n-1] = 元素n;

我们将数据放到数组中之后又如何获取数组中的元素呢?

**获取数组元素**时: 数组名称[元素所对应下标]; 

如:初始化一个数组 int arr[3] = {1,2,3}; 那么arr[0]就是元素1。

**注意**:

1、**数组的下标均以0开始**;

2、数组在初始化的时候,数组内元素的个数不能大于声明的数组长度;

3、如果采用第一种初始化方式,元素个数小于数组的长度时,多余的数组元素初始化为0;

4、在声明数组后没有进行初始化的时候,静态(static)和外部(extern)类型的数组元素初始化元素为0,自动(auto)类型的数组的元素初始化值不确定。

## 数组的遍历

数组就可以采用循环的方式将每个元素遍历出来,而不用人为的每次获取指定某个位置上的元素。

数组遍历时要注意以下几点:

1、最好避免出现数组越界访问,循环变量最好不要超出数组的长度

2、C语言的数组长度一经声明,长度就是固定,无法改变,并且C语言并不提供计算数组长度的方法。

## 数组作为函数参数

数组可以由整个数组当作函数的参数,也可以由数组中的某个元素当作函数的参数:

1、整个数组当作函数参数,即把数组名称传入函数中

2、数组中的元素当作函数参数,即把数组中的参数传入函数中

数组作为函数参数时注意以下事项:

1、数组名作为函数实参传递时,函数定义处作为接收参数的数组类型形参既可以指定长度也可以不指定长度。

2、数组元素作为函数实参传递时,**数组元素类型必须与形参数据类型一致。**

## 字符串与数组

字符串就是由多个字符组合而成的一段话。

可以使用数组来定义我们所要的字符串。一般有以下两种格式:

1、**char 字符串名称[长度] = "字符串值";**

2、**char 字符串名称[长度] = {'字符1','字符2',...,'字符n','\0'};**

<u>注意:</u>

1、[]中的长度是可以省略不写的;

2、采用第2种方式的时候最后一个元素必须是'\0','\0'表示字符串的结束标志;

3、采用第2种方式的时候在数组中不能写中文。

在输出字符串的时候要使用:printf(“%s”,字符数组名字);或者puts(字符数组名字); 。

## 字符串函数

![image20221104235907831.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/42760b1c-39c2-4ceb-baef-46d81d360e73.png)

1、strlen()获取字符串的长度,在字符串长度中是不包括‘\0’而且汉字和字母的长度是不一样的。

2、strcmp()在比较的时候会**把字符串先转换成ASCII码**再进行比较,返回的结果为**0表示s1和s2的ASCII码相等**,返回结果为**1表示s1比s2的ASCII码大**,返回结果为**-1表示s1比s2的ASCII码小**

3、strcpy()拷贝之后会覆盖原来字符串且不能对字符串常量进行拷贝

4、strcat在使用时s1与s2指的内存空间不能重叠,且s1要有足够的空间来容纳要复制的字符串

## 多维数组

多维数组的定义格式是:

**数据类型 数组名称[常量表达式1] [常量表达式2]...[常量表达式n];**


这样定义了一个**名称为num**,**数据类型为int**的**二维数组**。其中**第一个[3]表示第一维下标的长度**,就像购物时分类存放的购物;**第二个[3]表示第二维下标的长度**,就像每个购物袋中的元素。

多维数组的初始化

1、数据类型 数组名称[常量表达式1] [常量表达式2]...[常量表达式n] = {{值1,..,值n},{值1,..,值n},...,{值1,..,值n}};

2、数据类型 数组名称[常量表达式1] [常量表达式2]...[常量表达式n]; 数组名称[下标1] [下标2]...[下标n] = 值;

多维数组初始化要注意以下事项:

1、采用第一种始化时数组声明必须指定列的维数。**因为系统会根据数组中元素的总个数来分配空间,当知道元素总个数以及列的维数后,会直接计算出行的维数**;

2、采用第二种初始化时数组声明必须同时指定行和列的维数。

## 多位数组的遍历

多维数组需要采用**嵌套循环**                        注意:**多维数组的每一维下标均不能越界**

## 文件基本操作

![image20221101204443449.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/75b92bbb-07bc-42aa-b57e-0a1c4460226b.png)
![image20221101204725862.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/f5e4fca4-fe75-49b7-bf8e-9cb63cd3461b.png)
![image20221102141755049.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/4eececf8-e179-4103-884d-b089630a95d0.png)
![image20221101204942145.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/a124e64b-9e09-472b-8ebf-7a84e1bec502.png)

buf 缓存         stream 即为进行的操作,文件结构体          fgets( )与gets( )类似,一次只获取一行,可通过多写几行fgets( )或用一个循环来获取多行内容

![image20221102140830809.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/7a20c304-76fc-4698-b4c6-7ad4bbc69096.png)

或![image20221102141117483.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/fbcd5b30-f8ea-4003-b6af-8a68ed92745e.png)

关于长度,可以用宏定义先定义好,便于后续代码较长时的改动![image20221102141359040.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/900ab023-af9e-4ba4-8cf3-ba6b9a78791c.png)
![image20221102141423946.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/bfbb30fb-4225-4cbf-92dc-8058478b98ce.png)
![image20221102142524764.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/c2db034c-07c1-43f6-9af2-a356e807009d.png)
![image20221102142639079.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/010ae964-eb95-44ae-a2fd-db52070666d7.png)
## 指针

### 1.类型

数据类型的本质作用:合理地利用空间     sizeof( )函数,测量空间大小  

`void test01()`

`{`

​        `//基本类型 char   short   int   long   float   double          //char 占1字        节空间`      

​        `char ch;`

​        `printf("sizeof(ch) = %d\n",sizeof(ch));  //1字节`

​        `ine num;`

​        `printf("sizeof(int) = %d\n",sizeof(int));  //4字节`

`}`

![image20221026092233254.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/154812ea-6f04-420d-b352-07ad66fe872c.png)

short 占2字节

 内存——沟通CPU和硬盘的桥梁
![image20221026092538171.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/f13c1678-8c3b-472f-be0b-2320539e162c.png)
![image20221026095025850.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/490f7821-6a2e-4bd4-8c55-860d0133aa55.png)

18 == 8位 b(二进制位)            1b只能存放0或1

### 2.指针变量

编号(地址):内存中每一个字节分配一个号码

指针变量:定义一个变量,存放上面的号码,这样的变量叫指针变量

取变量的的地址用 &   ,&num  代表标量 num的起始地址,%p是用来输出地址

![image20221027234339762.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/ec5ceee6-74de-4970-87bc-48c33b24b277.png)
![image20221027234417897.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/d743ef31-cf8e-42f1-81a7-242ff0612c96.png)

eg:    int ***p = NULL;

指针变量两种类型:自身的类型       指向的类型

自身的类型:在指针变量定义的时候,将变量名拖黑,剩下啥类型,指针变量就是啥类型。  eg:  p  自身的类型就是  int ***

指向的类型:在指针变量定义的时候,将变量名和离它最近的一个 *拖黑,剩下啥类型,指针变量指向的类型就是啥类型 。   eg:  p指向的类型是int **

指针变量指向的类型的作用:决定了指针变量所取空间内存的宽度,决定了指针变量+1跳过的单位跨度

![image20221028000240997.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/e69e73dd-affc-43ab-b62c-bafc715f9988.png)
![image20221028000635014.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/68275d31-5f0c-48ac-9cc6-4293b4ebad55.png)
![image20221028000350642.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/2dc27f78-91e0-442a-a445-9cad5076d4e5.png)

临时转换数据类型

# 结构体

![image20221101181942688.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/b1b0deee-acb2-455e-8b22-89032c3b477b.png)
![image20221101183009555.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/63061092-9fb0-4ada-899a-50575728ed86.png)
![image20221101183205391.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/4828ffbf-c6e7-4535-885a-23de93f3df5b.png)
![image20221101191348417.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/2c49012f-9a12-4ff2-b0ee-d09b97aae48d.png)
**注意字符为‘ ’ 字符串为""**
![image20221101192718446.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/9382fd83-e36f-4e11-8d45-cc3f3a9360c1.png)

 数组长度要比每个元素长度至少多1,多出来一个用来保存 \0

![image20221101193610490.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/0c005468-af92-426c-b831-c8f4f35404d8.png)

 出现类型不匹配的情况,就强制转换类型
![image20221101195608105.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/d8328a0e-670d-40f9-8775-c10e96877a83.png)
![image20221101200020794.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/04e4b816-1dd9-4609-ac69-22b90950ea84.png)
传入时间

swap(&,&) 交换函数,传入两个指针,前后交换位置

![image20221101202457529.png](https://beyondclouds.oss-cn-beijing.aliyuncs.com/blog/images/0c9de186-75de-48e2-8452-98aa73dac932.png)

 传入当前时间

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值