上一部分我们整理了C语言的基本特点、环境、语法等详情可戳👉紫薇星上的C语言(1)
这一部分我们将会整理C语言的运算符、判断、循环与数组,冲冲冲👇
6.运算符
运算符是一种告诉编译器执行特定的数学或逻辑操作的符号。包括算术运算符、关系运算符、逻辑运算符、位运算符、赋值运算符、杂项运算符。
- 算术运算符
运算符 | 描述 | 实例(令A为10,B为20) |
---|---|---|
+ | 把两个操作数相加 | A + B 将得到 30 |
- | 从第一个操作数中减去第二个操作数 | A - B 将得到 -10 |
* | 把两个操作数相乘 | A * B 将得到 200 |
/ | 分子除以分母 | B / A 将得到 2 |
% | 取模运算符,整除后的余数 | B % A 将得到 0 |
++ | 自增运算符,整数值增加 1 | A++ 将得到 11 |
-- | 自减运算符,整数值减少 1 | A-- 将得到 9 |
同时需要注意的是,A++ 与 ++A是有区别的,区别在于A++先赋值后运算,++A先运算后赋值,例:
int c;
int a = 10;
c = a++;
int c;
int a = 10;
c = ++a;
上面程序运行后,a先赋值给c,再由10变为11 ;下面程序运行后,a先由10变为11,再赋值给c;--运算同理。
- 关系运算符
运算符 | 描述 | 实例(令A为10,B为20) |
---|---|---|
== | 检查两个操作数的值是否相等,如果相等则条件为真。 | (A == B) 为假。 |
!= | 检查两个操作数的值是否相等,如果不相等则条件为真。 | (A != B) 为真。 |
> | 检查左操作数的值是否大于右操作数的值,如果是则条件为真。 | (A > B) 为假。 |
< | 检查左操作数的值是否小于右操作数的值,如果是则条件为真。 | (A < B) 为真。 |
>= | 检查左操作数的值是否大于或等于右操作数的值,如果是则条件为真。 | (A >= B) 为假。 |
<= | 检查左操作数的值是否小于或等于右操作数的值,如果是则条件为真。 | (A <= B) 为真。 |
- 逻辑运算符
运算符 | 描述 | 实例(令A为1,B为0) |
---|---|---|
&& | 称为逻辑与运算符。如果两个操作数都非零,则条件为真。 | (A && B) 为假。 |
|| | 称为逻辑或运算符。如果两个操作数中有任意一个非零,则条件为真。 | (A || B) 为真。 |
! | 称为逻辑非运算符。用来逆转操作数的逻辑状态。如果条件为真则逻辑非运算符将使其为假。 | !(A && B) 为真。 |
- 位运算符
运算符 | 描述 | 实例(令A为60 即 0011 1100,B为13 即 0000 1101) |
---|---|---|
& | 按位与操作,按二进制位进行"与"运算。运算规则: 0&0=0; 0&1=0; 1&0=0; 1&1=1; | (A & B) 将得到 12,即为 0000 1100 |
| | 按位或运算符,按二进制位进行"或"运算。运算规则: 0|0=0; 0|1=1; 1|0=1; 1|1=1; | (A | B) 将得到 61,即为 0011 1101 |
^ | 异或运算符,按二进制位进行"异或"运算。运算规则: 0^0=0; 0^1=1; 1^0=1; 1^1=0; | (A ^ B) 将得到 49,即为 0011 0001 |
~ | 取反运算符,按二进制位进行"取反"运算。运算规则: ~1=0; ~0=1; | (~A ) 将得到 -61,即为 1100 0011,一个有符号二进制数补码形式。 |
<< | 二进制左移运算符。将一个运算对象的各二进制位全部左移若干位(左边的二进制位丢弃,右边补0)。 | A << 2 将得到 240,即为 1111 0000 |
>> | 二进制右移运算符。将一个数的各二进制位全部右移若干位,正数左补0,负数左补1,右边丢弃。 | A >> 2 将得到 15,即为 0000 1111 |
- 赋值运算符
运算符 | 描述 | 实例 |
---|---|---|
= | 简单的赋值运算符,把右边操作数的值赋给左边操作数 | C = A + B 将把 A + B 的值赋给 C |
+= | 加且赋值运算符,把右边操作数加上左边操作数的结果赋值给左边操作数 | C += A 相当于 C = C + A |
-= | 减且赋值运算符,把左边操作数减去右边操作数的结果赋值给左边操作数 | C -= A 相当于 C = C - A |
*= | 乘且赋值运算符,把右边操作数乘以左边操作数的结果赋值给左边操作数 | C *= A 相当于 C = C * A |
/= | 除且赋值运算符,把左边操作数除以右边操作数的结果赋值给左边操作数 | C /= A 相当于 C = C / A |
%= | 求模且赋值运算符,求两个操作数的模赋值给左边操作数 | C %= A 相当于 C = C % A |
<<= | 左移且赋值运算符 | C <<= 2 等同于 C = C << 2 |
>>= | 右移且赋值运算符 | C >>= 2 等同于 C = C >> 2 |
&= | 按位与且赋值运算符 | C &= 2 等同于 C = C & 2 |
^= | 按位异或且赋值运算符 | C ^= 2 等同于 C = C ^ 2 |
|= | 按位或且赋值运算符 | C |= 2 等同于 C = C | 2 |
- 杂项运算符
运算符 | 描述 | 实例 |
---|---|---|
sizeof() | 返回变量的大小。 | sizeof(a) 将返回 4,其中 a 是整数。 |
& | 返回变量的地址。 | &a; 将给出变量的实际地址。 |
* | 指向一个变量。 | *a; 将指向一个变量。 |
? : | 条件表达式 | 如果条件为真 ? 则值为 X : 否则值为 Y |
- 运算符优先级
运算符的优先级确定表达式中项的组合,这会影响到一个表达式如何计算。某些运算符比其他运算符有更高的优先级,下表将按运算符优先级从高到低列出各个运算符,具有较高优先级的运算符出现在表格的上面,具有较低优先级的运算符出现在表格的下面。在表达式中,较高优先级的运算符会优先被计算。
类别 | 运算符 | 结合性 |
---|---|---|
后缀 | () [] -> . ++ - - | 从左到右 |
一元 | + - ! ~ ++ - - (type)* & sizeof | 从右到左 |
乘除 | * / % | 从左到右 |
加减 | + - | 从左到右 |
移位 | << >> | 从左到右 |
关系 | < <= > >= | 从左到右 |
相等 | == != | 从左到右 |
位与 AND | & | 从左到右 |
位异或 XOR | ^ | 从左到右 |
位或 OR | | | 从左到右 |
逻辑与 AND | && | 从左到右 |
逻辑或 OR | || | 从左到右 |
条件 | ?: | 从右到左 |
赋值 | = += -= *= /= %=>>= <<= &= ^= |= | 从右到左 |
逗号 | , | 从左到右 |
7.判断
C语言中有许多判断语句,可以使程序员们指定一个或多个要评估或测试的条件,以及条件为真时要执行的语句(必需的)和条件为假时要执行的语句(可选的),任何非零和非空的值假定为 true,把零或 null 假定为 false。判断流程基本如下:
C语言中有以下类型的判断语句:
语句 | 描述 |
---|---|
if语句 | 一个 if 语句 由一个布尔表达式后跟一个或多个语句组成。 |
if...else语句 | 一个 if 语句 后可跟一个可选的 else 语句,else 语句在布尔表达式为假时执行。 |
嵌套if语句 | 您可以在一个 if 或 else if 语句内使用另一个 if 或 else if 语句。 |
switch语句 | 一个 switch 语句允许测试一个变量等于多个值时的情况。 |
嵌套switch语句 | 您可以在一个 switch 语句内使用另一个 switch 语句。 |
- if语句
if语句的语法为:
if(boolean_expression) //括号中为判断条件
{
/* 如果判断条件为真将执行if中的语句 */
}
/* 如果判断条件为假将跳过if执行if外的语句 */
示例:
if(true) //括号中为判断条件
{
/* 如果判断条件为真将执行if中的语句 */
a = 1;
}
/* 如果判断条件为假将跳过if执行if外的语句 */
a = 0;
- if...else语句
if...else语句的语法为:
if(boolean_expression) //括号中为判断条件
{
/* 如果判断条件为真将执行if中的语句 */
}else{
/* 如果判断条件为假将执行else中的语句 */
}
一个 if 语句后可跟一个可选的 else if...else 语句,这可用于测试多种条件。 if...else if...else 语句的语法:
if(boolean_expression_1) //括号中为判断条件
{
/* 当判断条件为 1 时执行 */
}
else if( boolean_expression_2)
{
/* 当判断条件为 2 时执行 */
}
else if( boolean_expression_3)
{
/* 当判断条件为 3 时执行 */
}
else
{
/* 当上面条件都不为真时执行 */
}
当使用 if...else if...else 语句时,以下几点需要注意:
- 一个 if 后可跟 0个或 1个 else,else 必须在所有 else if 之后。
- 一个 if 后可跟 0个或多个 else if,else if 必须在 else 之前。
- 一旦某个 else if 条件匹配成功,其他的 else if 或 else 内容语句将不会被执行。
- 嵌套if语句
可以在一个 if 或 else if 语句内使用另一个 if 或 else if 语句。嵌套if语句的语法为:
if(boolean_expression_1) //括号中为判断条件
{
/* 如果判断条件为真将执行if中的语句 */
if(boolean_expression_2) //括号中为判断条件
{
/* 如果判断条件为真将执行if中的语句 */
}
}
/* 如果判断条件为假将跳过if执行if外的语句 */
也可以嵌套 else if...else,方式与嵌套 if 语句相似。
- switch语句
switch 语句允许测试一个变量等于多个值时的情况。每个值称为一个 case,且被测试的变量会对每个 switch case 进行判断。switch语句的语法为:
switch(expression){ //括号中为判断条件
case constant-expression :
statement(s);
break; /* 可选的 */
case constant-expression :
statement(s);
break; /* 可选的 */
/* 您可以有任意数量的 case 语句 */
default : /* 可选的 */
statement(s);
}
switch 语句必须遵循下面的规则:
- switch 语句中的 expression 是一个常量表达式,必须是一个整型或枚举类型。
- 在一个 switch 中可以有任意数量的 case 语句,每个 case 后跟一个要比较的值和一个冒号。
- case 的 constant-expression 必须与 switch 中的变量具有相同的数据类型,且必须是一个常量或字面量。
- 当被测试的变量等于 case 中的常量时,case 后跟的语句将被执行,直到遇到 break 语句为止。
- 当遇到 break 语句时,switch 终止,控制流将跳转到 switch 语句后的下一行。
- 不是每一个 case 都要包含 break,如果 case 语句不包含 break,控制流将会 继续 后续的 case,直到遇到 break 为止。
- 一个 switch 语句可以有一个可选的 default case,出现在 switch 的结尾,default case 可用于在上面所有 case 都不为真时执行一个任务,default case 中的 break 语句不是必需的。
示例:
switch(a){ //括号中为判断条件
case 1 :
b = 1;
break; /* 可选的 */
case 2 :
b = 2;
break; /* 可选的 */
/* 您可以有任意数量的 case 语句 */
default : /* 可选的 */
b = 3;
}
- 嵌套switch语句
可以把一个 switch 作为一个外部 switch 的语句序列的一部分,即可以在一个 switch 语句内使用另一个 switch 语句。即使内部和外部 switch 的 case 常量包含共同的值,也没有矛盾。嵌套switch语句的语法为:
switch(ch1) {
case 'A':
printf("这个 A 是外部 switch 的一部分" );
switch(ch2) {
case 'A':
printf("这个 A 是内部 switch 的一部分" );
break;
case 'B': /* 内部 B case 代码 */
}
break;
case 'B': /* 外部 B case 代码 */
}
- 运算符(三元运算符)
除了这些判断语句外,也可以用三元运算符 ?:来替代 if...else 语句。形式为:
Exp1 ? Exp2 : Exp3;
//如果Exp1 的值为真,则Exp2 的值为整个表达式的值,否则Exp3 的值为整个表达式的值。
8.循环
有的时候,我们可能需要多次执行同一块代码。例如,计算次方,阶乘这些问题的时候,如果每次运算都使用一条语句来运行,那么会造成非常大的工作量。这时候就需要用到循环,循环语句允许我们多次执行一个语句或语句组,循环流程如下:
C语言中有以下类型的循环语句:
循环类型 | 描述 |
---|---|
while循环 | 当给定条件为真时,重复语句或语句组。它会在执行循环主体之前测试条件。 |
for循环 | 多次执行一个语句序列,简化管理循环变量的代码。 |
do...while循环 | 除了它是在循环主体结尾测试条件外,其他与 while 语句类似。 |
嵌套循环 | 您可以在 while、for 或 do..while 循环内使用一个或多个循环。 |
- while循环
while循环的语法为:
while(true) //括号中为判断条件
{
/*判断条件为真执行循环中的语句*/
}
/*判断条件为假跳出循环*/
while 循环可能一次都不会执行,当条件为 false 时,会跳过循环主体,直接执行紧接着 while 循环的下一条语句。
- for循环
for循环的语法为:
for ( init; condition; increment )
{
statement(s);
}
对 for 循环来说需要注意:
- init 会首先被执行,且只会执行一次,这一步允许声明并初始化任何循环控制变量,也可以不在这里写任何语句,只要有一个分号出现即可。
- 接下来会判断 condition,如果为真,则执行循环主体;如果为假,则不执行循环主体,且控制流会跳转到紧接着 for 循环的下一条语句。
- 在执行完 for 循环主体后,控制流会跳回上面的 increment 语句,该语句允许您更新循环控制变量,该语句可以留空,只要在条件后有一个分号出现即可。
- 条件再次被判断,如果为真,则执行循环,这个过程会不断重复(循环主体,然后增加步值,再然后重新判断条件),在条件变为假时,for 循环终止。
- do...while循环
do...while循环不像 for 和 while 循环,它们是在循环头部测试循环条件,在 C 语言中,do...while 循环是在循环的尾部检查它的条件,do...while 循环与 while 循环类似,但是 do...while 循环会确保至少执行一次循环。do...while循环的语法为:
do
{
/*首先执行循环一次,然后执行判断*/
}while(true); //括号中为判断条件
/*如果判断为真返回循环,判断为假跳出循环*/
- 嵌套循环
程序中允许在一个循环内使用另一个循环,如:
for (initialization; condition; increment/decrement)
{
statement(s);
for (initialization; condition; increment/decrement)
{
statement(s);
... ... ...
}
... ... ...
}
while (condition1)
{
statement(s);
while (condition2)
{
statement(s);
... ... ...
}
... ... ...
}
do
{
statement(s);
do
{
statement(s);
... ... ...
}while (condition2);
... ... ...
}while (condition1);
嵌套循环可以在任何类型的循环内嵌套其他任何类型的循环,如一个 for 循环可以嵌套在一个 while 循环内,反之亦然。
循环控制语句改变代码的执行顺序,通过它你可以实现代码的跳转。
控制语句 | 描述 |
---|---|
break | 终止循环或 switch 语句,程序流将继续执行紧接着循环或 switch 的下一条语句。 |
continue | 告诉一个循环体立刻停止本次循环迭代,重新开始下次循环迭代。 |
goto | 将控制转移到被标记的语句。但是不建议在程序中使用 goto 语句。 |
- break
break 语句有以下两种用法:
- 当 break 语句出现在一个循环内时,循环会立即终止,且程序流将继续执行紧接着循环的下一条语句。
- 它可用于终止 switch 语句中的一个 case。
- continue
continue 语句有点像 break 语句,但它不是强制终止,continue 会跳过当前循环中的代码强迫开始下一次循环。在 for 循环中continue 语句执行后自增语句仍然会执行。对于 while 和 do...while 循环,continue 语句重新执行条件判断语句。
- goto
goto 语句允许把控制无条件转移到同一函数内的被标记的语句。注意:在任何编程语言中,都不建议使用 goto 语句。因为它使得程序的控制流难以跟踪,难以理解和难以修改,任何使用 goto 语句的程序可以改写成不需要使用 goto 语句的写法。
//示例
while(true){
a = 0;
if(a == 1){
label:
continue;
}
break;
}
goto label;
/*
这是一个简单的程序语句,流程如下
a = 0; break; goto label; continue; a = 0;
一直循环,这里可以看出break, continue, goto的区别
*/
当判断条件被设置为一直为真时,就会出现无限循环:
while(1){
/*一直执行循环内语句*/
}
9.函数与作用域
每个 C 程序都至少有一个函数,即主函数 main() ,所有简单的程序都可以定义其他额外的函数。可以把代码划分到不同的函数中,如何划分代码到不同的函数中可以自己决定,但在逻辑上,划分通常是根据每个函数执行一个特定的任务来进行的。函数是一组一起执行一个任务的语句,函数还有很多叫法,比如方法、子例程或程序,等等。
函数声明告诉编译器函数的名称、返回类型和参数;函数定义提供了函数的实际主体;C 标准库提供了大量的程序可以调用的内置函数,例如,函数 strcat() 用来连接两个字符串,函数 memcpy() 用来复制内存到另一个位置。
- 函数声明
函数声明会告诉编译器函数名称及如何调用函数。函数的实际主体可以单独定义,格式为:
return_type function_name( parameter list );
示例:
int max(int num1, int num2);
在函数声明中,参数的名称并不重要,只有参数的类型是必需的,因此下面也是有效的声明:
int max(int, int);
注意:一个源文件中定义函数且在另一个文件中调用函数时,函数声明是必需的,在这种情况下,应该在调用函数的文件顶部声明函数。
- 函数定义
函数定义的一般形式如下:
return_type function_name( parameter list )
{
body of the function
}
上述格式中,组成部分如下:
- 返回类型:一个函数可以返回一个值,return_type 是函数返回的值的数据类型。有些函数执行所需的操作而不返回值,在这种情况下,return_type 是关键字 void。
- 函数名称:这是函数的实际名称,函数名和参数列表一起构成了函数签名。
- 参数:参数就像是占位符,当函数被调用时,会向参数传递一个值,这个值被称为实际参数。参数列表包括函数参数的类型、顺序、数量,参数是可选的,也就是说,函数可能不包含参数。
- 函数主体:函数主体包含一组定义函数执行任务的语句。
以上述max()函数,令该函数有两个参数 num1 和 num2,会返回这两个数中较大的那个数:
/* 函数返回两个数中较大的那个数 */
int max(int num1, int num2)
{
/* 局部变量声明 */
int result;
if (num1 > num2)
result = num1;
else
result = num2;
return result;
}
- 调用函数
当程序调用函数时,程序控制权会转移给被调用的函数;被调用的函数执行已定义的任务,当函数的返回语句被执行时,或到达函数的结束括号时,会把程序控制权交还给主程序。调用函数时传递所需参数,如果函数返回一个值,则可以存储返回值。我们仍使用上述的max()函数来举例:
#include <stdio.h>
/* 函数声明 */
int max(int num1, int num2);
int main ()
{
/* 局部变量定义 */
int a = 100;
int b = 200;
int ret;
/* 调用函数来获取最大值 */
ret = max(a, b);
printf( "Max value is : %d\n", ret );
return 0;
}
/* 函数返回两个数中较大的那个数 */
int max(int num1, int num2)
{
/* 局部变量声明 */
int result;
if (num1 > num2)
result = num1;
else
result = num2;
return result;
}
- 函数参数
如果函数要使用参数,则必须声明接受参数值的变量,这些变量称为函数的形式参数,形式参数就像函数内的其他局部变量,在进入函数时被创建,退出函数时被销毁,当调用函数时,有两种向函数传递参数的方式:
调用类型 | 描述 |
---|---|
传值调用 | 该方法把参数的实际值复制给函数的形式参数。在这种情况下,修改函数内的形式参数不会影响实际参数。 |
引用调用 | 通过指针传递方式,形参为指向实参地址的指针,当对形参的指向操作时,就相当于对实参本身进行的操作。 |
向函数传递参数的传值调用方法,把参数的实际值复制给函数的形式参数。在这种情况下,修改函数内的形式参数不会影响实际参数。如在上述程序中,使用a, b来传递num1, num2的值,但在传递后,无论max()函数中num1与num2发生了什么改变,a, b都不会会改变。
而通过引用传递方式,形参为指向实参地址的指针,当对形参的指向操作时,就相当于对实参本身进行的操作,传递指针可以让多个函数访问指针所引用的对象,而不用把对象声明为全局可访问。这就相当于直接将a, b拿去用作num1, num2,改变num1, num2的值就是改变了a, b的值。这部分涉及到指针,我们在以后整理指针的时候会详细讲解。
默认情况下,C 语言使用传值调用方法来传递参数,一般来说,这意味着函数内的代码不会改变用于调用函数的实际参数。
作用域是程序中定义的变量所存在的区域,超过该区域变量就不能被访问,C 语言中有三个地方可以声明变量:在函数或块内部的局部变量、在所有函数外部的全局变量、在形式参数的函数参数定义中。
- 局部变量
某个函数或块的内部声明的变量称为局部变量,它只能被该函数或该代码块内部的语句使用,在函数外部是不可知的。
- 全局变量
全局变量是定义在函数外部,通常是在程序的顶部,全局变量在整个程序生命周期内都是有效的,在任意的函数内部能访问全局变量。全局变量可以被任何函数访问,也就是说,全局变量在声明后整个程序中都是可用的。
#include <stdio.h>
/* 全局变量声明 */
int g = 20;
int main ()
{
/* 局部变量声明 */
int g = 10;
printf ("value of g = %d\n", g);
return 0;
}
局部变量和全局变量的名称可以相同,但是在函数内,如果两个名字相同,会使用局部变量值,全局变量不会被使用。
- 形式参数
函数的参数,形式参数,被当作该函数内的局部变量,如果与全局变量同名它们会优先使用。在上面调用函数部分中,a, b为实际参数,而max()函数中的num1, num2为形式参数。
10.数组
C 语言支持数组数据结构,它可以存储一个固定大小的相同类型元素的顺序集合。数组是用来存储一系列数据,但它往往被认为是一系列相同类型的变量。
数组的声明并不是声明一个个单独的变量,比如 num0、num1、...、num99,而是声明一个数组变量,比如 num,然后使用 num[0]、num[1]、...、num[99] 来代表一个个单独的变量。数组中的特定元素可以通过索引访问。
所有的数组都是由连续的内存位置组成。最低的地址对应第一个元素,最高的地址对应最后一个元素。
- 声明数组
要声明一个数组,需要指定元素的类型和元素的数量。格式如下:
type arrayName [ arraySize ];
这叫做一维数组,arraySize 必须是一个大于零的整数常量,type 可以是任意有效的 C 数据类型。例如,要声明一个类型为 double 包含 10 个元素的数组 balance:double balance[10]; balance是一个数组,可以容纳 10 个类型为 double 的数字。
- 初始化数组
可以逐个初始化数组,也可以使用一个初始化语句,如:
double balance[5] = {1000.0, 2.0, 3.4, 7.0, 50.0};
大括号 { } 之间的值的数目不能大于我们在数组声明时在方括号 [ ] 中指定的元素数目,如果您省略掉了数组的大小,数组的大小则为初始化时元素的个数,即:
double balance[] = {1000.0, 2.0, 3.4, 7.0, 50.0};
//与上述语句含义相同。
- 访问数组元素
数组元素可以通过数组名称加索引进行访问,元素的索引是放在方括号内,跟在数组名称的后边。所有的数组都是以 0 作为它们第一个元素的索引,也被称为基索引,数组的最后一个索引是数组的总大小减去 1,以此类推,如:
balance[4] = 50.0;
- 多维数组
C 语言支持多维数组。多维数组声明的一般形式如下:
type name[size1][size2]...[sizeN];
例如:我们现在创建一个三维数组:
int threedim[5][10][4];
而在C语言中,最常见的是二维数组,在本质上,是一个一维数组的列表,声明一个 x 行 y 列的二维整型数组,格式如下:
type arrayName [ x ][ y ];
其中,type 可以是任意有效的 C 数据类型,arrayName 是一个有效的 C 标识符。一个二维数组可以被认为是一个带有 x 行和 y 列的表格。因此,数组中的每个元素是使用形式为 a[ i , j ] 的元素名称来标识的,其中 a 是数组名称,i 和 j 是唯一标识 a 中每个元素的下标。
- 初始化二维数组
多维数组可以通过在括号内为每行指定值来进行初始化。下面是一个带有 3 行 4 列的数组。
int a[3][4] = {
{0, 1, 2, 3} , /* 初始化索引号为 0 的行 */
{4, 5, 6, 7} , /* 初始化索引号为 1 的行 */
{8, 9, 10, 11} /* 初始化索引号为 2 的行 */
};
同时,内部嵌套的括号是可选的,下面的初始化与上面是等同的:
int a[3][4] = {0,1,2,3,4,5,6,7,8,9,10,11};
- 访问二维数组元素
二维数组中的元素是通过使用下标(即数组的行索引和列索引)来访问的。例如:
int val = a[2][3];
这一部分我们整理了运算符、判断、循环、函数与作用域以及数组,这些已经是C语言基础中比较重要的部分了,下一部分我们会随时使用函数,数组等这些内容进行举例,下次见👋