github传送门:https://github.com/Chen5173/WC
项目要求
wc.exe 是一个常见的工具,它能统计文本文件的字符数、单词数和行数。这个项目要求写一个命令行程序,模仿已有wc.exe 的功能,并加以扩充,给出某程序设计语言源文件的字符数、单词数和行数。
实现一个统计程序,它能正确统计程序文件中的字符数、单词数、行数,以及还具备其他扩展功能,并能够快速地处理多个文件。
具体功能要求:
程序处理用户需求的模式为:
wc.exe [parameter] [file_name]
基本功能列表:
wc.exe -c file.c //返回文件 file.c 的字符数 (实现)
wc.exe -w file.c //返回文件 file.c 的词的数目 (实现)
wc.exe -l file.c //返回文件 file.c 的行数 (实现)
扩展功能
-s 递归处理目录下符合条件的文件。
-a 返回更复杂的数据(代码行 / 空行 / 注释行)
-s -c/-w/-l/-a *.cpp/txt/.. 返回当前文件夹里面所有符合条件的文件的相对应信息,若无第二个参数,则返回所有符合文件的文件名的路径
PSP2.1表格
PSP2.1 |
Personal Software Process Stages |
预估耗时(分钟) |
实际耗时(分钟) |
Planning |
计划 |
30 | 30 |
Estimate |
估计这个任务需要多少时间 |
20 | 20 |
Development |
开发 |
900 | 720 |
Analysis |
需求分析 (包括学习新技术) |
120 | 180 |
Design Spec |
生成设计文档 |
30 | 30 |
Design Review |
设计复审 (和同事审核设计文档) |
30 | 30 |
Coding Standard |
代码规范 (为目前的开发制定合适的规范) |
20 | 20 |
Design |
具体设计 |
100 | 90 |
Coding |
具体编码 |
200 | 300 |
Code Review |
代码复审 |
60 | 60 |
Test |
测试(自我测试,修改代码,提交修改) |
120 | 100 |
Reporting |
报告 |
30 | 30 |
Test Report |
测试报告 |
30 | 30 |
Size Measurement |
计算工作量 |
20 | 20 |
Postmortem & Process Improvement Plan |
事后总结, 并提出过程改进计划 |
40 | 30 |
合计 |
1750 | 1690 |
解题思路
-
采用C语言实现各个功能,通过命令行的模式进行输入。
- 对于统计字符数,则是使用fgect()函数对文件中字符逐一取出,判断其是否为可显示字符,即ascii码在33~126的范围内,则字符数加1。
- 对于统计行数,则是在取出来的字符中遇到'/n'或者‘eof'时,行数加1。
- 对于统计词的字数,则是利用FILE指针的结构体的一个成员_Placeholder(_Placeholder在函数fgetc()执行后的一个指针,指向了下一个字符的位置,即*_Placeholder就是下一个字符),假设刚获取的字符为a,*_Placeholder的值为b,通过比较a是否为字母的同时,判断b是否同为字母字符,如果不是,单词数加1,是则继续获取下一个字符,知道文件所有字符全部读取完。
- 对于递归文件夹获取所有指定文件并进行操作,利用struct _finddata_t该结构体,来获取当前文件的属性,判断其是否为文件夹,若是,则继续递归文件夹,不是则判断其后缀名是否符合所指定文件,符合则统计,不符合则继续查找下一个文件。
- 对于查询复杂操作,空行则是利用一个数组存放文件一行的可显示字符,若数组中的字符的长度小于2(包括换行符),则空行加1;在前面的基础上,利用strchr()函数判断数组中是否存在着“//”,若无,则字符行加1;若有,则判断在“//”前面是否存在两个以上(包括两个)的话,则为字符行,若小于1,则为注释行。
程序流程
关键代码
功能:获取行数
功能:获取词数
功能:获取字符数
功能:获取复杂数据
功能:递归文件夹
测试文件:
测试截图:
递归文件夹:(此处只是为了验证递归查询操作,故各个文件只是文件名不一样,文件内容一致)
项目小结:
这次项目经历中,因为之前从没有做过使用函数去打开函数的操作,所以,当拿到题目的时候,需要自己上网搜索c语言的打开文件的函数fopen和获取文件内容的函数fgetc,找到文件函数后,字符计算和函数计算还是比较简单的,之后遇到的一个问题是单词的计算,因为考虑到这个单词的计算是需要前后字符的比较的,然后观察了一下执行fgetc函数后FILE结构体的变化,发现其中的一个成员_Placeholder是指向下一个字符的地址,于是刚好可以利用到。而一开始的判断逻辑是想着先判断第一个获取的是非字母,第二个是字母的时候,发现没有办法去计算第一个单词;后来更换了一下逻辑,换成判断第一个是字母,如果第二个是非字母,则可算是一个单词,从而解决了这个问题。在打算做文件递归的时候,因为不知道文件如何判断一个文件是文件夹还是文件,又上网找了相关资料,然后找到了一个相关的结构体,可根据其相关成员值来判断。在做复杂数据处理的时候,采用了一数组一行文件内容的方法,对整个文件做一行一行的处理。在做这个项目的过程中也遇到许许多多的一些细节逻辑bug,但最终都能通过单步跟踪一步步找出来。本来还想着做下图像化界面,一方面是目前能力有限,之前基本没有做过图像化界面的经历,要想做得学很多东西,但奈何时间有限,来不及研究图像化界面的内容。