“计数器”是编程中最基本、最常用的概念之一,它本质上就是一个变量,其核心功能就是记录某个事件发生的次数。

(图片来源网络,侵删)
下面我将从基础到进阶,全面地为你解析 C 语言中的计数器。
计数器的基本概念
计数器就是一个变量,通常用于循环中,以控制循环的次数,或者在程序执行过程中统计特定事件的发生频率。
核心三要素:
- 初始化: 在使用计数器之前,必须给它一个初始值,通常是
0。 - 递增/递减: 在循环的每次迭代中,改变计数器的值(通常是
+1或-1)。 - 比较/判断: 在循环的每次开始或结束时,检查计数器的值,以决定是否继续循环。
最简单的计数器示例:for 循环
这是最经典、最常见的计数器用法。for 循环的结构完美地体现了计数器的三个核心要素。

(图片来源网络,侵删)
#include <stdio.h>
int main() {
// 1. 初始化: int i = 0; (创建一个整型变量 i 并赋值为 0)
// 2. 条件判断: i < 5; (只要 i 小于 5,循环就继续)
// 3. 递增: i++ (每次循环结束后,i 的值加 1)
for (int i = 0; i < 5; i++) {
printf("当前循环次数: %d\n", i);
}
return 0;
}
输出:
当前循环次数: 0
当前循环次数: 1
当前循环次数: 2
当前循环次数: 3
当前循环次数: 4
代码解析:
int i = 0;: 这是初始化,我们创建了一个名为i的整数变量作为计数器,并从 0 开始计数。i < 5;: 这是判断条件,在每次循环开始前,程序都会检查i是否小于 5,如果条件为真,就执行循环体;如果为假,循环结束。i++: 这是递增操作。 是自增运算符,等同于i = i + 1,它在每次循环体执行完毕后执行,为下一次计数做准备。
计数器的数据类型选择
计数器不一定非要用 int 类型,选择哪种数据类型取决于你期望计数的最大值。
| 数据类型 | 大小( | 适用场景 |
|---|---|---|
unsigned char |
1 字节 (0 到 255) | 计数范围很小,如统计按键次数、状态切换等。 |
unsigned short |
2 字节 (0 到 65535) | 中等规模计数,如统计每日网站访问量。 |
unsigned int |
4 字节 (0 到 约42亿) | 最常用的通用计数器类型。 |
unsigned long long |
8 字节 (0 到 约 1.8 x 10¹⁹) | 需要极大计数的场景,如全球用户数、文件字节总数等。 |
示例:使用 unsigned short 作为计数器

(图片来源网络,侵删)
#include <stdio.h>
int main() {
unsigned short short_counter = 0;
for (short_counter = 0; short_counter < 10; short_counter++) {
printf("Short counter: %hu\n", short_counter);
}
return 0;
}
注意: 在 printf 中,%hu 是 unsigned short 的格式说明符。
其他循环中的计数器
除了 for 循环,while 和 do-while 循环也可以使用计数器,但需要手动管理计数器的三个要素。
while 循环中的计数器
#include <stdio.h>
int main() {
int i = 0; // 手动初始化
while (i < 5) { // 手动判断条件
printf("While loop count: %d\n", i);
i++; // 手动递增
}
return 0;
}
while 循环更适合在循环开始前不确定循环次数的场景,但用于计数时,其结构不如 for 循环紧凑。
do-while 循环中的计数器
do-while 的特点是先执行一次循环体,再判断条件。
#include <stdio.h>
int main() {
int j = 0;
do {
printf("Do-while loop count: %d\n", j);
j++;
} while (j < 5); // 注意这里的分号
return 0;
}
这个循环的输出和 for 循环一样,它适用于至少需要执行一次的场景,比如获取用户输入直到输入合法。
计数器的进阶应用
计数器的用途远不止控制循环次数。
A. 统计特定事件的数量
统计一个数组中有多少个偶数。
#include <stdio.h>
int main() {
int numbers[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
int count = 0; // 计数器,初始化为0
int size = sizeof(numbers) / sizeof(numbers[0]);
for (int i = 0; i < size; i++) {
if (numbers[i] % 2 == 0) { // 如果是偶数
count++; // 计数器加1
}
}
printf("数组中偶数的个数是: %d\n", count); // 输出最终结果
return 0;
}
输出:
数组中偶数的个数是: 5
B. 嵌套循环中的计数器
在嵌套循环中,通常需要两个计数器,一个用于外层循环,一个用于内层循环。
#include <stdio.h>
int main() {
// 外层循环计数器 i
for (int i = 1; i <= 3; i++) {
printf("外层循环第 %d 次\n", i);
// 内层循环计数器 j
for (int j = 1; j <= 2; j++) {
printf(" -> 内层循环第 %d 次\n", j);
}
}
return 0;
}
输出:
外层循环第 1 次
-> 内层循环第 1 次
-> 内层循环第 2 次
外层循环第 2 次
-> 内层循环第 1 次
-> 内层循环第 2 次
外层循环第 3 次
-> 内层循环第 1 次
-> 内层循环第 2 次
注意:内层循环的计数器 j 在每次进入外层循环时都会重新初始化。
最佳实践和注意事项
- 命名清晰: 使用有意义的变量名,如
student_count,loop_counter,而不是a,b,c。 - 初始化: 永远不要忘记初始化你的计数器,使用未初始化的变量(“垃圾值”)会导致不可预测的行为。
- 数据类型溢出: 如果你的计数器可能超过其数据类型的最大值,就会发生溢出,一个
unsigned char计数器在达到 255 后,再加 1 会变回 0。unsigned char c = 255; c++; // c 的值现在变成了 0,而不是 256
对于这种情况,应该选择更大的数据类型(如
unsigned int)或使用long long。 - 作用域: 在
for循环的初始化部分声明的计数器(如for(int i=0;...))其作用域仅限于该for循环内部,如果在循环外部使用i,会编译报错。
| 特性 | 描述 |
|---|---|
| 本质 | 一个用于记录次数的变量。 |
| 核心三要素 | 初始化、递增/递减、判断。 |
| 最佳循环 | for 循环是实现计数器最自然、最清晰的方式。 |
| 数据类型 | 根据预期的最大值选择合适的类型(int, unsigned int, long long 等)。 |
| 应用 | 控制循环次数、统计事件数量、数组遍历、嵌套循环等。 |
掌握计数器是学习 C 语言乃至所有编程语言的第一步,理解了它,你就掌握了程序流程控制的基础。
