C 语言编程教程

C 语言 - 首页

C 语言基础

C 语言 - 概述 C 语言 - 特性 C 语言 - 发展历史 C 语言 - 环境设置 C 语言 - 程序结构 C 语言 - Hello World C - 编译过程 C - 注释 C - 标记 C - 关键字 C - 标识符 C - 用户输入 C - 基本语法 C - 数据类型 C - 变量 C - 整数提升 C - 类型转换 C - 类型转换 C - 布尔值

C 语言中的常量和文字

C - 常量 C - 字面量 C - 转义序列 C - 格式说明符

C 语言中的运算符

C - 运算符 C - 算术运算符 C - 关系运算符 C - 逻辑运算符 C - 位运算符 C - 赋值运算符 C - 一元运算符 C - 递增和递减运算符 C - 三元运算符 C - sizeof 运算符 C - 运算符优先级 C - 其他运算符

C 语言中的决策

C - 决策 C - if 语句 C - if...else 语句 C - 嵌套 if 语句 C - switch 语句 C - 嵌套 switch 语句

C 语言中的循环

C - 循环 C - While 循环 C - For 循环 C - Do...while 循环 C - 嵌套循环 C - 无限循环 C - Break 语句 C - Continue 语句 C - goto 语句

C 语言中的函数

C - 函数 C - Main 函数 C - 按值调用函数 C - 按引用调用函数 C - 嵌套函数 C - 可变参数函数 C - 用户定义函数 C - 回调函数 C - return 语句 C - 递归

C 语言中的作用域规则

C - 作用域规则 C - 静态变量 C - 全局变量

C 语言中的数组

C - 数组 C - 数组的属性 C - 多维数组 C - 将数组传递给函数 C - 从函数返回数组 C - 可变长度数组

C 语言中的指针

C - 指针 C - 指针和数组 C - 指针的应用 C - 指针运算 C - 指针数组 C - 指向指针的指针 C - 将指针传递给函数 C - 从函数返回指针 C - 函数指针 C - 指向数组的指针 C - 指向结构体的指针 C - 指针链 C - 指针 vs 数组 C - 字符指针和函数 C - NULL 指针 C - void 指针 C - 悬垂指针 C - 解引用指针 C - Near、Far 和 Huge 指针 C - 指针数组的初始化 C - 指针与多维数组

C 语言中的字符串

C - 字符串 C - 字符串数组 C - 特殊字符

C 语言的结构体和联合

C - 结构体 C - 结构体和函数 C - 结构体数组 C - 自引用结构 C - 查找表 C - 点 (.) 运算符 C - 枚举(或 enum) C - 结构填充和打包 C - 嵌套结构 C - 匿名结构和联合 C - 联合 C - Bit 位字段 C - Typedef

C 语言中的文件处理

C - 输入和输出 C - 文件 I/O(文件处理)

C 语言中的预处理器

C - 预处理器 C - #pragma 编译指示 C - 预处理器操作符 C - 宏 C - 头文件

C 语言中的内存管理

C - 内存管理 C - 内存地址 C - 存储类

C 其他主题

C - 错误处理 C - 可变参数 C - 命令执行 C - 数学函数 C - static 静态关键字 C - 随机数生成 C - 命令行参数

C 语言编程资源

C语言问题与解答答案 C语言快速指南 C语言速查表 C语言实用资源 C语言讨论


C 语言中的头文件

#include 预处理器指令用于将一个文件(通常称为头文件)中函数、常量和宏等的定义引入另一个 C 代码中。头文件的扩展名为".h",您可以从中引入一个或多个预定义函数、常量、宏等的前向声明。C 语言提供头文件有助于程序的模块化设计。

系统头文件

C 编译器软件捆绑了许多预编译的头文件。这些文件称为系统头文件。一个著名的例子是"stdio.h",几乎每个 C 程序都包含这个头文件。

每个系统头文件都包含许多实用函数。这些函数通常被称为库函数。例如,执行 IO 操作所需的 printf() 和 scanf() 函数就是"stdio.h"头文件中提供的库函数。

加载一个或多个头文件的预处理语句始终位于 C 代码的开头。我们从一个基本的"Hello World"程序开始学习 C 语言编程,首先要包含"stdio.h"文件。-

#include <stdio.h>

int main() {

   /* 我的第一个 C 语言程序 */
   printf("Hello, World! 
");

   return 0;
}

C 预处理指令 #include 本质上是请求编译器加载特定头文件的内容,以便程序可以使用它们。

C 或 C++ 程序中的常见做法是将所有常量、宏、系统全局变量和函数原型保存在头文件中,并在需要时包含该头文件。

C 语言中包含头文件的语法

使用 #include 指令 加载头文件。其使用方法如下:

#include <filename.h>

如果头文件位于 system/default 目录中,则将其名称放在尖括号内。

#include "filename.h"

如果头文件位于与源文件相同的目录中,则将用户定义或非标准头文件的名称放在双引号内。

#include 指令的工作原理是指示 C 预处理器 在继续处理当前源文件的其余部分之前,先扫描指定的文件作为输入。预处理器的输出包含已生成的输出、包含文件的输出以及 #include 指令后文本的输出。

C 语言中的标准头文件

典型的 C 编译器捆绑了许多预编译的头文件。每个头文件都包含一组预定义的标准库函数。"#include"预处理指令用于在程序中包含扩展名为".h"的头文件。

下表列出了 C 语言中的一些头文件 -

头文件 描述 函数/宏/变量
stdio.h 输入/输出函数 scanf()、printf()、fopen()、FILE
stdlib.h 通用函数 atoi()、atof()、malloc()
math.h 数学函数 sin()、cos()、pow()、sqrt()
string.h 字符串函数 strcpy()、strlen()、strcat()
ctype.h 字符处理函数 isalpha()、isupper()、 ispunct()
time.h 日期和时间函数 asctime()、gmtime()、mktime()
float.h 浮点类型的限制 FLT_ROUNDS、FLT_RADIX
limits.h 基本类型的大小 CHAR_BIT、CHAR_MIN、CHAR_MAX
wctype.h 用于确定宽字符数据中包含的类型的函数。 iswalpha()、iswctype()、iswupper()

示例

以下代码使用了一些头文件中的库函数 -

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>

int main() {

   char s1[20] = "53875";
   char s2[10] = "Hello";
   char s3[10] = "World";

   int res;
   res = pow(8, 4);
   printf("Using math.h, The value is : %d
", res);

   long int a = atol(s1);
   printf("Using stdlib.h, the string to long int: %d
", a);

   strcpy(s2, s3);
   printf("Using string.h, the strings s2 and s3: %s	%s
", s2, s3);

   return 0;
}

输出

运行此代码时,将产生以下输出 -

Using math.h, The value is: 4096
Using stdlib.h, the string to long int: 53875
Using string.h, the strings s2 and s3: World	World

用户定义的头文件

我们可以在 C 程序中添加一个或多个用户定义的函数(除了 main() 函数)。但是,如果代码包含大量函数定义,将它们放在一个以".c"为扩展名的源代码文件中会变得难以处理和维护。因此,类似性质的函数/宏/变量会被集中到头文件中,像包含标准头文件一样包含它们,并调用其中定义的函数。

用户定义的头文件通常与 C 源代码位于同一目录中。

使用 CodeBlocks IDE 创建和使用头文件的步骤如下所述。启动 CodeBlocks IDE 并创建一个新的控制台应用程序 -

Header Files

为项目选择一个合适的名称。在文件夹中添加一个新的空文件,并将以下代码保存为 "myheader.h" -

#ifndef MYHEADER_H
#define MYHEADER_H

void sayHello();
int add(int a, int b);
double area(double radius);
int length(char *x);

#endif

如果一个头文件被包含两次,编译器将对其内容进行两次处理,从而导致错误。防止这种情况的标准方法是将文件的全部实际内容用 #ifndef 指令 的条件定义括起来,这被称为 头文件保护

头文件保护会检查头文件是否已定义。如果未定义,则表示该文件是首次被包含,并且会执行保护内的代码。

头文件包含要包含的函数的前向声明或原型。这些函数的实际定义位于与头文件同名的".c"文件中。

创建头文件

将以下代码保存在"myheader.c"文件中 -

#include <stdio.h>
#include <string.h>
#include <math.h>

#define PI 3.142

void sayHello(){
   printf("Hello World
");
}

int add(int a, int b){
   int result;
   result = a+b;
   return result;
}

double area(double radius){
   double areaofcircle = PI*pow(radius, 2);
   return areaofcircle;
}

int length(char *x){
   return strlen(x);
}

使用头文件

现在我们可以在程序中包含"myheader.h"文件并调用上述任何函数。将以下代码保存为项目文件夹中的"main.c"。

#include <stdio.h>
#include "myheader.h"

int main() {

   int p = 10, q = 20;
   double x = 5.25;

   sayHello();
   printf("sum of %d and %d is %d
", p, q, add(p,q));
   printf("Radius: %lf Area: %lf", x, area(x));

   return 0;
}

构建项目并运行"main.c",可以从 CodeBlocks IDE 的运行菜单或命令行运行,以获得以下结果 -

Hello World
sum of 10 and 20 is 30
Radius: 5.250000 Area: 86.601375

计算包含

有时需要从多个不同的头文件中选择一个包含到程序中。例如,它们可能指定在不同类型的操作系统上使用的配置参数。您可以使用一系列条件语句来实现这一点,如下所示 -

#if SYSTEM_1
   # include "system_1.h"
#elif SYSTEM_2
   # include "system_2.h"
#elif SYSTEM_3
   ...
#endif

但随着文件规模的扩大,它变得繁琐乏味。为此,预处理器提供了使用宏来指定头文件名称的功能。这被称为计算包含。您无需将头文件名称作为 #include 的直接参数,只需在其中输入一个宏名称即可。-

#define SYSTEM_H "system_1.h"
...
#include SYSTEM_H

SYSTEM_H 将被扩展,预处理器将查找 system_1.h,就像 #include 最初就是这样编写的一样。SYSTEM_H 可以在 Makefile 中使用 -D 选项来定义。