关于4~6次作业总结

一、前言

三次作业对正则表达式、聚合、继承、接口进行了考察。相对前三次作业,加入了很多简单的题目,这些题目分值不高,仅占%30,因此虽然加入了一些简单的题目,但是总体难度并未减小。

二、设计与分析

①题目集4(7-2)、题目集5(7-5)两种日期类聚合设计的优劣比较

 题目集4(7-2)显然没有题目集5(7-5)设计的好

一个类对于其他类知道的越少越好,就是说一个对象应当对其他对象有尽可能少的了解,只和朋友通信,不和陌生人说话。

下面给出题目集4(7-2)的类图

这种设计会造成类与类之间的通讯效率极低,比如DateUtil类要调用year类的函数需要先引用Day类方法,后引用Month类方法,然后引用Year类方法,这之中有着大量的中介类,大大提高了整个程序的复杂度。

SourceMonitor生成报表

 

 

 

 上面分别是7-2、7-5的ScourceMonitor的生成报表,从生成报表上可以知道下面的复杂度要低得多。而且7-5的设计明显比7-2的设计要简洁的多。

(迪米特法则:个类对于其他类知道的越少越好,就是说一个对象应当对其他对象有尽可能少的了解,只和朋友通信,不和陌生人说话。)

题目集4(7-2)和题目集5(7-5)虽然都遵循了迪米特法则,然而题目集5(7-5)却要好得多

下面我们再看看题目集5(7-5)的类图

       由类图可知,day类、month类、year类的对象只出现在DateUtil类中,这里只出现一个中介类,DateUtill作为业务类,相对题目集4(7-2)整个程序的复杂度大大降低,这样有利于程序的维护。虽然迪米特法则可以降低类之间的耦合度,提高模块的相对独立性。但是过度使用迪米特法则会使系统产生大量的中介类,从而增加系统的复杂性,使模块之间的通信效率降低。所以,在釆用迪米特法则时需要反复权衡,确保高内聚和低耦合的同时,保证系统的结构清晰。我们设计程序的时候应该权衡利弊,选择最合适的设计。

②题目集4(7-3)、题目集6(7-5、7-6)三种渐进式图形继承设计的思路与技术运用(封装、继承、多态、接口等)

 题目集4(7-3)类图

1、我们对整个程序的思路进行一个概括

由类图可知,抽象类Shape有一个抽象方法getArea(),两个子类Circle和Rectangle继承类Shape的方法getArea()。而Circle和Rectangle子类分别为Ball和Box,Ball和Box分别对父类的方法getArea()经行了重写,好加了新的方法getVolum(),顾名思义,getVolum得到相对应图形的体积。

2、接下来看看程序技术应用

程序对Shape类、Circle类、Rectangle类、Ball类、Box类、进行了封装,Circle类、Rectangle类继承了Shape类,Ball类和Box类分别继承了Circle类、Rectangle类,还有重写这些方法。如果通过重写父类方法扩展新功能,写起来可能会很简单,但这会使整个继承体系的可复用性变得很差,特别是运用多态比较频繁时,程序很有可能会运行错误。因此我们可以对程序的设计进行进一步的改进,在Shape类中增加一个新的抽象方法getVolum(),这样Circle继承了getVolume()方法,Ball从Circle中继承了getVolume()方法。同理,Rectangle继承了getVolume()方法,Box从Rectangle中继承了getVolume()方法。因为圆是没有体积的所以,在Circle和Rectangle中getVolume()返回0。

 题目集6(7-5)类图

1、设计思路

设计思路很简单,就是三个图形继承自Shape类。

2、技术

 

这个设计相对题目集4(7-3)要好得多,这里父类中的方法,子类都有;子类中的方法都能在父类中找的到,这样就完成了多态。

题目集6(7-6)类图

 

 这个设计完全不同于前面两个程序,这边以GetArea作为父类,并不是Shape,而且这里面只有getArea()法,而且只有子类Rectangle,Circle,并不像题目集4(7-3)那样有子类Ball和Box需要求体积。这样的话就很容易完成多态。

③对三次题目集中用到的正则表达式技术的分析总结

进行正则表达式操作,要引用java.utiil.regex包

java.util.regex 包主要包括以下三个类:

  • Pattern 类:

    pattern 对象是一个正则表达式的编译表示。Pattern 类没有公共构造方法。要创建一个 Pattern 对象,你必须首先调用其公共静态编译方法,它返回一个 Pattern 对象。该方法接受一个正则表达式作为它的第一个参数。

  • Matcher 类:

    Matcher 对象是对输入字符串进行解释和匹配操作的引擎。与Pattern 类一样,Matcher 也没有公共构造方法。你需要调用 Pattern 对象的 matcher 方法来获得一个 Matcher 对象。

  • PatternSyntaxException:

    PatternSyntaxException 是一个非强制异常类,它表示一个正则表达式模式中的语法错误。

matches方法

1 String regex = "[\\da-zA-Z]{4}";
2         Scanner in = new Scanner(System.in);
3         String te = in.next();
4         if(te.matches(regex)) {
5             System.out.print(te + "属于验证码");
6         }else {
7             System.out.print(te + "不属于验证码");
8         }

这个是题目集6(7-3)校验验证码的一段代码,这里用到了方法matcher匹配字符串,如果匹配成功,返回true,否则返回false。

Pattern类和Matcher类

1 Pattern pattern = Pattern.compile(regex2);
2             Matcher matcher = pattern.matcher(s);
3             while(matcher.find()) {
4                 list.add(matcher.group(0));
5             }

这是寻找与正则表达式相关一段字符串,并且把这些字符串储存在列表中。

find()方法判断下面还有没可以匹配的字符串。

group(0)第一个匹配到的字符串。

④题目集5(7-4)中Java集合框架应用的分析总结

题目集5(7-4)提交源代码

 1 import java.util.Scanner;
 2 import java.util.Set;
 3 import java.util.HashSet;
 4 import java.util.Map;
 5 import java.util.HashMap;
 6 import java.util.regex.Pattern;
 7 import java.util.regex.Matcher;
 8 import java.util.ArrayList;
 9 import java.util.Arrays;
10 
11 class Main {
12     public static void main(String[] args) {
13         String code = in();
14         if(code.isEmpty()) {
15             System.out.print("Wrong Format");
16         }
17         code = code.replaceAll("(\".*?\")", "");//处理字符串中的关键字
18         String[] Keys = {//所有的关键字
19                  "abstract", "assert", "boolean", "break", "byte",
20                "case", "catch", "char", "class", "const",
21                "continue", "default", "do", "double", "else",
22                "enum", "extends", "final", "finally", "float",
23                "for", "false", "goto", "if", "implements", "import",
24                "instanceof", "int", "interface", "long", "native",
25                "new", "null" , "package", "private", "protected", 
26                "public","true", "return", "strictfp", "short", "static", 
27                "super", "switch", "synchronized", "this", "throw", 
28                "throws","transient", "try", "void", "volatile", "while"
29         };
30         code = code.replace("\t"," ");
31         code = code.replace("{"," ");
32         code = code.replace("}"," ");
33         code = code.replaceAll("\\["," ");
34         code = code.replaceAll("\\]"," ");
35         code = code.replace(","," ");
36         code = code.replace(";"," ");
37         code = code.replace("."," ");
38         code = code.replace("("," ");
39         code = code.replace(")"," ");
40         code = code.replace("[^a-zA-Z]"," ");
41         //满足测试点
42         String[] cut = code.split("\\s");
43         ArrayList<String> list = new ArrayList<>();
44         Map<String,Integer> map = new HashMap<>();
45         int count = 0;
46         for(int i = 0;i < Keys.length;i++) {
47             count = 0;
48             for(int j = 0;j < cut.length;j++) {
49                 if(Keys[i].equals(cut[j])) {
50                     map.put(Keys[i],++count);
51                 }
52             }
53         }
54         Set sort = map.keySet();
55         Object[] a = sort.toArray();
56         Arrays.sort(a);
57         for(Object i: a) {
58             System.out.print(map.get(i) + "\t" + i + "\n");
59         }
60         
61     }
62     public static String in() {//自动删减注释
63         Scanner input = new Scanner(System.in);
64         String line = "";
65         StringBuilder scan = new StringBuilder();
66         for(int i = 0;;i++) {
67             line = input.nextLine();
68             if(line.equals("exit")) {
69                 break;
70             }
71             if(line.matches("(.*)//(.*)")) {//由于//注释只有一行,在每行输入的同时删除注释。
72                 String[] cut = line.split("//");
73                 line = cut[0];
74             }
75             scan.append(line);
76         }
77         String str = scan.toString();
78         str = str.replaceAll("/\\**(.*?)/"," ");
79         return str;
80     }
81 }

java集合框架图

 

从上面的集合框架图可以看到,Java 集合框架主要包括两种类型的容器,一种是集合(Collection),存储一个元素集合,另一种是图(Map),存储键/值对映射。Collection 接口又有 3 种子类型,List、Set 和 Queue,再下面是一些抽象类,最后是具体实现类,常用的有 ArrayListLinkedListHashSet、LinkedHashSet、HashMap、LinkedHashMap 等等。

Set

Set 具有与 Collection 完全一样的接口,只是行为上不同,Set 不保存重复的元素。

Set 接口存储一组唯一,无序的对象。

Map

Map 接口存储一组键值对象,提供key(键)到value(值)的映射。

42         String[] cut = code.split("\\s");
43         ArrayList<String> list = new ArrayList<>();
44         Map<String,Integer> map = new HashMap<>();
45         int count = 0;
46         for(int i = 0;i < Keys.length;i++) {
47             count = 0;
48             for(int j = 0;j < cut.length;j++) {
49                 if(Keys[i].equals(cut[j])) {
50                     map.put(Keys[i],++count);
51                 }
52             }
53         }

这里用到Map为了将找到的关键储存起来。这里我们会有一个疑问,key(键)是String类型呢?这里value是关键字出现的次数,如果将关键字出现此时作为key(键),有可能有两个关键字出现的次数相等,

就不能通过key找到value了。

 

而用到Set是为了将map中的关键字进行排序。

54         Set sort = map.keySet();
55         Object[] a = sort.toArray();
56         Arrays.sort(a);
57         for(Object i: a) {
58             System.out.print(map.get(i) + "\t" + i + "\n");
59         }
60         

(3)采坑心得:

题目集4(7-3)

 

 

 

因为我是直接将例子里面的输出拷过来的所以多了个\t,虽然这两个输出看上去是一样的,其实不一样的。我们看第一张图,和第二张图的输入是一样的,输出看起来也是一样的,但是我们看54行~58行,这个是不一样的。

 题目集5(7-4)

这里我开始整个思路都是错的,我是将所有的标点符号以及空格都换成"",然后将所有关键字找出来,这种设计是完全错误的,因为将两端连接起来可能无意形成新的关键字,因此关键字可能会多

因为开始们有保存这个错误的代码所以现在我发给出图片。

(4)改进建议:

可以考一些小题目,这些题目可以简单一点,量多一点。最好可以将每部分的知识点都涉及一点,这样的话方便同学们自学,否则的话题目的难度太难的话,一下还真无从下手。要是通过写这些小题目,同学们对于知识点有了一定的了解,有了这个基础,做难题可能会相对轻松。学习效率更高,基础更加牢固。

(5)总结:

这几次题目集,让我对正则表达式有了更深层次的了解。还有就是,集合框架的初步了解。另外还有接口、多态的初步系学习。

我们可以进行线上线下的混合式教学,但是那些网课,可以作为我们的学习资料,没有必要强制性要求去学,因为我们除了这些网课,我们还有其他的学习资料,并不是只有这些网课才能学到东西。现在想要获得一些资料,百度就可以。

 

posted @ 2021-05-02 17:14  大白小哥  阅读(75)  评论(0)    收藏  举报