吾爱破解 - 52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 1703|回复: 4
收起左侧

[其他转载] 【C语言】【笔记】

[复制链接]
s.observer 发表于 2021-3-6 12:42
这是在网上自学C语言时整理的笔记
  • C环境配置(windows)
本地环境:1、文本编译器+2、C编译器1 、 dev c++  与  VS code2、在www.mingw.org下载 MinGW  安装程序(exe文件),安装后将bin目录添加到PATH环境变量中(1),在cmd中输入gcc -v查看版本信息 (2)(1)          (2)  
  • C程序结构
    • 预处理指令
    • 函数
    • 变量
    • 语句&表达式
    • 注释
hello world   
  • #include <stdio.h> 是预处理器指令,告诉 C 编译器在编译之前要包含 stdio.h 文件。
  • int main() 是主函数,程序从这里开始执行。(只能有一个main函数!)
  • 函数:1:函数首部 2:函数体(声明部分;执行部分)
  • 注释有两种形式//  单行 和/*...*/多行
  • printf(...) 是 C 中另一个可用的函数,会在屏幕上显示消息 "Hello, World!"。
  • return 0; 终止 main() 函数,并返回值 0。
  
  • C 语言的其他基本的构建块
*C的令牌(Token):C 程序由各种令牌组成,令牌可以是关键字、标识符、常量、字符串值,或者是一个符号。*分号(;):表明一个逻辑实体的结束*注释(//或/*...*/):不能在注释内嵌套注释,注释也不能出现在字符串或字符值中。 *标识符:(C 是区分大小写的编程语言),C 标识符是用来标识变量、函数,或任何其他用户自定义项目的名称。一个标识符以字母 A-Z 或 a-z 或下划线 _ 开始,后跟零个或多个字母、下划线和数字(0-9)。C 标识符内不允许出现标点字符,比如 @、$ 和 %。*关键字:
关键字
说明
auto
声明自动变量
break
跳出当前循环
case
开关语句分支
char
声明字符型变量或函数返回值类型
const
定义常量,如果一个变量被 const 修饰,那么它的值就不能再被改变
continue
结束当前循环,开始下一轮循环
default
开关语句中的"其它"分支
do
循环语句的循环体
double
声明双精度浮点型变量或函数返回值类型
else
条件语句否定分支(与 if 连用)
enum
声明枚举类型
extern
声明变量或函数是在其它文件或本文件的其他位置定义
float
声明浮点型变量或函数返回值类型
for
一种循环语句
goto
无条件跳转语句
if
条件语句
int
声明整型变量或函数
long
声明长整型变量或函数返回值类型
register
声明寄存器变量
return
子程序返回语句(可以带参数,也可不带参数)
short
声明短整型变量或函数
signed
声明有符号类型变量或函数
sizeof
计算数据类型或变量长度(即所占字节数)
static
声明静态变量
struct
声明结构体类型
switch
用于开关语句
typedef
用以给数据类型取别名
unsigned
声明无符号类型变量或函数
union
声明共用体类型
void
声明函数无返回值或无参数,声明无类型指针
volatile
说明变量在程序执行中可被隐含地改变
while
循环语句的循环条件
C99 新增关键字
_Bool
_Complex
_Imaginary
inline
restrict
C11 新增关键字
_Alignas
_Alignof
_Atomic
_Generic
_Noreturn
_Static_assert
_Thread_local

*C中的空格:只包含空格的行,可能带有注释,被C 编译器忽略。(在语句中添加空格使其可读性变得更强,更工整)。
  • C循环
1、for循环

[C] 纯文本查看 复制代码
for(单次表达式;条件表达式;末尾循环体)
{
中间循环体;
}
[C] 纯文本查看 复制代码
#include <stdio.h>
int main(void)
{
	for(int a = 10;a < 20;a = a + 1)
	{printf("a的值: %d\n",a);
	}
	return 0;
}
2、whlie 循环

[C] 纯文本查看 复制代码
while (表达式)
{
        语句;
}

}
(当表达式为真,则执行下面的语句;语句执行完之后再判断表达式是否为真,如果为真,再次执行下面的语句;然后再判断表达式是否为真……就这样一直循环下去,直到表达式为假,跳出循环。这个就是 while 的执行顺序。)eg、  
[C] 纯文本查看 复制代码
# include <stdio.h>
int main(void)
{
    int i = 1;
    int j = 1;
    double sum = 0;  //结果肯定是小数, 所以要定义成double或float型
    while (1.0/i > 1e-6)  /*当1/i小于10的-6次方时停止循环。这个循环条件是自己定的, 定得越小最后的结果就越精确。注意1一定要写成小数的形式即1.0*/
    {
        sum += (1.0 / i) * j;
        i+=2;
        j = -j;  //实现正负交替
    }
    sum *=4;
    printf("sum = %lf\n", sum);  //double是%lf, 取6位小数是%.6
    return 0;
}
         C语言
常量和变量

1、常量
  • 整型:整常数,由一个活或多个可带正负号的数字组成。
    • 十进制整数:由0~9数字组成,不能以0开始,没有前缀
    • 八进制整数:以0为前缀,其后由0~7的数字组成,没有小数部分
    • 十六进制整数:以0x或0X开头,其后为0~9的数字和a~f(或A~F)
  • 实型:浮点数

      • 十进制小数形式:由数字和小数点组成,必须有小数点(0.24或 .24 )
      • 指数形式:有十进制数、阶码标志“e”或“E”和阶码组成,阶码只能是整数。e和E前面必须有数字,后面必须是整数(不可以是12e12.4)
    • C编译系统对实型常量不分float和double,都作double处理以更精确,也可以在实型常量后面加上字母f或F来指定其为单精度实型(float)
  • 符号:被标识符表示的常量

      • 值和类型是通过符号常量的定义决定的
      • 符号常量在使用之前必须定义
        • 形式:#define + 标识符常量
    • 习惯上,为了与程序中的变量名区别,符号常量名一般用大写字母表示
  • 字符型
    • 字符常量(字符常数):只能用单撇号括起来(“()”不代表字符本身且其中只能有一个字符,引号中不能有‘    \);一般采用ASCII码表示;常量区分大小写
    • 转义字符:
转义字符
字符值
输出结果
\n
换行
将光标从当前位置移到下一行开头
\b
退格(backspace)
将光标从当前位置后退一格
\a
警告(alert)
产生声音或视觉信号
\f
换页(form feed)
将光标从当前位置移到下一页开头
\'
单撇号
\"
双撇号
"
\?
问号
\
反斜线
\
\r
回车(carrisge return)
将光标从当前位置移到本行开头
\t
水平制表符
将光标从当前位置移到下个TAB位置
\v
垂直制表符
将光标从当前位置移到下一个垂直制表对齐点
\o    \oo…其中o为一个八进制数
八进制对应ascii码
对应字符
\xh[h...]其中h为一个十六进制数
十六进制对应ascii码
对应字符
  • 字符串常量:用一对双撇号括起来的字符串(普通的字符、转义序列和通用的字符)序列
    • 定义常量
      • 使用 #define 预处理器
[C] 纯文本查看 复制代码
#include <stdio.h>、
#define l 10   
#define w  5
int main()
{
 
   int s;  
   s = l * w;
   printf("s =  %d /n", s);
  
   return 0;
}
输出:s = 50
  • 使用 const 关键字  (const 声明常量要在一个语句内完成)
[C] 纯文本查看 复制代码
#include <stdio.h>
 
int main()
{
   const int  LENGTH = 10;
   const int  WIDTH  = 5;
   //const char NEWLINE = '\n';
   int area;  
   
   area = LENGTH * WIDTH;
   printf("value of area : %d", area);  //在%d后加\n,与原代码输出结果相同
   //printf("%c", NEWLINE);
 
   return 0;
}

2、变量
变量只是在程序中可以改变的量,一旦被定义,就具备了3个基本要素:变量名、变量类型和变量值
  • 变量名:必须先定义,再使用
  • char(整数类型)、int(整型)、float(单精度浮点值)、double(双精度浮点值)、void(类型的缺失)

数据类型
指的是用于声明不同类型的变量或函数的一个广泛的系统。变量的类型决定了变量存储占用的空间和解释存储的位模式。1、基本类型:整数类型和浮点类型,(算数类型)2、枚举类型:定义在程序中只能赋予其一定的离散整数值的变量,(算数类型)3、派生类型:指针类型、数组类型、结构类型、共用体类型和函数类型4、void类型:表明没有可用的值
enum(枚举)
格式:enum 枚举名 {枚举元素1,枚举元素2,……};注意:第一个枚举成员的默认值为整型的 0,后续枚举成员的值在前一个成员上加 1。可以在定义枚举类型时改变枚举元素的值:enum season {spring, summer=3, autumn, winter};没有指定值的枚举元素,其值为前一元素加 1。也就说 spring 的值为 0,summer 的值为 3,autumn 的值为 4,winter 的值为 5
枚举变量的定义
1、先定义枚举类型,再定义枚举变量
[C] 纯文本查看 复制代码
enum DAY
{
      MON=1, TUE, WED, THU, FRI, SAT, SUN
};
enum DAY day;
2、定义枚举类型的同时定义枚举变量
[C] 纯文本查看 复制代码
enum DAY
{
      MON=1, TUE, WED, THU, FRI, SAT, SUN
} day;
3、省略枚举名称,直接定义枚举变量

enum
{
      MON=1, TUE, WED, THU, FRI, SAT, SUN
} day;
C 语言中,枚举类型被当做 int 或者 unsigned int 类型来处理。可以使用for 来遍历枚举的元素(元素必须连续)
将整数转换为枚举
[C] 纯文本查看 复制代码
#include <stdio.h>
#include <stdlib.h>
 
int main()
{
 
    enum day
    {
        saturday,
        sunday,
        monday,
        tuesday,
        wednesday,
        thursday,
        friday
    } workday;
 
    int a = 1;
    enum day weekend;
    weekend = ( enum day ) a;  //类型转换
    //weekend = a; //错误
    printf("weekend:%d",weekend);
    return 0;
}

C储存类
  • auto:所有局部变量默认的存储类,只能用在函数内,即 auto 只能修饰局部变量。
  • register:用于定义存储在寄存器中而不是 RAM 中的局部变量
  • static:
    • 指示编译器在程序的生命周期内保持局部变量的存在,而不需要在每次它进入和离开作用域时进行创建和销毁。因此,使用 static 修饰局部变量可以在函数调用之间保持局部变量的值。
    • static 修饰符也可以应用于全局变量。当 static 修饰全局变量时,会使变量的作用域限制在声明它的文件内。
    • 全局声明的一个 static 变量或方法可以被任何函数或方法调用,只要这些方法出现在跟 static 变量或方法同一个文件中。
  • extern:用于提供一个全局变量的引用,全局变量对所有的程序文件都是可见的。对于无法初始化的变量,会把变量名指向一个之前定义过的存储位置。

运算符
  • 算数运算符:
+ 、-、*、 /、 %(取余)、++(整数增加1)、--(整数减少1)
  • eg
[C] 纯文本查看 复制代码
#include <stdio.h>
 
int main()
{
   int a = 21;
   int b = 10;
   int c ;
 
   c = a + b;
   printf("Line 1 - c 的值是 %d\n", c );
   c = a - b;
   printf("Line 2 - c 的值是 %d\n", c );
   c = a * b;
   printf("Line 3 - c 的值是 %d\n", c );
   c = a / b;
   printf("Line 4 - c 的值是 %d\n", c );
   c = a % b;
   printf("Line 5 - c 的值是 %d\n", c );
   c = a++;  // 赋值后再加 1 ,c 为 21,a 为 22
   printf("Line 6 - c 的值是 %d\n", c );
   c = a--;  // 赋值后再减 1 ,c 为 22 ,a 为 21
   printf("Line 7 - c 的值是 %d\n", c );


 
}
  • 关系运算符(检查并判断条件真假)
==  (等于)   != (不等于)      > (大于)    < (小于)     >=  (大于等于)      <= (小于等于)   
[C] 纯文本查看 复制代码
#include<stdio.h>
int main(void) 


{
	int a = 12;
	int b = 12;
	
	if(a == b)
	{
		printf("abcdefg \n");
	}
	else
	{
		printf("qwer \n");
	}
	if(a < b)
	{
		printf("qwersz \n"); 
	}
	else
	{
		printf("poiu \n");
	}
	return 0;
}
  • 逻辑运算符
    • &&(逻辑与运算符):两个操作数都非零,则条件为真。
    • ||(逻辑或运算):两个操作数中有任意一个非零,则条件为真。
    • !(辑非运算符):逆转操作数的逻辑状态。如果条件为真则逻辑非运算符将使其为假。(放在括号前)
  • 位运算符(按二进制进行计算)
    • 位运算符作用于位,并逐位执行操作。
&与         |或       ^异或      ~取反         <<二进制左移(左边的二进制位丢弃,右边补0)>>二进制右移(右边的二进制位丢弃,正数左补0,负数左补1)
  • 赋值运算符
运算符
描述
实例
=
赋值运算符把右边的值赋给左边
C = A + B
+=
加且赋值运算符把右边数加上左边数的结果赋值给左边
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()  (返回变量的大小。。。字节数)&  (返回变量的地址)*(指向一个变量)?  (条件表达式)
  • 运算符优先级(从左到右)
    • 后缀           ()            []             ->            .                ++             - -
    • 一元           +       -      !      ~      ++      - -       (type)       *      &      sizeof
    • 乘除           *          /      %
    • 加减          +     -
    • 移位          <<           >>
    • 关系          <       <=             >          >=
    • 相等                      ==          !=
    • 位与 AND            &
    • 位异或XOR          ^
    • 位或 OR               |
    • 逻辑与 AND         &&
    • 逻辑或 OR            ||
    • 条件                      ?
    • 赋值           =      +=       -=       *=       /=      %=       >>=     <<=    &=        ^=      |=
    • 逗号                     ,
  
C判断与选择
C 语言把任何非零和非空的值假定为 true,把零或 null 假定为 false
  • 判断语句
    • if语句
      • 一个 if 语句 由一个布尔表达式后跟一个或多个语句组成

      布尔表达式(Boolean expression)是一段代码声明,它最终只有true(真)和false(假)两个取值。最简单的布尔表达式是等式(equality),这种布尔表达式用来测试一个值是否与另一个值相同。——百度百科
[C] 纯文本查看 复制代码
 

if(boolean_expression)
{
   /* 如果布尔表达式为真将执行的语句 */
}
如果布尔表达式为 true,则 if 语句内的代码块将被执行。如果布尔表达式为 false,则 if 语句结束后的第一组代码(闭括号后)将被执行。
  • if...else
    • if...else语句
      • 一个 if 语句 后可跟一个可选的 else 语句,else 语句在布尔表达式为 false 时执行。
[C] 纯文本查看 复制代码
if(boolean_expression)
{
   /* 如果布尔表达式为真将执行的语句 */
}
else
{
   /* 如果布尔表达式为假将执行的语句 */
}
如果布尔表达式为 true,则执行 if 块内的代码。如果布尔表达式为 false,则执行 else 块内的代码。
  • if...else if......else语句
[C] 纯文本查看 复制代码
if(boolean_expression 1)
{
   /* 当布尔表达式 1 为真时执行 */
}
else if( boolean_expression 2)
{
   /* 当布尔表达式 2 为真时执行 */
}
else if( boolean_expression 3)
{
   /* 当布尔表达式 3 为真时执行 */
}
else 
{
   /* 当上面条件都不为真时执行 */
}
注意: 一个 if 后可跟零个或一个 else,else 必须在所有 else if 之后。一个 if 后可跟零个或多个 else if,else if 必须在 else 之前。一旦某个 else if 匹配成功,其他的 else if 或 else 将不会被测试。  
  • 嵌套if语句
可以在一个 ifelse if 语句内使用另一个 ifelse if 语句嵌套 if 语句的语法:
[C] 纯文本查看 复制代码
if( boolean_expression 1)
{
   /* 当布尔表达式 1 为真时执行 */
   if(boolean_expression 2)
   {
      /* 当布尔表达式 2 为真时执行 */
   }
}
比如:
[C] 纯文本查看 复制代码
#include <stdio.h>
 
int main ()
{
   /* 局部变量定义 */
   int a = 100;
   int b = 200;
 
   /* 检查布尔条件 */
   if( a == 100 )
   {
       /* 如果条件为真,则检查下面的条件 */
       if( b == 200 )
       {
          /* 如果条件为真,则输出下面的语句 */
          printf("a 的值是 100,且 b 的值是 200\n" );
       }
   }
   printf("a 的准确值是 %d\n", a );
   printf("b 的准确值是 %d\n", b );
 
r
eturn 0;}结果是:

a 的值是 100,且 b 的值是 200

a 的准确值是 100

b 的准确值是 200
如果改一下:第一个if判定为false,则执行else后的语句
[C] 纯文本查看 复制代码
#include <stdio.h>
 
int main ()
{
   /* 局部变量定义 */
   int a = 100;
   int b = 200;
 
   /* 检查布尔条件 */
   if( a == 200 )                                //将条件都改为false
   {
       /* 如果条件为真,则检查下面的条件 */
       if( b == 100 )
       {
          /* 如果条件为真,则输出下面的语句 */
          printf("a 的值是 100,且 b 的值是 200\n" );
       }
       else
       {
         printf("b 的值是 200,不是100\n");
       }
   }
   else
   {
        if( b == 200 )
         {
          printf("a 的值是 100,且 b 的值是 200\n" );
         }
     
   }
   printf("a 的准确值是 %d\n", a );
   printf("b 的准确值是 %d\n", b );
 
   return 0;
}
  • 选择语句
    • switch语句
一个 switch 语句允许测试一个变量等于多个值时的情况。每个值称为一个 case,且被测试的变量会对每个 switch case 进行检查。
[C] 纯文本查看 复制代码
switch(expression)
{
    case constant-expression  :
       statement(s);
       break; /* 可选的 */
    case constant-expression  :
       statement(s);
       break; /* 可选的 */
  
    /* 可以有任意数量的 case 语句 */
    default : /* 可选的 */
       statement(s);
}
注意:
  • expression 是一个常量表达式,必须是一个整型或枚举类型。
  • 在一个 switch 中可以有任意数量的 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 语句不是必需的。
eg:  
  • 嵌套switch语句
把一个 switch 作为一个外部 switch 的语句序列的一部分,即可以在一个 switch 语句内使用另一个 switch 语句。即使内部和外部 switch 的 case 常量包含共同的值,也没有矛盾
[C] 纯文本查看 复制代码
switch(ch1)
 {
   case 'A': 
        printf("外部 switch 的A" );
        switch(ch2)
         {
           case 'A':
              printf("内部 switch 的A" );
              break;
           case 'B': //内部 B case 代码 
         }
        break;
   case 'B': //外部 B case 代码 
 }

C循环
  • while循环
只要给定的条件为真,C 语言中的 while 循环语句会重复执行一个目标语句。
[C] 纯文本查看 复制代码
while(表达式)             //语句块
{
    语句块                //循环体
}
[C] 纯文本查看 复制代码
#include <stdio.h>
int main(){
    int i = 1, sum = 0;
    while(i <= 100){
        sum += i;
        i++;
    }
    printf("%d\n",sum);
    return 0;
}
  • do...while循环
[C] 纯文本查看 复制代码
  do
  {
      语句块
  }
  while(表达式);
do-while循环会先执行“语句块”,然后再判断表达式是否为真,如果为真则继续循环;如果为假,则终止循环。因此,do-while 循环至少要执行一次“语句块”。 eg:用do-while计算35加到10086的值:
[C] 纯文本查看 复制代码
#include <stdio.h>
int main()
{
    int i=35, sum=0;
    do{
        sum+=i;
        i++;
    }
    while(i<=10086);
    printf("%d\n", sum);
    return 0;
}
do...whlie语句与while语句还有一个明显的区别就是在while(i<=10086);后有分号
  • for循环
[C] 纯文本查看 复制代码
for(表达式1; 表达式2(循环条件); 表达式3(自增或自减))
{
    语句块(循环体);
}
执行顺序为:从1、2、3依次执行,且表达式1 仅执行一次,执行表达式2时,若其值为真则进行,反之则停止。重复执行表达式2、3,直至表达式2 不成立,循环结束。其中:for的作用是使表达式2,、3不断执行观察whlie循环的例子,发现for循环也能进行从1加到100的操作
[C] 纯文本查看 复制代码
#include<stdio.h>
int main()
{
  int i,sum;
  for (i = 1,i <= 100,i = i + 1)
  {
    sum  += i;
  }
  printf ("从一加到一百等于 %d\n",sum);
  return 0;


}
可见:for循环中的条件更加紧凑在for循环中,for语句中的表达式1可以拿到外面,但 ;不能省略表达式2省略后需做其他处理,否则会变成死循环 省略了表达式3,就不会修改表达式2中的变量,这时可在循环体中加入修改变量的语句当三个表达式全省略时,程序会一直运行下去
[C] 纯文本查看 复制代码
#include <stdio.h>
 
int main ()
{
   for( ; ; )
   {
      printf("循环会永远执行下去!\n");
   }
   return 0;
}
  • 嵌套循环
循环语句可以在任何类型的循环内嵌套其他任何类型的循环。
  • 循环控制语句
改变代码的执行顺序,实现代码的跳转。
  • break语句
  • break 语句出现在一个循环内时,循环会立即终止,且程序流将继续执行紧接着循环的下一条语句。
  • 它可用于终止 switch 语句中的一个 case。
  • 当使用嵌套循环时,break语句会结束最内层的循环
  • continue循环
跳过当前循环中的代码,强迫开始下一次循环。#对于 for 循环,continue 语句执行后自增语句仍然会执行。#对于 while 和 do...while 循环,continue 语句会重新执行条件判断语句。
  • goto语句
把控制无条件转移到同一函数内的被标记的语句。*注意:在任何编程语言中,都不建议使用 goto 语句。因为它使得程序的控制流难以跟踪,使程序难以理解和难以修改。任何使用 goto 语句的程序可以改写成不需要使用 goto 语句的写法。
C函数
C语言允许我们将常用的代码以固定的格式封装(包装)成一个独立的模块,只要知道这个模块的名字就可以重复使用,这个模块就叫做函数(Function)。函数的本质是一段可以重复使用的代码,这段代码被提前编写好了,放到了指定的文件中,使用时直接调取即可。C语言自带的函数称为库函数。C语言自带的库称为标准库(Standard Library),其他公司或个人开发的库称为第三方库(Third-Party Library)。自己编写的函数称为自定义函数。自定义函数和库函数在编写和使用方式上完全相同。结构:
  • 返回类型:一个函数可以返回一个值。有些函数执行所需的操作而不返回值,在这种情况下,返回类型是 void。
  • 函数名称:这是函数的实际名称。函数名和参数列表一起构成了函数签名。
  • 参数:参数就像是占位符。当函数被调用时,您向参数传递一个值,这个值被称为实际参数。参数列表包括函数参数的类型、顺序、数量。参数是可选的,也就是说,函数可能不包含参数。
  • 函数主体:函数主体包含一组定义函数执行任务的语句。
[C] 纯文本查看 复制代码
void sum(int begin,int end)
{
    int i;
    int sum =0;
    for (i=begin; i<=end; i++){
        sum += i;
    }
    printf("%d到%d的和是%d/n",begin,end,sum);
}
其中“void”是返回类型,sum是变量名,()里的值为参数表,第一行为函数头,{}里的为函数体。函数在使用时必须带上括号,有必要的话还要传递参数,函数的执行结果也可以赋值给其它变量。C语言不允许函数嵌套定义;也就是说,不能在一个函数中定义另外一个函数,必须在所有函数之外定义另外一个函数。main() 也是一个函数定义,也不能在 main() 函数内部定义新函数。
参数
  • 形参(形式参数):在函数定义中出现的参数可以看做是一个占位符,它没有数据,只能等到函数被调用时接收传递进来的数据,所以称为形式参数,简称形参。
  • 实参(实际参数):函数被调用时给出的参数包含了实实在在的数据,会被函数内部的代码使用,所以称为实际参数,简称实参。
形参和实参的区别和联系
  • 形参变量只有在函数被调用时才会分配内存,调用结束后,立刻释放内存,所以形参变量只有在函数内部有效,不能在函数外部使用。
  • 实参可以是常量、变量、表达式、函数等,无论实参是何种类型的数据,在进行函数调用时,它们都必须有确定的值,以便把这些值传送给形参,所以应该提前用赋值、输入等办法使实参获得确定值。
  • 实参和形参在数量上、类型上、顺序上必须严格一致,否则会发生“类型不匹配”的错误。当然,如果能够进行自动类型转换,或者进行了强制类型转换,那么实参类型也可以不同于形参类型。
  • 函数调用中发生的数据传递是单向的,只能把实参的值传递给形参,而不能把形参的值反向地传递给实参;换句话说,一旦完成数据的传递,实参和形参就再也没有瓜葛了,所以,在函数调用过程中,形参的值发生改变并不会影响实参。(传值调用
  • ***此外,还有引用调用(需要用到指针的知识):通过指针传递方式,形参为指向实参地址的指针,当***对形参的指向操作时,就相当于对实参本身进行的操作。
  • 形参和实参虽然可以同名,但它们之间是相互独立的,互不影响,因为实参在函数外部有效,而形参在函数内部有效。
       形式参数,被当作该函数内的局部变量,如果与全局变量同名它们会优先使用,只能在函数内部使用。       当局部变量被定义时,系统不会对其初始化,您必须自行对其初始化。定义全局变量时,系统会自动对其初始化
函数返回值
函数的返回值是指函数被调用之后,执行函数体中的代码所得到的结果,这个结果通过 return 语句返回。说明:
  • 没有返回值的函数为空类型,用void表示。 一旦函数的返回值类型被定义为 void,就不能再接收它的值。
  • return 语句可以有多个,可以出现在函数体的任意位置,但是每次调用函数只能有一个 return 语句被执行,所以只有一个返回值。
  • 函数遇到 return 语句就立即返回,后面的所有语句都不会被执行。因此,return 语句可以强制结束函数执行。
  • return 语句是提前结束函数的唯一办法。return 后面可以跟一份数据,表示将这份数据返回到函数外面;也可以不跟任何数据,表示什么也不返回,仅仅用来结束函数。

函数调用
函数调用(Function Call),即使用已经定义好的函数。函数不能嵌套定义,但可以嵌套调用,也就是在一个函数的定义或调用过程中允许出现对另外一个函数的调用。

       如果一个函数 A() 在定义或调用过程中出现了对另外一个函数 B() 的调用,那么我们就称 A() 为主调函数或主函数,称 B() 为被调函数。当主调函数遇到被调函数时,主调函数会暂停,CPU 转而执行被调函数的代码;被调函数执行完毕后再返回主调函数,主调函数根据刚才的状态继续往下执行。

       一个C语言程序的执行过程可以认为是多个函数之间的相互调用过程,它们形成了一个或简单或复杂的调用链条。这个链条的起点是 main(),终点也是 main()。当 main() 调用完了所有的函数,它会返回一个值(例如return 0;),从而结束整个程序。

       函数是一个可以重复使用的代码块,CPU 会一条一条地挨着执行其中的代码,当遇到函数调用时,CPU 首先要记录下当前代码块中下一条代码的地址(假设地址为 0X1000),然后跳转到另外一个代码块,执行完毕后再回来继续执行 0X1000 处的代码。因此,在所有函数之外进行加减乘除运算、使用 if...else 语句、调用一个函数等都是没有意义的,这些代码位于整个函数调用链条之外,永远都不会被执行到。C语言禁止出现这种情况。

函数声明及函数原型
C语言代码由上到下依次执行,原则上函数定义要出现在函数调用之前,否则就会报错。但在实际开发中,经常会在函数定义之前使用它们,这个时候就需要提前声明。声明(Declaration),就是告诉编译器我要使用这个函数,你现在没有找到它的定义不要紧,请不要报错,稍后我会把定义补上。 格式:1.去掉函数定义中的函数体,并在最后加上分号;,返回类型  函数名( 数据类型1 数据1, 数据类型2 数据2... );    2.也可以不写形参,只写数据类型:返回类型  函数名( 数据类型1, 数据类型2 ... );  

函数声明给出了函数名、返回值类型、参数列表(重点是参数类型)等与该函数有关的信息,称为函数原型(Function Prototype)。函数原型的作用是告诉编译器与该函数有关的信息,让编译器知道函数的存在,以及存在的形式,即使函数暂时没有定义,编译器也知道如何使用它。

有了函数声明,函数定义就可以出现在任何地方了,甚至是其他文件、静态链接库、动态链接库等。

作用域规则
作用域:变量的有效范围,是程序中定义的变量所存在的区域和在哪个范围以内使用,超过该区域变量就不能被访问。

每个C语言程序都包含了多个作用域,不同的作用域中可以出现同名的变量,C语言会按照从小到大的顺序、一层一层地去父级作用域中查找变量,如果在最顶层的全局作用域中还未找到这个变量,那么就会报错。
    规则:任何一种编程中,作用域是程序中定义的变量所存在的区域,超过该区域变量就不能被访问。
  • C 语言中有三个地方可以声明变量:
  • 在函数或块内部的局部变量
  • 在所有函数外部的全局变量
  • 在形式参数的函数参数定义中
  • 每一段可运行的C语言代码都包含了多个作用域。(至少一个代码块)
[C] 纯文本查看 复制代码
int main(){
    return 0;
}
此代码包含两个作用域,一个是 main() 函数内部的局部作用域,一个是 main() 函数外部的全局作用域。

       C语言规定,在同一个作用域中不能出现两个名字相同的变量,否则会产生命名冲突;但是在不同的作用域中,允许出现名字相同的变量,它们的作用范围不同,彼此之间不会产生冲突。这句话有两层含义:

* 不同函数内部可以出现同名的变量,不同函数是不同的局部作用域;

* 函数内部和外部可以出现同名的变量,函数内部是局部作用域,函数外部是全局作用域。
  • 局部变量(形式参数):在某个函数或块的内部声明的变量称为局部变量。它们只能被该函数或该代码块内部的语句使用。局部变量在函数外部是无效的。
    • C语言允许在代码块内部定义变量,这样的变量具有块级作用域;换句话说,在代码块内部定义的变量只能在代码块内部使用,出了代码块就无效了。

说明:

1) 在 main 函数中定义的变量也是局部变量,只能在 main 函数中使用;同时,main 函数中也不能使用其它函数中定义的变量。main 函数也是一个函数,与其它函数地位平等。

2) 形参变量、在函数体内定义的变量都是局部变量。实参给形参传值的过程也就是给局部变量赋值的过程。

3) 可以在不同的函数中使用相同的变量名,它们表示不同的数据,分配不同的内存,互不干扰,也不会发生混淆。

4) 在语句块中也可定义变量,它的作用域只限于当前语句块。
  • 全局变量:全局变量在所有函数外部定义,通常是在程序的顶部。全局变量在整个程序生命周期内都是有效的,在任意的函数内部能访问全局变量。全局变量可以被任何函数访问。也就是说,全局变量在声明后整个程序中都是可用的。它的作用域默认是整个程序,也就是所有的源文件,包括 .c 和 .h 文件。
在程序中,局部变量和全局变量的名称可以相同,但是在函数内,如果两个名字相同,会使用局部变量值,全局变量不会被使用。
  • 初始化局部变量和全局变量:当局部变量被定义时,系统不会对其初始化。定义全局变量时,系统会自动对其初始化。
如:int  --->  0  ;   char  --->  '\0'  ;   float  --->  0  ;   double  --->  0  ;   pointer  --->  null

正确地初始化变量是一个良好的编程习惯,否则有时候程序可能会产生意想不到的结果,因为未初始化的变量会导致一些在内存位置中已经可用的垃圾值。

递归函数(递归调用)
递归调用:一个函数在它的函数体内调用它自身称为递归调用,这种函数称为递归函数。eg:求n的阶乘:
[C] 纯文本查看 复制代码
#include <stdio.h>
//定义求n的阶乘的函数
long factorial(int n) {//返回值类型为long,函数名为factorial,参数n
    if (n == 0 || n == 1) {//||  或符号
        return 1;
    }
    else {
        return factorial(n - 1) * n;  // 递归调用
    }
}
int main() {
    int a;
    printf("输入数据: ");
    scanf("%d", &a);
    printf("Factorial(%d) = %ld\n", a, factorial(a));
    return 0;
}
结果能输入的最大数据为16,再大就会数据溢出
C语言输入输出
输入输出(Input and Output, IO)
printf()
在C语言中,有三个函数可以用来在显示器上输出数据:
  • puts():只能输出字符串,并且输出结束后会自动换行。
  • putchar():只能输出单个字符。
  • printf():可以输出各种类型的数据。
格式控制符
说明
%c
输出一个单一的字符
%hd、%d、%ld
以十进制、有符号的形式输出 short、int、long 类型的整数
%hu、%u、%lu
以十进制、无符号的形式输出 short、int、long 类型的整数
%ho、%o、%lo
以八进制、不带前缀、无符号的形式输出 short、int、long 类型的整数
%#ho、%#o、%#lo
以八进制、带前缀、无符号的形式输出 short、int、long 类型的整数
%hx、%x、%lx%hX、%X、%lX
以十六进制、不带前缀、无符号的形式输出 short、int、long 类型的整数。如果 x 小写,那么输出的十六进制数字也小写;如果 X 大写,那么输出的十六进制数字也大写。
%#hx、%#x、%#lx%#hX、%#X、%#lX
以十六进制、带前缀、无符号的形式输出 short、int、long 类型的整数。如果 x 小写,那么输出的十六进制数字和前缀都小写;如果 X 大写,那么输出的十六进制数字和前缀都大写。
%f、%lf
以十进制的形式输出 float、double 类型的小数
%e、%le%E、%lE
以指数的形式输出 float、double 类型的小数。如果 e 小写,那么输出结果中的 e 也小写;如果 E 大写,那么输出结果中的 E 也大写。
%g、%lg%G、%lG
以十进制和指数中较短的形式输出 float、double 类型的小数,并且小数部分的最后不会添加多余的 0。如果 g 小写,那么当以指数形式输出时 e 也小写;如果 G 大写,那么当以指数形式输出时 E 也大写。
%s
输出一个字符串


printf() 的高级用法
eg:输出一个 4×4 的整数矩阵,数字要对齐。
[C] 纯文本查看 复制代码
#include <stdio.h>
int main()
{
    int a1=20, a2=345, a3=700, a4=22;
    int b1=56720, b2=9999, b3=20098, b4=2;
    int c1=233, c2=205, c3=1, c4=6666;
    int d1=34, d2=0, d3=23, d4=23006783;
    printf("%-9d %-9d %-9d %-9d\n", a1, a2, a3, a4);
    printf("%-9d %-9d %-9d %-9d\n", b1, b2, b3, b4);
    printf("%-9d %-9d %-9d %-9d\n", c1, c2, c3, c4);
    printf("%-9d %-9d %-9d %-9d\n", d1, d2, d3, d4);
    return 0;
}
结果:其中:%-9d中,d表示以十进制输出,9表示最少占9个字符的宽度,宽度不足以空格补齐,-表示左对齐。  printf() 格式控制符的完整形式如下:%[flag][width][.precision]type

[ ] 表示此处的内容可以省略。
  • type 表示输出类型,比如 %d、%f、%c、%lf,type 就分别对应 d、f、c、lf;type 这一项必须有,这意味着输出时必须要知道是什么类型。
  • width 表示最小输出宽度,也就是至少占用几个字符的位置。当输出结果的宽度不足 width 时,以空格补齐(如果没有指定对齐方式,默认会在左边补齐空格);当输出结果的宽度超过 width 时,width 不再起作用,按照数据本身的宽度来输出。
  • .precision 表示输出精度,也就是小数的位数。
  • 当小数部分的位数大于 precision 时,会按照四舍五入的原则丢掉多余的数字;
  • 当小数部分的位数小于 precision 时,会在后面补 0。
  • 另外,.precision 也可以用于整数和字符串,但是功能却是相反的:
    • 用于整数时,.precision 表示最小输出宽度。与 width 不同的是,整数的宽度不足时会在左边补 0,而不是补空格。
    • 用于字符串时,.precision 表示最大输出宽度,或者说截取字符串。当字符串的长度大于 precision 时,会截掉多余的字符;当字符串的长度小于 precision 时,.precision 就不再起作用。
  • flag 是标志字符。例如%-9d中 flags 对应-。
  
标志字符
含  义
-
-表示左对齐。如果没有,就按照默认的对齐方式,默认一般为右对齐。
+
用于整数或者小数,表示输出符号(正负号)。如果没有,那么只有负数才会输出符号。
空格
用于整数或者小数,输出值为正时冠以空格,为负时冠以负号。
#
  • 对于八进制(%o)和十六进制(%x / %X)整数,# 表示在输出时添加前缀;八进制的前缀是 0,十六进制的前缀是 0x / 0X。
  • 对于小数(%f / %e / %g),# 表示强迫输出小数点。如果没有小数部分,默认是不输出小数点的,加上 # 以后,即使没有小数部分也会带上小数点。

printf() 不能立即输出的问题
eg:
[C] 纯文本查看 复制代码
#include<stdio.h>
#include<unistd.h>
int main()
{
    printf("请看下面文字:\n");
    sleep(5);  //程序暂停5秒钟
    printf("C语言好难啊(哭.jpg)\n");
    return 0;
}
#录制gif软件:GifCam.exe ***问题:这是教程原话:

***但我在devc++上运行时反而sleep()可以运行而Sleep()不能运行   
scanf()
scanf() 是最灵活、最复杂、最常用的输入函数,但它不能完全取代其他函数
  • scanf(): 可以输入多种类型的数据。
  • getchar()、getche()、getch():用于输入单个字符。
  • gets():获取一行数据,并作为字符串处理。
  • scanf() 格式控制符汇总
格式控制符
说明
%c
读取一个单一的字符
%hd、%d、%ld
读取一个十进制整数,并分别赋值给 short、int、long 类型
%ho、%o、%lo
读取一个八进制整数(可带前缀也可不带),并分别赋值给 short、int、long 类型
%hx、%x、%lx
读取一个十六进制整数(可带前缀也可不带),并分别赋值给 short、int、long 类型
%hu、%u、%lu
读取一个无符号整数,并分别赋值给 unsigned short、unsigned int、unsigned long 类型
%f、%lf
读取一个十进制形式的小数,并分别赋值给 float、double 类型
%e、%le
读取一个指数形式的小数,并分别赋值给 float、double 类型
%g、%lg
既可以读取一个十进制形式的小数,也可以读取一个指数形式的小数,并分别赋值给 float、double 类型
%s
读取一个字符串(以空白符为结束)
字符串的两种定义形式:char str1[] = "字符串1";char *str2 = "字符串2";

       第一种形式的字符串所在的内存既有读取权限又有写入权限,第二种形式的字符串所在的内存只有读取权限,没有写入权限。printf()、puts() 等字符串输出函数只要求字符串有读取权限,而 scanf()、gets() 等字符串输入函数要求字符串有写入权限,所以,第一种形式的字符串既可以用于输出函数又可以用于输入函数,而第二种形式的字符串只能用于输出函数。
对于第一种形式的字符串,在[ ]里面要指明字符串的最大长度,如果不指明,也可以根据=后面的字符串来自动推算,但是只定义了一个字符串,没有立即给它赋值的时候无法自动推算,只能手动指明最大长度因此一定要写作char url[30]([ ] 里面为字符串长度),不能写作char url[]。对于字符串,不需要加 &,这是因为字符串的名字会自动转换为字符串的地址。   
  • getchar()为scanf("%c", c)的简化版 ,
  • char c;
  •     c = getchar();
可以简化成           char c = getchar();
  • getche()  没有缓冲区,输入一个字符后会立即读取,不用按下回车键。
  • getch()    也没有缓冲区,输入一个字符后会立即读取,不用按下回车键,但是它没有回显,看不到输入的字符。
注意:  getche()  与  getch()  位于 conio.h 头文件中,而这个头文件是 Windows 特有的,Linux 和 Mac OS 下没有包含该头文件。换句话说,getche() 并不是标准函数,默认只能在 Windows 下使用,不能在 Linux 和 Mac OS 下使用。
  • gets() ——专用的字符串输入函数,有缓冲区,能读取含有空格的字符串。
与 scanf() 的主要区别:
  • scanf() 读取字符串时以空格为分隔,遇到空格就认为当前字符串结束了,所以无法读取含有空格的字符串。
  • gets() 认为空格也是字符串的一部分,只有遇到回车键时才认为字符串输入结束,所以,不管输入了多少个空格,只要不按下回车键,对 gets() 来说就是一个完整的字符串。

C数组
C语言数组属于构造数据类型。它可以存储一个固定大小的相同类型元素的顺序集合。数组是用来存储一系列数据,但它往往被认为是一系列相同类型的变量。一个数组可以分解为多个数组元素,这些数组元素可以是基本数据类型或是构造类型。因此按数组元素的类型不同,数组又可分为数值数组、字符数组、指针数组、结构数组等各种类别。              所有的数组都是由连续的内存位置组成。最低的地址对应第一个元素,最高的地址对应最后一个元素。数组中的特定元素可以通过索引访问,第一个索引值为 0。eg:输出一个 4×4 的整数矩阵:
[C] 纯文本查看 复制代码
#include <stdio.h>
#include <stdlib.h>
int main()
{
    int a1=20, a2=345, a3=700, a4=22;
    int b1=56720, b2=9999, b3=20098, b4=2;
    int c1=233, c2=205, c3=1, c4=6666;
    int d1=34, d2=0, d3=23, d4=23006783;
    printf("%-9d %-9d %-9d %-9d\n", a1, a2, a3, a4);
    printf("%-9d %-9d %-9d %-9d\n", b1, b2, b3, b4);
    printf("%-9d %-9d %-9d %-9d\n", c1, c2, c3, c4);
    printf("%-9d %-9d %-9d %-9d\n", d1, d2, d3, d4);
    system("pause");
    return 0;
}
结果: 「数组内存是连续的」,连续的内存为指针操作(通过指针来访问数组元素)和内存处理(整块内存的复制、写入等)提供了便利,这使得数组可以作为缓存(临时存储数据的一块内存)使用。  
使用方法:
  • 声明:指定元素的类型和元素的数量
    • 一维数组:arraySize 为大于零的整数常量,type 为任意有效的 C 数据类型。
数据类型  数组名[数据容纳量];type arrayName [ arraySize ];
  • 初始化数据:可以逐个初始化数组,也可以使用一个初始化语句
数据类型 数组名[数据容纳量] = {1000.0, 2.0, 3.4, 7.0, 50.0};double balance[5] = {1000.0, 2.0, 3.4, 7.0, 50.0};//其中 { } 之间的值的数目不能大于在数组声明 [ ] 中指定的元素数目
  • 可以只给部分元素赋值。当{ }中值的个数少于元素个数时,只给前面部分元素赋值。
当赋值的元素少于数组总体元素的时候,剩余的元素自动初始化为 0:
  • 对于short、int、long,就是整数 0;
  • 对于char,就是字符 '\0';
  • 对于float、double,就是小数 0.0。
  • 只能给元素逐个赋值,不能给数组整体赋值。
  • 如给全部元素赋值,那么在定义数组时可以不给出数组长度。
所有的数组都是以 0 作为它们第一个元素的索引,也被称为基索引,也可以称为下标(index),数组的最后一个索引是数组的总大小减去 1。例如:可以用  balance[1] = {2.0}   数组中第二个元素的值赋为 2.0
  • 访问数组元素:数组元素可以通过数组名称加索引进行访问
     eg:可以定义    int shuju = balance[3];       表示把数组balance的第4个数据赋值给变量shujueg:输入10个数字并输出
[C] 纯文本查看 复制代码
#include <stdio.h>
int main(){
    int nums[10];
    int i;
   
    //从控制台读取用户输入
    for(i=0; i<10; i++){
        scanf("%d", &nums[i]);  //注意取地址符 &,
    }
   
    //依次输出数组元素
    for(i=0; i<10; i++){
        printf("%d ", nums[i]);
    }
   
    return 0;
}
注意:
  • 数组中每个元素的数据类型必须相同,对于int num[10];,每个元素都必须为 int。
  • 数组长度 length 最好是整数或者常量表达式,如 10、20*4 等,这样在所有编译器下都能运行通过;如果 length 中包含了变量,如 n、4*m 等,在某些编译器下就会报错。
  • 访问数组元素时,下标的取值范围为 0 ≤ index < length,过大或过小都会越界,导致数组溢出,发生不可预测的情况。

多维数组
  • 二维数组
定义:数据类型  数组名[第一位下标长度(行)][第二维下标长度(列)];dataType arrayName[length1][length2];二维数组的各个元素是相邻,彼此之间没有缝隙,按行排列。 eg1:一个学习小组有 5 个人,每个人有 3 门课程的考试成绩,求该小组各科的平均分和总平均分。
[C] 纯文本查看 复制代码
#include <stdio.h>
int main(){
    int i, j;  //二维数组下标
    int sum = 0;  //当前科目的总成绩
    int average;  //总平均分
    int v[3];  //各科平均分
    int a[5][3];  //用来保存每个同学各科成绩的二维数组
    printf("Input score:\n");
    for(i=0; i<3; i++){
        for(j=0; j<5; j++){
            scanf("%d", &a[j][i]);  //输入每个同学的各科成绩
            sum += a[j][i];  //计算当前科目的总成绩
        }
        v[i]=sum/5;  // 当前科目的平均分
        sum=0;
    }
    average = (v[0] + v[1] + v[2]) / 3;
    printf("Math: %d\nC Languag: %d\nEnglish: %d\n", v[0], v[1], v[2]);
    printf("Total: %d\n", average);
    return 0;
}
对于该题目,可以定义一个二维数组 a[5][3] 存放 5 个人 3 门课的成绩,定义一个一维数组 v[3] 存放各科平均分,再定义一个变量 average 存放总平均分。结果:
  • 二维数组的初始化(赋值):可以按行分段赋值,也可按行连续赋值
对于数组 a[5][3],按行分段赋值应该写作:int a[5][3]={ {80,75,92}, {61,65,71}, {59,63,70}, {85,87,90}, {76,77,85} };按行连续赋值应该写作:int a[5][3]={80, 75, 92, 61, 65, 71, 59, 63, 70, 85, 87, 90, 76, 77, 85};这两种赋初值的结果是完全相同的。 对eg1初始化时应写作:
[C] 纯文本查看 复制代码
#include <stdio.h>
int main(){
    int i, j;  //二维数组下标
    int sum = 0;  //当前科目的总成绩
    int average;  //总平均分
    int v[3];  //各科平均分
    int a[5][3] = {{80,75,92}, {61,65,71}, {59,63,70}, {85,87,90}, {76,77,85}};
    for(i=0; i<3; i++){
        for(j=0; j<5; j++){
            sum += a[j][i];  //计算当前科目的总成绩
        }
        v[i] = sum / 5;  // 当前科目的平均分
        sum = 0;
    }
    average = (v[0] + v[1] + v[2]) / 3;
    printf("Math: %d\nC Languag: %d\nEnglish: %d\n", v[0], v[1], v[2]);
    printf("Total: %d\n", average);
    return 0;
}
注意:
  • 可以只对部分元素赋值,未赋值的元素自动取  0  值。
  • 对全部元素赋值时,第一维的长度可以不给出。
  • 二维数组可以看作是由一维数组嵌套而成的:一个数组的每个元素类型相同且又是一个数组时,这个数组就是二维数组。一个二维数组也可以分解为多个一维数组。
  
判断数组中是否包含某个元素
C语言标准库没有提供与数组查询相关的函数,所以只能自己编写代码。
  • 对无序数组的查询
无序数组,就是数组元素的排列没有规律。无序数组元素查询是用循环遍历数组中的每个元素,把每个要查询的值比较一遍。eg:查找数组中的值
[C] 纯文本查看 复制代码
#include <stdio.h>
int main(){
    //定义一个数组
    int nums[10] = {1, 10, 6, 296, 177, 23, 0, 100, 34, 999};
    int i, num, thisindex = -1;
   
    printf("Input an integer: ");
    scanf("%d", &num);
    for(i=0; i<10; i++){
        if(nums[i] == num){//遍历审查数组中的每个元素,如果相等就获取它的下标并跳出循环。
            thisindex = i;
            break;
        }
    }
    if(thisindex < 0){
        printf("%d isn't  in the array.\n", num);
    }else{
        printf("%d is  in the array, it's index is %d.\n", num, thisindex);
    }
    return 0;
}
注意:数组下标的取值范围是非负数,当 thisindex >= 0 时,该数字在数组中,当 thisindex < 0 时,该数字不在数组中,所以在定义 thisindex 变量时,必须将其初始化为一个负数。
  • 对有序数组的查询
只需遍历其中一部分数据(比如从小到大的顺序)即可。eg:
[C] 纯文本查看 复制代码
#include <stdio.h>
int main(){
    int nums[10] = {0, 1, 6, 10, 23, 34, 100, 177, 296, 999};
    int i, num, thisindex = -1;
   
    printf("Input an integer: ");
    scanf("%d", &num);
    for(i=0; i<10; i++){
        if(nums[i] == num){
            thisindex = i;
            break;
        }else if(nums[i] > num){
            break;
        }
    /*因为这是一个递增数组,因此是nums[i] > num,若是递减数组,改成<即可*/
    }
    if(thisindex < 0){
        printf("%d isn't  in the array.\n", num);
    }else{
        printf("%d is  in the array, it's index is %d.\n", num, thisindex);
    }
   
    return 0;
}
  

免费评分

参与人数 3吾爱币 +3 热心值 +3 收起 理由
wxz520wxz + 1 + 1 谢谢@Thanks!
lyl610abc + 1 + 1 我很赞同!
layuai + 1 + 1 用心讨论,共获提升!

查看全部评分

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

我是东软的学生 发表于 2021-3-6 14:54
学习了。
layuai 发表于 2021-3-6 14:55
知识非常适合基础的看看,还可以顺便巩固一下
lyl610abc 发表于 2021-3-6 15:04
wxbb979 发表于 2021-3-6 15:43
前来学习~C语言
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

返回列表

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-11-25 19:23

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表