Word Count
Word Count
一.个人Gitee地址:https://gitee.com/godcoder979/(该项目完整代码在这里)
二.项目简介:
该项目是一个统计文件字符、单词、行数等数目的应用程序,通过输入命令来执行你想要的操作。所用语言:java
命令格式:
wc.exe [para] <filename> [para] <filename> ... -o <filename>
功能:
-a:统计文件中的代码行、空行、注释行;
-c:统计文件中的字符数,不包括换行符;
-w:统计文件中的单词数;
-l:统计文件的行数;
-s:统计一个文件夹中符合要求的文件;
-o:指定输出文件;
三.PSP表格:
PSP2.1 | PSP阶段 | 预估耗时(分钟) | 实际耗时(分钟) |
---|---|---|---|
Planning | 计划 | 20 | 10 |
· Estimate | · 估计这个任务需要多少时间 | 5 | 5 |
Development | 开发 | 500 | 600 |
· Analysis | · 需求分析(包括学习新技术) | 20 | 30 |
· Design Spec | · 生成设计文档 | 30 | 30 |
· Design Review | · 设计复审(和同事审核设计文档) | 10 | 15 |
· Coding Standard | · 代码规范(为目前的开发制定合适的规范) | 5 | 5 |
· Design | · 具体设计 | 15 | 20 |
· Coding | · 具体编码 | 200 | 400 |
· Code Review | · 代码复审 | 40 | 30 |
· Test | · 测试(自我测试,修改代码,提交修改) | 20 | 30 |
Reporting | 报告 | 60 | 50 |
· Test Report | · 测试报告 | 20 | 15 |
· Size Measurement | · 计算工作量 | 10 | 5 |
· Postmortem & Process improvement Plan | · 事后总结,并提出过程改进计划 | 30 | 30 |
合计 | 580 | 660 |
四.解题思路:
整个项目比较简单,用户输入需要进行的操作和基本的文件信息就可以保存结果到一个文件里。所以可以这样分析:
1)识别用户输入的选项和文件名,分析需要进行的操作
2)实现每一种功能,根据分析执行相应的操作
3)将结果保存到一个文件里
代码模块划分:
1)主函数:
通过用户输入的指令进行相应的逻辑处理
2)功能调用模块:
这个模块被主函数调用,根据分析执行相应操作
3)判断模块:
根据用户输入的指令得出需要执行那些功能,这是功能调用模块执行的依据
4)功能实现模块:
这个模块就是实现以上统计字符、单词等功能了
五.关键代码展示:
1.judge方法(分析用户要实现的功能,当flag为true是代表将要实现)
private static void judge(String str) {
// TODO Auto-generated method stub
if(str.equals("-s")&&s_flag==false){
s_flag=true;
}
else if(str.equals("-*")&&star_flag==false){
star_flag=true;
c_flag=true;
w_flag=true;
l_flag=true;
a_flag=true;
}
else if(str.equals("-a")&&a_flag==false){
a_flag=true;
}
else if(str.equals("-c")&&c_flag==false){
c_flag=true;
}
else if(str.equals("-w")&&w_flag==false){
w_flag=true;
}
else if(str.equals("-l")&&l_flag==false){
l_flag=true;
}
else if(file_flag==false)//还没有指定输入文件
{
if(s_flag==false){//如果输入的不是路径
file_name=str;
txt_name=str;
}
file_flag=true;
}
else if(str.equals("-o")&&o_flag==false){
o_flag=true;
}
else if(o_flag==true&&file_flag==true){//已经有输入文件且o_flag为真但是没有指定输出文件
output_name+=str;
all_flag=true;
}
else{
System.out.println("指令判断完成");
} }
2.字符统计:
private static int num_of_char(String filename) {
// TODO Auto-generated method stub
System.out.println(filename); File file=new File(filename);
Reader readfile=null;
int c_num=0;
try{
readfile = new InputStreamReader(new FileInputStream(file));
int tempchar;
while ((tempchar=readfile.read()) != -1) {
if((char)tempchar!='\r'&&(char)tempchar!='\n'){
c_num++;
}
}
readfile.close();
}
catch(Exception e){
e.printStackTrace();
System.out.println("指定输入文件不存在");
}
return c_num;
}
3.单词统计:(这里面我用IsLetter来判断字母的大小写)
private static int num_of_word(String filename){
File file=new File(filename);
Reader readfile=null;
boolean letter_flag=false;
int w_num=0;
try{
readfile = new InputStreamReader(new FileInputStream(file));
int tempchar;
while ((tempchar=readfile.read()) != -1) {
if(IsLetter((char)tempchar)){
letter_flag=true;
}
else if(letter_flag==true){
letter_flag=false;
w_num++;
}
}
readfile.close();
}
catch(Exception e){
System.out.println("指定输入文件不存在");
}
return w_num;
}
4.行数统计:(遇到换行符就加一。Windows中的换行符为“\r\n”,这里只使用"\n"。)
private static int num_of_line(String filename) {
// TODO Auto-generated method stub
File file=new File(filename);
Reader readfile=null;
int l_num=1;
try{
readfile = new InputStreamReader(new FileInputStream(file));
int tempchar;
while ((tempchar=readfile.read()) != -1) {
if((char)tempchar=='\n'){
l_num++;
}
}
readfile.close();
}
catch(Exception e){
System.out.println("指定输入文件不存在");
}
return l_num;
}
5.空行、代码行、注释行统计:(按行读文件,去除每一行的换行符和空格,获得的string长度为0就代表空行;一行中如果只有“{/*”、“{//”、“//”、“/*”代表注释行(这些就是注释的开头),直到统计到注释的末尾;其余的均为代码行。)
private static int [] code_ana(String filename){
File file=new File(filename);
int nothing=0;
int line=0;
int note=0;
int code_line=0;
boolean note_flag=false;
BufferedReader readfile = null;
try{
readfile = new BufferedReader(new FileReader(file));
String tempString = null;
while ((tempString = readfile.readLine()) != null) {
line++;
tempString=tempString.replaceAll("\r\n"," ");//去掉所有换行符和空格
if(note_flag==true){
note++;
if(tempString.endsWith("*/")){
note_flag=false;//代表注释内容在本行结束
}
}
if(tempString.equals(" ")||tempString.equals("{")||tempString.equals("}")){
nothing++;
}
if(tempString.startsWith("//")||tempString.startsWith("{//")){
note++;
}
if(tempString.startsWith("/*")||tempString.startsWith("{/*")){
if(tempString.endsWith("*/")){
note++;
}
else{
note++;
note_flag=true;//代表注释的内容在本行还没结束
}
}
code_line=line-note-nothing;
}
readfile.close();
}
catch(Exception e){
System.out.println("指定输入文件不存在");
}
int []num =new int[3];
num[0]=code_line;
num[1]=nothing;
num[2]=note;
return num;
}
7.功能调用模块(这里通过judge得到的功能需求,然后调用功能模块执行相应的操作):
private static void work() {
// TODO Auto-generated method stub
if(o_flag==true){
if(all_flag==false)
System.out.println("命令格式不正确:有输出指令但是没有指定输出文件");
} if(a_flag==true){
String Command="代码行/空行/注释行";
int []num=code_ana(file_name);
System.out.print(txt_name+","+Command+":"+num[0]+"/"+num[1]+"/"+num[2]+"\r\n");
} if(c_flag==true){
String Command="字符数";
System.out.print(txt_name+","+Command+":"+num_of_char(file_name)+"\r\n");
} if(l_flag==true){
String Command="行数";
System.out.print(txt_name+","+Command+":"+num_of_line(file_name)+"\r\n");
} if(all_flag==true){
if(a_flag==true){
String Command="代码行/空行/注释行";
code_output(output_name,Command,code_ana(file_name));
}
if(c_flag==true){
String Command="字符数";
output(output_name,Command,num_of_char(file_name));
}
if(w_flag==true){
String Command="单词数";
output(output_name,Command,num_of_word(file_name));
}
if(l_flag==true){
String Command="行数";
output(output_name,Command,num_of_line(file_name));
}
System.out.println("运行并且输出内容保存成功");
}
else {
System.out.println("本指令没有指定输出文件,所以输出内容没有保存");
}
}
8.读取文件夹(当我们输入的是一个绝对路径时,在这里向下递归查找符合要求的文件):
private static void files_output(String path_name){
String []path=path_name.split("\\*");
File file=new File(path[0]);
if(file.exists()){
File[]files=file.listFiles();
if(files!=null){
for(File f:files){
if(f.getName().endsWith(path[1])){
txt_name=f.getName();
file_name=f.getAbsolutePath();
work();
}
}
}
else{
System.out.println("文件夹内容为空");
}
}
else{
System.out.println(path[0]+":指定路径或文件不存在");
} }
六.测试用例:
这里我们用的是idea:直接通过传入参数的不同来测试每一种功能以及他们的组合:
下面是我用的输入文件:
1)-c input.txt -o output.txt:
2)-w input.txt -o output.txt:
3)-l input.txt -o output.txt:
4)-a input.txt -o output.txt:
5)-a -w -l -c input.txt -o output.txt:
6) -s -w -l D:/test/*.txt -o output.txt:这里我们是在一个文件夹里向下递归查找符合要求的txt文件:
七.参考文献
《构建之法--现代软件工程》 --邹欣 [第三版]
PS:(本次项目还有一些功能没有实现)未完待续......
Word Count的更多相关文章
- Hive Word count
--https://github.com/slimandslam/pig-hive-wordcount/blob/master/wordcount.hql DROP TABLE myinput; DR ...
- mac上eclipse上运行word count
1.打开eclipse之后,建立wordcount项目 package wordcount; import java.io.IOException; import java.util.StringTo ...
- MapReduce工作机制——Word Count实例(一)
MapReduce工作机制--Word Count实例(一) MapReduce的思想是分布式计算,也就是分而治之,并行计算提高速度. 编程思想 首先,要将数据抽象为键值对的形式,map函数输入键值对 ...
- Word Count作业
Word Count作业 一.个人Gitee地址:https://gitee.com/Changyu-Guo 二.项目简介 该项目主要是模拟Linux上面的wc命令,基本要求如下: 命令格式: wc. ...
- [Hive_add_6] Hive 实现 Word Count
0. 说明 Hive 通过 explode()函数 和 split()函数 实现 WordConut 1. Hive 实现 Word Count 方式一 1.1 思路 将每一行文本变为 Array 数 ...
- Mac下hadoop运行word count的坑
Mac下hadoop运行word count的坑 Word count体现了Map Reduce的经典思想,是分布式计算中中的hello world.然而博主很幸运地遇到了Mac下特有的问题Mkdir ...
- [MapReduce_1] 运行 Word Count 示例程序
0. 说明 MapReduce 实现 Word Count 示意图 && Word Count 代码编写 1. MapReduce 实现 Word Count 示意图 1. Map:预 ...
- 【2016.3.22】作业 Word count 小程序
今天更下word count程序的设计思路及实现方法. 我的程序贴在coding里,这里就先不贴出来了, 我的coding地址:https://coding.net/u/holy_angel/p/wo ...
- 软件工程第三个程序:“WC项目” —— 文件信息统计(Word Count ) 命令行程序
软件工程第三个程序:“WC项目” —— 文件信息统计(Word Count ) 命令行程序 格式:wc.exe [parameter][filename] 在[parameter]中,用户通过输入参数 ...
随机推荐
- [Swift]LeetCode394. 字符串解码 | Decode String
Given an encoded string, return it's decoded string. The encoding rule is: k[encoded_string], where ...
- [Swift]LeetCode498. 对角线遍历 | Diagonal Traverse
Given a matrix of M x N elements (M rows, N columns), return all elements of the matrix in diagonal ...
- 洛谷P1036选数(素数+组合数)
题目链接:https://www.luogu.org/problemnew/show/P1036 主要考两个知识点:判断一个数是否为素数.从n个数中选出m个数的组合 判断一个数是否为素数: 素数一定是 ...
- Java语言的简单基础
1.Java 是一种高级程序设计语言. 2.Java 是大小敏感的程序语言. 3.Java 中的 public 修饰的类名一般要与文件名相同,但也有特列:内部类. 4.Java 程序能在任何操作系统中 ...
- pytthon—day8 读写模式的结合、文件操作模式、with完成文本文件复制、游标操作
一.读写模式的结合 w:写指没有新建文件,有文件就清空 w=open('1.txt','w',encoding='utf-8') w.write('000\n') 在写入数据时,需要及时处理内存空间, ...
- Linux中断程序命令
在运行 python 脚本的时候想要中断程序,发现如下情况: ctrl+c 居然无法中断程序! 这时候尝试 ctrl+d 还是毫无效果,最后尝试 ctrl+\: 查看该程序是否还在运行 ps aux ...
- 【Spark篇】---Spark中广播变量和累加器
一.前述 Spark中因为算子中的真正逻辑是发送到Executor中去运行的,所以当Executor中需要引用外部变量时,需要使用广播变量. 累机器相当于统筹大变量,常用于计数,统计. 二.具体原理 ...
- Python 工厂函数和内建函数
工厂函数 工厂函数都是类对象, 即当你调用他们时, 创建的其实是一个类实例 例如: str(), list(), tuple()... 内建函数 内建函数通常是python自定义的一些函数, 这些函数 ...
- Redis配置与安装
Redis 是一个非关系型高性能的key-value数据库.在部分场合可以对关系数据库起到很好的补充作用.它提供了Java,C/C++,C#,PHP,JavaScript,Perl,Object-C, ...
- 带着萌新看springboot源码09(springboot+JdbcTemplate)
emmm.....常规开局,继续说一下废话,前面简单的说了一下spring的ioc容器创建原理(花了不少时间去看了别人的博客+查了不少资料+自己的理解),相信大家对ioc容器有了一个初步的认识了. s ...