GitHub仓库地址: https://github.com/softwarehsc/java1
PSP表格:
PSP2.1 | Personal Software Process Stages | 预估耗时(分钟) | 实际耗时(分钟) |
---|---|---|---|
合计 | 540 | ||
· Test Repor | · 测试报告 | 60 | 40 |
· Test | · 测试(自我测试,修改代码,提交修改) | 60 | 240 |
· Size Measurement | · 计算工作量 | 10 | 10 |
· Postmortem & Process Improvement Plan | · 事后总结, 并提出过程改进计划 | 10 | 10 |
· Estimate | · 估计这个任务需要多少时间 | 20 | 60 |
· Design Spec | · 生成设计文档 | 30 | 30 |
· Design Review | · 设计复审 | 30 | 10 |
· Design | · 具体设计 | 60 | 30 |
· Coding Standard | · 代码规范 (为目前的开发制定合适的规范) | 20 | 15 |
· Coding | · 具体编码 | 120 | 380 |
· Code Review | · 代码复审 | 60 | 30 |
· Analysis | · 需求分析 (包括学习新技术) | 60 | 60 |
Reporting | 报告 | 80 | 60 |
Planning | 计划 | 60 | 60 |
Development | 开发 | 480 | 795 |
需求分析
-
统计文件的字符数:
- 只需要统计Ascii码,汉字不需考虑
- 空格,水平制表符,换行符,均算字符
-
统计文件的单词总数,单词:至少以4个英文字母开头,跟上字母数字符号,单词以分隔符分割,不区分大小写。
统计文件的有效行数:任何包含非空白字符的行,都需要统计。- 英文字母: A-Z,a-z
- 字母数字符号:A-Z, a-z,0-9
- 分割符:空格,非字母数字符号
- 例:file123是一个单词, 123file不是一个单词。file,File和FILE是同一个单词
- 统计文件中各单词的出现次数,最终只输出频率最高的10个。频率相同的单词,优先输出字典序靠前的单词。
-
按照字典序输出到文件result.txt:例如,windows95,windows98和windows2000同时出现时,则先输出windows2000
- 输出的单词统一为小写格式
-
输出的格式为
characters: number
words: number
lines: number <word1>: number <word2>: number
实现过程
在eclipse建立文件main.java包含文件的读入和主方法,调用lib.java中Print类的求characters、words、lines等的方法实现需求。
在WordCount类中首先通利用BufferedReader类通过从字符输入流中读取文本。将所有字母单词转换为小写形式,再次读取文档,通过正则表达式
过滤掉标点符号分离出单词存储在lists列表中(List<String> lists = new ArrayList<String>(); )。最后通过wordsCount存储单词计数信息(Map<String, Integer> wordsCount = new TreeMap<String,Integer>();)
代码说明
主方法类用于读取文本文件统计字符个数 并调用Prinit类中的函数输出相应words、lines等参数的值:
1 public class WordCount { 2 3 public static void main(String[] args) throws Exception { 4 Scanner scanner=new Scanner(System.in); 5 String pathname=scanner.nextLine(); 6 //将文本单词转化为小写 7 Reader myReader = new FileReader(pathname); 8 Reader myBufferedReader = new BufferedReader(myReader); 9 CharArrayWriter tempStream = new CharArrayWriter(); 10 int i = -1; 11 int k1=0; 12 do { 13 k1++; 14 if(i!=-1) 15 tempStream.write(i); 16 i = myBufferedReader.read(); 17 if(i >= 65 && i <= 90){ 18 i += 32; 19 } 20 }while(i != -1); 21 myBufferedReader.close(); 22 Writer myWriter = new FileWriter(pathname); 23 tempStream.writeTo(myWriter); 24 tempStream.flush(); 25 tempStream.close(); 26 myWriter.close(); 27 ///再次读取文档 28 BufferedReader br = new BufferedReader(new FileReader(pathname)); 29 30 List<String> lists = new ArrayList<String>(); //存储过滤后单词的列表 31 String read= null; 32 while((read = br.readLine()) != null){ 33 String[] wordsArr1 = read.split("[^a-zA-Z]"); //过滤出只含有字母的 34 for (String word : wordsArr1) { 35 if(word.length() != 0){ //去除长度为0的行 36 lists.add(word); 37 } 38 } 39 } 40 41 br.close(); 42 43 Map<String, Integer> wordsCount = new TreeMap<String,Integer>(); //存储单词计数信息,key值为单词,value为单词数 44 for (String li : lists) { 45 if(wordsCount.get(li) != null){ 46 wordsCount.put(li,wordsCount.get(li) + 1); 47 }else{ 48 wordsCount.put(li,1); 49 } 50 51 } 52 System.out.println("Characters: "+k1); 53 Print printwords=new Print(); 54 printwords.printWords(wordsCount); 55 Print printline=new Print(); 56 printline.printline(pathname); 57 Print printWordsFrequence=new Print(); 58 printWordsFrequence.printWordFrequence(wordsCount); 59 } 60 } 61
1、printWords(Map<String,Integer> oldmap)函数用于输出文本单词总数:
1 public static void printWords(Map<String,Integer> oldmap){
2
3 ArrayList<Map.Entry<String,Integer>> list = new ArrayList<Map.Entry<String,Integer>>(oldmap.entrySet());
4
5 Collections.sort(list,new Comparator<Map.Entry<String,Integer>>(){
6 public int compare(Entry<String, Integer> o1, Entry<String, Integer> o2) {
7 return o2.getValue() - o1.getValue(); //降序
8 }
9 });
10
11 int sum=0;
12 for(int i = 0; i<list.size(); i++){
13 sum+=list.get(i).getValue();
14 }
15 System.out.println("words: "+sum);
16 }
2、printline(String pathname)函数用于输出文本行数:
1 public static void printline(String pathname)
2 {
3 try
4 {
5 BufferedReader br = new BufferedReader(new FileReader(pathname));
6 int count=0;
7 while (br.ready()) {
8 br.readLine();
9 count ++;
10 }
11 System.out.println("lilnes: "+count);
12 }
13 catch(IOException e) {
14 e.printStackTrace();
15 }
16 }
3、 printWordFrequence(Map<String,Integer> oldmap)函数用于输出排名前十且以四个英文字母开头的单词的频率
1 public static void printWordFrequence(Map<String,Integer> oldmap){
2
3 ArrayList<Map.Entry<String,Integer>> list = new ArrayList<Map.Entry<String,Integer>>(oldmap.entrySet());
4
5 Collections.sort(list,new Comparator<Map.Entry<String,Integer>>(){
6 public int compare(Entry<String, Integer> o1, Entry<String, Integer> o2) {
7 return o2.getValue() - o1.getValue(); //降序
8 }
9 });
10 int k=0;
11 for(int i = 0; i<list.size(); i++){
12 if(k>10)break;
13 if(list.get(i).getKey().length()>3)
14 {
15 System.out.println(list.get(i).getKey()+ ": " +list.get(i).getValue());
16 k++;
17 }
18
19 }
20 }