学术诚信声明:本文所涉及的代码实现、编译调试分析及实验结论均为本人独立完成,未抄袭、剽窃他人学术成果,所有参考资料已在文末标注,恪守学术诚信原则,对本文内容的真实性与原创性负责。
摘要:本次课程实践围绕78 号选题分糖果的 C 语言古代码修复展开,是 C 语言课程的核心实践任务之一。实践过程中,首先针对原始代码中void main()、clrscr()等与现代 C99/C11 标准不兼容的语法问题,完成编译错误分析与代码修正;随后通过 Dev-C++ 和 VSCode 双编译器完成代码调试与运行测试,深入解析了分糖果程序的数组操作、循环迭代核心逻辑;最后借助 Gitee+Git 实现代码版本管理,并完成技术报告的撰写。通过本次实践,不仅掌握了老旧 C 语言代码向现代标准迁移的方法,还熟悉了 VSCode 开发环境配置与代码托管平台的使用,提升了 C 语言编程能力与项目工程化管理思维。
1. 选题与准备
1.1 选题理由
本次课程实践选定10 个孩子分糖果的 C 语言经典实例(78 号选题),具体选题考量如下:
- 该代码综合运用 C 语言数组操作、循环结构、自定义函数调用三大核心基础语法,是入门阶段语法实践的典型载体,能有效检验基础语法的掌握程度;
- 原始代码包含
void main()、clrscr()等 Turbo C 老旧语法元素,与现代 C 语言标准(C99/C11)存在明显兼容性差异,适合开展 “传统代码向现代标准迁移修复” 的课程任务; - 分糖果的循环分配逻辑结合生活化场景,易于理解且能直观展现 “条件判断 - 循环迭代 - 结果收敛” 的编程逻辑,降低了语法与业务逻辑结合的学习难度。
1.2 环境准备
- 操作系统:Windows 11 专业版
- 编译工具:Dev-C++ 5.11(主要编译环境)、VSCode + MinGW-w64(gcc 8.1.0,用于跨编辑器调试)
- 辅助工具:CSDN 技术社区(检索老旧函数替代方案)、AI 编程工具(辅助分析语法错误成因)、Gitee 代码托管平台(实现代码版本管理)
2. 编译调试过程
修改前代码:
#include<stdio.h>
void print(int s[]);
int judge(int c[]);
int j=0;
void main()
{
static int sweet[10]={10,2,8,22,16,4,10,6,14,20};
int i,t[10],l;
clrscr();
printf(" Child No. 1 2 3 4 5 6 7 8 9 10\n");
printf("------------------------------------------------------\n");
printf(" Round No.|\n");
print(sweet);
while(judge(sweet))
{
for(i=0;i<10;i++)
if(sweet[i]%2==0)
t[i]=sweet[i]=sweet[i]/2;
else
t[i]=sweet[i]=(sweet[i]+1)/2;
for(l=0;l<9;l++)
sweet[l+1]=sweet[l+1]+t[l];
sweet[0]+=t[9];
print(sweet);
}
printf("------------------------------------------------------\n");
printf("\n Press any key to quit...");
getch();
}
int judge(int c[])
{
int i;
for(i=0;i<10;i++)
if(c[0]!=c[i]) return 1;
return 0;
}
void print(int s[])
{
int k;
printf(" <%2d> | ",j++);
for(k=0;k<10;k++) printf("%4d",s[k]);
printf("\n");
}
2.1 初始编译与错误分析

通过 Dev-C++ 编译原始代码,共触发3 个致命编译错误,错误信息及深层成因分析如下表所示:
| 错误行号 | 错误提示内容 | 错误类型 | 成因解析 |
| 5行11列 | ::main' must return'int' | 语法规范错误 | C99/C11国际标准对C语言主函数的返回值类型做了强制规定,要求main函数必须以int类型声明,原始代码的void main()写法违反该标准。 |
| 9行12列 | 'clrscr' was not declared in this scope | 函数未定义错误 | clrscr()是早期Turbo C编译器的专属清屏函数,现代主流编译器(Dev-C++/gcc)已逐步弃用该函数,未保留其声明与实现。 |
| 28行11列 | 'getch' was not declared in this scope | 函数未定义错误 | getch()函数的声明被包含在<conio.h>头文件中,原始代码未引入该头文件,导致编译器无法识别该函数。 |
2.2 错误修正
针对上述编译错误,采用标准语法替换 + 头文件补充的策略逐一解决,具体修正方案如下:
| 典型错误 | 修正方法 | 修正依据 |
| void main()语法问题 | 将主函数声明改为int main(),并在函数末尾添加return 0;语句 | 遵循C99/C11标准对主函数返回值的强制要求,保证程序退出状态的规范性。 |
| clrscr()清屏函数失效 | 使用system("cls")替代,并引用<stdlib.h>头文件 | system("cls")是Windows系统下的通用清屏命令,<stdlib.h>头文件包含该函数的声明,适配现代编译器 |
| getch()函数未定义 | 在代码开头引入<conio.h>头文件 | <conio.h>头文件中包含getch()函数的原型声明,可解决编译器的识别问题 |
2.3 反复调式

- 首次调试:添加
<stdlib.h>头文件后,system("cls")仍出现编译错误,经排查是 Dev-C++ 未开启对 C11 标准的支持,勾选编译器设置中的 “支持 C11 标准” 选项后,该错误消除; - 二次调试:在 VSCode 中编译时,
getch()函数偶发 “标识符未定义” 错误,更换 MinGW-w64 的 32 位版本编译器后,该问题得到解决; - 最终结果:修正后的代码在 Dev-C++ 和 VSCode 中均实现零错误、零警告编译,运行时能按预期输出分糖果的轮次过程及最终结果。
3.代码理解与重命名
3.1 运行测试
修改后完整代码:
#include<stdio.h>
#include<conio.h>
#include<stdlib.h>
void print(int s[]);
int judge(int c[]);
int j=0;
int main()
{
static int sweet[10]={10,2,8,22,16,4,10,6,14,20};
int i,t[10],l;
system("cls");
printf(" Child No. 1 2 3 4 5 6 7 8 9 10\n");
printf("------------------------------------------------------\n");
printf(" Round No.|\n");
print(sweet);
while(judge(sweet))
{
for(i=0;i<10;i++)
if(sweet[i]%2==0)
t[i]=sweet[i]=sweet[i]/2;
else
t[i]=sweet[i]=(sweet[i]+1)/2;
for(l=0;l<9;l++)
sweet[l+1]=sweet[l+1]+t[l];
sweet[0]+=t[9];
print(sweet);
}
printf("------------------------------------------------------\n");
printf("\n Press any key to quit...");
getch();
return 0;
}
int judge(int c[])
{
int i;
for(i=0;i<10;i++)
if(c[0]!=c[i]) return 1;
return 0;
}
void print(int s[])
{
int k;
printf(" <%2d> | ",j++);
for(k=0;k<10;k++)
printf("%4d",s[k]);
printf("\n");
}
运行结果展示:

编译并运行修正后的代码,程序执行流程如下:
- 控制台首先执行清屏操作,随后输出孩子编号表头与轮次标题栏;
- 打印初始状态下 10 个孩子的糖果数量,接着进入循环分配逻辑;
- 每一轮分配完成后,实时打印当前轮次及各孩子的糖果数,直至所有孩子的糖果数相等;
- 循环结束后输出分隔线与退出提示,等待用户按键后程序终止。
程序核心功能为:通过奇偶判断拆分糖果、循环传递半数糖果的逻辑,使 10 个孩子的糖果数量逐步收敛至相同值。
3.2 代码解析
该代码采用模块化编程思想,将功能拆分为三大核心模块:
- 主函数
main():作为程序入口,完成糖果数组的初始化、清屏、表头打印、循环分配逻辑的执行与终止判断,是程序的核心控制模块; - 判断函数
judge():接收糖果数组参数,遍历数组判断所有元素是否相等,返回 1 表示未达标、0 表示达标,为循环终止提供判断依据; - 打印函数
print():按指定格式输出当前轮次与各孩子的糖果数,实现程序运行过程的可视化展示。
代码核心逻辑流程图:

3.3 重命名
依据课程选题编号与功能特性,将原代码文件重命名为 **78 candy.c**,其中 “78” 为选题编号,“candy” 直观体现程序围绕分糖果逻辑开发的核心功能。
4.使用VS Code管理项目
4.1 VSCode 环境配置
1.安装 VSCode 后,在扩展商店下载并安装Microsoft 官方 C/C++ 插件,为 C 语言开发提供语法高亮、智能提示等功能;
2.配置 MinGW-w64 编译器路径,在 VSCode 的settings.json配置文件中添加如下内容:
| { "C_Cpp.default.compilerPath": "D:\\MinGW\\bin\\gcc.exe", "C_Cpp.default.intelliSenseMode": "gcc-x64" } |
3.通过 “任务:配置任务” 功能创建tasks.json文件,配置编译指令,实现代码的一键编译运行.
4.2 在VS Code中编译运行

- 将重命名后的
78 candy.c文件放入 VSCode 的项目文件夹中; - 按下
Ctrl+Shift+B快捷键执行编译任务,编译器自动生成对应的可执行文件; - 在 VSCode 终端中输入
./78 candy.exe指令,或点击终端的 “运行” 按钮,即可查看程序的运行结果。
5.代码版本管理
5.1 Gitee 仓库创建
- 登录 Gitee 平台,点击 “新建仓库” 按钮,填写仓库名称为C
-Candy-Distribution; - 仓库类型选择 “开源”,仓库描述填写 “C 语言 78 号选题分糖果问题古代码修复项目”;
- 勾选 “使用 Readme 文件初始化仓库” 选项,选择
.gitignore模板为 “C”,最后点击 “创建” 按钮完成仓库搭建。
5.2 VSCode 集成 Git
1.打开 VSCode 终端,执行 Git 全局配置指令,配置用户名与邮箱(与 Gitee 账号一致):
| git config --global user.name "S99tar" git config --global user.email "[email protected]" |
2.在项目文件夹下初始化本地 Git 仓库,并关联远程 Gitee 仓库:
git init git remote add origin https://gitee.com/S99tar/C-Candy-Distribution |
3.将代码文件添加至暂存区,完成本地提交后推送到远程 Gitee 仓库:
| git add . git commit -m "完成78号分糖果代码修复与功能测试" git push -u origin master |
5.2 结果分析
初始糖果数经过17轮分配后,所有小孩的糖果数收敛为 18 颗,验证了算法逻辑的正确性。程序按指定格式逐轮输出糖果数,getch()函数实现了 “按键退出” 的交互效果,整体功能符合实验要求。
6.总结
本次课程实践以 78 号选题分糖果的古 C 语言代码修复为核心,深入探究了传统 Turbo C 语法与现代 C 语言标准的兼容性差异,掌握了system("cls")、getch()等老旧函数的替代方案,以及 Dev-C++、VSCode 双编译器的环境配置技巧。同时,借助 Gitee+Git 工具实现了代码的版本管理,完整体验了 “本地开发 - 远程托管” 的项目工程化流程。
在代码修复过程中,深刻认识到 C 语言作为静态编译型语言,编译器环境配置、头文件依赖管理是程序正常运行的关键,而语法标准的迭代更新也要求开发者持续学习新的规范。后续将进一步深入学习 C 语言的指针、结构体等高级特性,结合更多实际场景提升编程与项目管理能力。
附录
- 代码地址:https://gitee.com/S99tars/c-candy-distribution/blob/master/78candy.c
https://gitee.com/S99tars/c-candy-distribution/blob/master/78candy.c - 参考资料:
- ISO/IEC 9899:1999(C99)标准文档
- CSDN 技术博客:《Turbo C 老旧函数在现代编译器中的替代方法》
- 苏小红,张彦航,赵玲玲,李东 《C 程序设计》(第五版). 高等教育出版社,202X。
转载自CSDN-专业IT技术社区
原文链接:https://blog.csdn.net/Y200599/article/details/156658801



