当类中的某些功能不满足我们的需求的时候,我们可以使用继承,重写此方法来实现我们的需求
继承:子类构造方法第一句话必须调用父类的构造方法,并且子类继承父类的成员变量和方法(除了私有成员和构造方法)
需求1:读取文本并显示行数
分析:使用缓存输入字符流,只能输出文本,并不会显示行数,那么我们需要重写BufferedReader的readLine
class LineBufferedReader extends BufferedReader{ //行数 int count = 1; //注意:子类构造方法第一句话必须调用父类的构造方法 //BufferedReader没有无参数的构造方法,所以我们需要指定调用父类的其中一个构造方法 public LineBufferedReader(Reader in) { super(in); } //重写readLine方法 @Override public String readLine() throws IOException { //接受父类的readLine()的内容 String line = super.readLine(); //父类的readLine方法,读取到文本的末尾时会返回null if(line != null) { String newline = count+line; count++; return newline; }else { //如果父类的readLine方法返回null,那么表示已经到末尾了,直接返回line(null) return line; } } } public class Demo1 { public static void main(String[] args) throws IOException { //找到目标文件 File file = new File("D:\新建文件夹\1.txt"); //建立数据传输通道 FileReader fileReader = new FileReader(file); LineBufferedReader bufferedReader = new LineBufferedReader(fileReader); String line = ""; while((line = bufferedReader.readLine())!=null) { System.out.println(line); } bufferedReader.close(); } }
需求2:读取文本并在每一行后面加一个逗号
需求3:读取文本并在每一行后面加一个分号
需求4:读取文本并显示行数且在每一行后面加一个逗号
需求5:读取文本并显示行数且在每一行后面加一个分号
需求6:读取文本并显示行数且在每一行后面加一个分号和逗号
等等....
这样每有一个需求,我们就要定义一个类并重写readLine方法,导致继承体系过于庞大,而且不灵活
装饰者设计模式可以达到同样的效果,并且我们只需要实现前三个需求就可以组合完成其他需求,这样大大减少了继承体系,并且更灵活
装饰者设计模式:增强一个类的功能,并且还可以让这些装饰类互相装饰
装饰者设计模式的步骤:
1.让装饰类有一个共同的父类和父接口(只有继承或者实现关系才能使用多态)
2.在内部维护一个被装饰的类的引用(这样是为了使用多态来完成互相装饰的效果)
装饰者设计模式,和继承的优缺点:
继承
优点:代码结构清晰,易理解,而且实现简单
缺点:对于每一个需求,都需要增强的子类实现,导致继承体系过于庞大,而且不灵活
装饰者设计模式
优点:内部使用多态技术,对多个需要增强的类进行增强,可以使这些装饰类达到互相装饰的效果,比较灵活
缺点:需要使用多态技术维护需要被增强的类,使代码稍微复杂了点
//给读取的文本添加行号 class LineBufferedReader extends BufferedReader{ //在内部维护一个被装饰的类的引用 BufferedReader bufferedReader; //行数 int count = 1; public LineBufferedReader(BufferedReader bufferedReader) {//参数---多态 super(bufferedReader);//在装饰者设计模式中。此语句没有任何作用只是为了防止报错 this.bufferedReader = bufferedReader; } //重写readLine方法 @Override public String readLine() throws IOException { //调用传入对象的readLine方法 String line = bufferedReader.readLine(); if(line != null) { String newline = count+line; count++; return newline; }else { return line; } } } //给每一个文本添加分号 class SemicolonBufferedReader extends BufferedReader{ //在内部维护一个被装饰的类的引用 BufferedReader bufferedReader; public SemicolonBufferedReader(BufferedReader bufferedReader) {//参数---多态 super(bufferedReader);//在装饰者设计模式中。此语句没有任何作用只是为了防止报错 this.bufferedReader = bufferedReader; } //重写readLine方法 @Override public String readLine() throws IOException { //调用传入对象的readLine方法 String line = bufferedReader.readLine(); if(line != null) { String newline = line+";"; return newline; }else { return line; } } }
读取文本并显示行数
public class Demo2 { public static void main(String[] args) throws IOException { //找到目标文件 File file = new File("D:\新建文件夹\1.txt"); //建立数据传输通道 FileReader fileReader = new FileReader(file); //读取文本 BufferedReader bufferedReader = new BufferedReader(fileReader); //给读取的文本添加行号 LineBufferedReader lineBufferedReader= new LineBufferedReader(bufferedReader); String line = ""; while((line = lineBufferedReader.readLine())!=null) { System.out.println(line); } bufferedReader.close(); } }
读取文本并在每一行后面加一个分号
public class Demo2 { public static void main(String[] args) throws IOException { //找到目标文件 File file = new File("D:\新建文件夹\1.txt"); //建立数据传输通道 FileReader fileReader = new FileReader(file); //读取文本 BufferedReader bufferedReader = new BufferedReader(fileReader); //给读取的文本添加分号 SemicolonBufferedReader semicolonBufferedReader = new SemicolonBufferedReader(bufferedReader); String line = ""; while((line = semicolonBufferedReader.readLine())!=null) { System.out.println(line); } bufferedReader.close(); } }
读取文本并显示行数且在每一行后面加一个分号(互相装饰)
public class Demo2 { public static void main(String[] args) throws IOException { //找到目标文件 File file = new File("D:\新建文件夹\1.txt"); //建立数据传输通道 FileReader fileReader = new FileReader(file); //读取文本 BufferedReader bufferedReader = new BufferedReader(fileReader); //给读取的文本添加行号 LineBufferedReader lineBufferedReader = new LineBufferedReader(bufferedReader); //给读取的文本添加分号 SemicolonBufferedReader semicolonBufferedReader = new SemicolonBufferedReader(lineBufferedReader); String line = ""; while((line = semicolonBufferedReader.readLine())!=null) { System.out.println(line); } bufferedReader.close(); } }