软件设计师笔记——(第七章:23种设计模式)
一、下午题总结(试题六)(⭐⭐⭐)二、创建型模式(5种)(⭐⭐⭐)1、工厂方法模式2、抽象工厂模式3、生成器模式4、原型模式5、单例模式三、结构型模式(7种)(⭐⭐⭐)1、适配器模式2、桥接模式3、组合模式4、装饰器模式5、外观模式6、享元模式7、代理模式四、行为型模式(11种)(⭐⭐⭐)1、责任链模式2、命令模式3、解释器模式4、迭代器模式5、中介者模式6、备忘录模式7、观察者模式8、状态模式9
目录
一、下午题总结(试题六)(⭐⭐⭐)
二、创建型模式(5种)(⭐⭐⭐)
1、工厂方法模式
1.意图:定义一个用于创建对象的接口,让子类决定将哪一个类实例化,使一个类的实例化延迟到其子类。
2.适用性
- 1.当一个类不知道它所必须创建的对象的时候。
- 2.当一个类希望由它的子类来指定所创建的对象的时候。
- 3.当类将创建的对象的职责委托给多个帮助子类中的某一个,并且你希望将哪一个帮助子类是代理这一信息局部化的时候。
3.结构图
4.结构图代码
public class FactoryMethod {
public static void main(String[] args) {
Factory factoryA = new FactoryA();
// 父类 对象名 = new 子类();
Product productA = factoryA.createProduct();
// Product productA = new ProductA();
productA.info();
Factory factoryB = new FactoryB();
Product productB = factoryB.createProduct();
productB.info();
}
}
// class Factory
interface Factory {
public Product createProduct();
}
class FactoryA implements Factory {
@Override
public Product createProduct() {
return new ProductA();
}
}
class FactoryB implements Factory {
@Override
public Product createProduct() {
return new ProductB();
}
}
// abstract class Product
interface Product {
// public abstract void info();
public void info();
}
// class ProductA extends Product
class ProductA implements Product {
@Override
public void info() {
System.out.println("产品的信息:A");
}
}
// class ProductB extends Product
class ProductB implements Product {
@Override
public void info() {
System.out.println("产品的信息:B");
}
}
2、抽象工厂模式
1.意图:提供一个创建一系列相关或相互依赖对象的接口,而无需指定他们具体的类。
2.适用性:
- ①一个系统要独立于它的产品的创建,组合和表示时;
- ②一个系统要由多个产品系列中的一个来配置时;
- ③需要强调一系列相关的产品对象的设计以便进行联合使用时;
- ④提供一个产品类库,而只想显示它们的接口而不是实现时。
3.结构图
4.结构图——软考12下原题
import java.util.*;
class Department { /*代码省略*/ }
interface IDepartment {
(1);
(2);
}
class SqlserverDepartment (3) {
public void Insert(Department department) {
System.out.println("Insert a record into Department in SQL Server!");
// 其余代码省略
}
public Department GetDepartment(int id) {
/*代码省略*/
}
}
class AccessDepartment (4) {
public void Insert(Department department) {
System.out.println("Insert a record into Department in ACCESS!");
// 其余代码省略
}
public Department GetDepartment(int id) {
/* 代码省略 */
}
}
(5) {
(6);
}
class SqlServerFactory implements IFactory {
public IDepartment CreateDepartment() {
return new SqlserverDepartment();
}
// 其余代码省略
}
class AccessFactory implements IFactory {
public IDepartment CreateDepartment() {
return new AccessDepartment();
}
// 其余代码省略
}
3、生成器模式
1.意图:将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。
2.适用性:
- ①当创建复杂对象的算法应该独立于该对象的组成部分以及它们的装配方式时。
- ②当构造过程必须允许被构造的对象有不同表示时。
3.结构图
4.结构图——软考18上原题
import java.util.*;
class Product {
private String partA;
private String partB;
public Product() {}
public void setPartA(String s) { partA = s; }
public void setPartB(String s) { partB = s; }
}
interface Builder {
public (1);
public void buildPartB();
public (2);
}
class ConcreteBuilder1 implements Builder {
private Product product;
public ConcreteBuilder1() { product = new Product(); }
public void buildPartA() { (3)("Component A"); }
public void buildPartB() { (4)("Component B"); }
public Product getResult() { return product;}
}
class ConcreteBuilder2 implements Builder {
// 代码省略
}
class Director {
private Builder builder;
public Director(Builder builder) { this.builder = builder; }
public void construct() {
(5);
// 代码省略
}
}
class Test {
public static void main(String[] args) {
Director director1 = new Director(new ConcreteBuilder1());
director1.construct();
}
}
4、原型模式
1.意图:用原型实例指定创建对象的种类,并且通过拷贝这个原型来创建新的对象。
2.适用性:
- ①当一个系统应该独立于它的产品创建、构成和表示时
- ②当要实例化的类是在运行时刻指定时。
- ③当一个类的实例化只能有几个不同状态组合的一种时。建立相应数目的原型并克隆它们,可能比每次用合适的状态手工实例化该类更方便些。
3.结构图
4.结构图——软考13上原题
class WorkExperience (1) Cloneable { // 工作经历
private String workDate;
private String company;
public Object Clone() {
(2);
obj.workDate= this.workDate;
obj.company = this.company;
return obj;
}
// 其余代码省略
}
class Resume (3) Cloneable { // 简历
private String name;
private String sex;
private String age;
private WorkExperience work;
public Resume(String name) {
this.name = name;
work = new WorkExperience();
}
private Resume(WorkExperience work) {
this.work = (4);
}
public void SetPersonInfo(String sex, String age) { /* 代码略 */ }
public void SetWorkExperience(String workDate, String company) {/* 代码略 */}
public Object Clone() {
Resume obj = (5);
// 其余代码省略
return obj;
}
}
class WorkResume {
public static void main(String[] args) {
Resume a = new Resume("张三");
a.SetPersonInfo("男", "29");
a.SetWorkExperience("1998-2000", "XXX公司");
Resume b = (6);
b.SetWorkExperience("2001-2006", "YYY公司");
}
}
5、单例模式
1.意图:保证一个类仅有一个实例,并提供一个访问这个唯一实例的全局访问点。
2.适用性:
- ①当类只能有一个实例而且客户可以从一个众所周知的访问点访问它时。
- ②当这个唯一实例应该是通过子类化可扩展的,并且客户应该无需更改代码就能使用一个扩展的实例时。
三、结构型模式(7种)(⭐⭐⭐)
1、适配器模式
1.适配器:将一个类的接口转换成客户希望的另外一个接口,使得原本由于接口不兼容而不能一起工作的那些类可以一起工作。
2.适用性:
- ①适用于想使用一个已经存在的类,而其接口不符合要求的情况。
- ②想创建一个可以服用的类,该类可以与其他不相关的类和不可预见的类协同工作。
3.结构图:
4.结构图——软考16上原题
import java.util.*;
class Address {
public void street() { /* 实现代码省略 */ }
public void zip() { /* 实现代码省略 */ }
public void city() { /* 实现代码省略 */ }
// 其他成员省略
}
class DutchAddress {
public void straat() { /* 实现代码省略 */ }
public void postcode() { /* 实现代码省略 */ }
public void plaats() { /* 实现代码省略 */ }
// 其他成员省略
}
class DutchAddressAdapter extends DutchAddress {
private (1);
public DutchAddressAdapter (Address addr) {
address = addr;
}
@Override
public void straat() {
(2);
}
@Override
public void postcode() {
(3);
}
@Override
public void plaats() {
(4);
}
// 其他成员省略
}
class Test {
public static void main(String[] args) {
Address addr = new Address();
(5);
System.out.println("\n The DutchAddress\n");
testDutch(addrAdapter);
}
static void testDutch(DutchAddress addr) {
addr.straat();
addr.postcode();
addr.plaats();
}
}
2、桥接模式
1.意图:将抽象部分与其实现部分分离,使它们都可以独立地变化。
2.适用性:
- ①适用于不希望在抽象和它的实现部分之间有一个固定的绑定关系的情况。
3.结构图
4.结构图——软考17下原题
import java.util.*;
class Matrix { // 各种格式的文件最终都被转化为像素矩阵
// 此处代码省略
}
abstract class Implementor {
public (1); // 显示像素矩阵m
}
class WinImp extends Implementor {
public void doPaint(Matrix m) { // 调用 Windows 系统的绘制函数绘制像素矩阵
// 此处代码省略
}
}
class LinuxImp extends Implementor {
public void doPaint(Matrix m) { // 调用 Linux 系统的绘制函数绘制像素矩阵
// 此处代码省略
}
}
abstract class Image {
public void setImp(Implementor imp) { this.imp = imp; }
public abstract void parseFile(String fileName);
protected Implementor imp;
}
class BMPImage extends Image {
// 此处代码省略
}
class GIFImage extends Image {
public void parseFile(String fileName) {
// 此处解析BMP文件并获得一个像素矩阵对象m
(2); // 显示像素矩阵m
}
}
class JPEGImage extends Image {
// 此处代码省略
}
class Main {
public static void main(String[]args) {
// 在Linux操作系统上查看demo.gif图像文件
Image image = (3);
Implementor imageImp = (4);
(5);
Image.parseFile("demo.gif");
}
}
3、组合模式
1.意图:将对象组合成树形结构以表示“部分一整体”的层次结构, 使得用户对单个对象和组合对象的使用具有一致性。
2.结构图
3.结构图——软考21上原题
import java.util.*;
abstract class MenuComponent { // 构成层叠菜单的元素
(1) String name; // 菜单项或子菜单名称
public void printName() { System.out.println(name); }
public (2);
public abstract boolean removeMenuElement(MenuComponent element);
public (3);
}
class MenuItem extends MenuComponent {
public MenuItem(String name) { this.name=name; }
public boolean addMenuElement(MenuComponent element) { return false; }
public boolean removeMenuElement(MenuComponent element){ return false; }
public List<MenuComponent> getElement(){ return null; }
}
class Menu extends MemuComponent {
private (4);
public Menu(String name) {
this.name = name;
this.elementList = new ArrayList<MenuComponent>;
}
public boolean addMenuElement(MenuComponent element) {
return elementList.add(element);
}
public boolean removeMenuElement(MenuComponent element) {
return elementList.remove(element);
}
public List<MenuComponent> getElement() { return elementList; }
}
class CompositeTest {
public static void main(String[] args) {
MenuComponent mainMenu = new Menu("Insert");
MenuComponent subMenu = new Menu("Chart");
MenuComponent element = new MenuItem("On This Sheet");
(5);
subMenu.addMenuElement(element);
printMenus(mainMenu);
}
private static void printMenus(MenuComponent ifile) {
ifile.printName();
List<MenuComponent> children = ifile.getElement();
if (children == null) return;
for(MenuComponent element; children) {
printMenus(element);
}
}
}
4、装饰器模式
1.意图:描述了以透明围栏来支持修饰的类和对象的关系,动态地给一个对象添加一些额外的职责,从增加功能的角度来看,装饰器模式相比生成子类更加灵活。
2.适用性:
①在不影响其他对象的情况下,以动态、透明的方式给单个对象添加职责
②处理那些可以撤销的职责
③当不能采用生成子类的方式进行扩充时。3.结构图
4.结构图——软考16下原题
class Invoice {
public void printInvoice() {
System.out.println("This is the content of the invoice!");
}
}
class Decorator extends Invoice {
protected Invoice ticket;
public Decorator(Invoice t) {
ticket = t;
}
public void printInvoice() {
if (ticket != null)
(1);
}
}
class HeadDecorator extends Decorator {
public HeadDecorator(Invoice t) {
super(t);
}
public void printInvoice () {
System.out.println("This is the header of the invoice!");
(2);
}
}
class FootDecorator extends Decorator {
public FootDecorator(Invoice t) {
super(t);
}
public void printInvoice() {
(3);
System.out.println("This is the footnote of the invoice!");
}
}
class Test {
public static void main(String[] args) {
Invoice t = new Invoice();
Invoice ticket;
ticket = (4);
ticket.printInvoice();
System.out.println("--------------------");
ticket = (5);
ticket.printInvoice();
}
}
程序的输出结果为:
This is the header of the invoice!
This is the content of the invoice!
This is the footnote of the invoice!
--------------------
This is the header of the invoice!
This is the footnote of the invoice!
5、外观模式
1.意图:为子系统中的一组接口提供一个一致的界面,Facade模式定义了一个高层接口,这个接口使得这一子系统更加容易使用。
2.适用性:
- ①适用于需要为一个复杂子系统提供一个简单接口的情况。
- ②客户程序与抽象类的实现部分之间存在很大的依赖性。
- ③当需要构建一个层次结构的子系统时,使用Facade模式定义子系统中每层的入口点。
3.结构图
4.结构图——软考22下原题
import java.util.*;
interface Patient {
( 1 )
}
interface Disposer{
( 2 )
}
class Registry implements Disposer{ //
public void dispose(Patient patient) {
System.out.println("I am registering..."+patient.getName());
}
}
class Doctor implements Disposer { //医生门诊
public void dispose(Patient patient) {
System.out.println("I am diagnosing..."+ patient.getName());
}
}
class Pharmacy implements Disposer { //取药
public void dispose(Patient patient) {
System.out.println("I am giving medicine..."+ patient.getName());
}
}
class Facade {
private Patient patient;
public Facade(Patient patient) { this.patient=patient;}
public void dispose(){
Registry registry=new Registry();
Doctor doctor=new Doctor();
Pharmacy ph=new Pharmacy();
registry.dispose(patient);
doctor.dispose(patient);
ph.dispose(patient);
}
}
class ConcretePatient implements Patient {
private String name;
public ConcretePatient(String name) { this.name=name;}
public String getName() { return name;}
}
class FacadeTest{
public static void main(String[] args) {
Patient patient=( 3 );
( 4 ) f =( 5 );
( 6 );
}
}
6、享元模式
1.意图:运用共享技术有效地支持大量细粒度的对象。
2.适用性:
- ①一个应用程序使用了大量的对象;
- ②完全由于使用大量的对象而造成很大的存储开销;
- ③对象的大多数状态都可变为外部状态;
- ④如果删除对象的外部状态,那么可以用相对。
3.结构图
4. 结构图——软考21下原题
import java.util.*;
enum PieceColor { BLACK, WHITE } // 棋子颜色
class PiecePos { // 棋子位置
private int x;
private int y;
public PiecePos(int a, int b) { x = a; y = b; }
public int getX() { return x; }
public int getY() { return y; }
}
abstract class Piece { // 棋子定义
protected PieceColor m_color; // 颜色
protected PiecePos m_pos; // 位置
public Piece(PieceColor color, PiecePos pos) {
m_color = color;
m_pos = pos;
}
(1);
}
class BlackPiece extends Piece {
public BlackPiece(PieceColor color, PiecePos pos) { super(color, pos); }
public void draw() { System.out.println("draw a blackpiece"); }
}
class WhitePiece extends Piece {
public WhitePiece(PieceColor color, PiecePos pos) { super(color, pos); }
public void draw() { System.out.println("white a blackpiece"); }
}
class PieceBoard { // 棋盘上已有的棋子
private static final ArrayList<(2)> m_arrayPiece = new ArrayList
private String m_blackName; // 黑方名称
private String m_whiteName; // 白方名称
public PieceBoard(String black, String white) {
m_blackName = black;
m_whiteName = white;
}
// 一步棋,在棋盘上放一颗棋子
public void SetPiece(PieceColor color, PiecePos pos) {
(3) piece = null;
if (color == PieceColor.BLACK) { // 放黑子
piece = new BlackPiece(color, pos); // 获取一颗黑子
System.out.println(m_blackName + "在位置(" + pos.getX() + "," + pos.getY() + ")");
(4);
} else { // 放白子
piece = new WhitePiece(color, pos); // 获取一颗白子
System.out.println(m_whiteName + "在位置(" + pos.getX() + "," + pos.getY() + ")");
(5);
}
m_arrayPiece.add(piece);
}
}
7、代理模式
1.意图:通过提供与对象相同的接口来控制对这个对象的访问,以使得在确实需要这个对象时才对它进行创建和初始化。
2.适用性:
- ①需要比较通用和复杂的对象指针代替简单指针时候。
四、行为型模式(11种)(⭐⭐⭐)
1、责任链模式
1.意图:使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系,将这些对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止。
2.适用性:
- ①适用于有多个的对象可以处理一个请求,哪个对象处理该请求运行时刻自动确定的情况。
- ②想在不明确指定接收者的情况下向多个对象中的一个提交一个请求。
- ③可处理一个请求的对象集合应被动态指定
2、命令模式
1.意图:将一个请求封装为一个对象,从而使得使用者可以采用不同的请求对客户进行参数化;对请求排队或记录请求日志,以及支持可撤销的操作。
2.适用性:
- ①抽象出待执行的动作以参数化某对象。
- ②在不同的时刻指定、排列和执行请求。
3.结构图
4. 结构图——软考14下原题
class Light {
public Light() {}
public Light(String name) { /* 代码省略 */ }
public void on() { /* 代码省略 */ } // 开灯
public void off() { /* 代码省略 */ } // 关灯
// 其余代码省略
}
(1) {
public void execute();
}
class LightOnCommand implements Command { // 开灯命令
Light light;
public LightOnCommand(Light light) { this.light = light; }
public void execute() { (2); }
}
class LightOffCommand implements Command { // 关灯命令
Light light;
public LightOffCommand(Light light) { this.light = light; }
public void execute() { (3); }
}
class RemoteControl { // 遥控器
Command[] onCommands = new Command[7];
Command[] offCommands = new Command[7];
public RemoteControl() { /* 代码省略 */ }
public void setCommand(int slot, Command onCommand, Command offCommand) {
(4) = onCommand;
(5) = offCommand;
}
public void onButtonWasPushed(int slot) {
(6);
}
public void offButtonWasPushed(int slot) {
(7);
}
}
class RemoteLoader {
public static void main(String[] args) {
RemoteControl remoteControl = new RemoteControl();
Light livingRoomLight = new Light("Living Room");
Light kitchenLight = new Light("kitchen");
LightOnCommand livingRoomLightOn = new LightOnCommand(livingRoomLight);
LightOffCommand livingRoomLightOff = new LightOffCommand(livingRoomLight);
LightOnCommand kitchenLightOn = new LightOnCommand(kitchenLight);
LightOffCommand kitchenLightOff = new LightOffCommand(kitchenLight);
remoteControl.setCommand(0, livingRoomLightOn, livingRoomLightOff);
remoteControl.setCommand(1, kitchenLightOn, kitchenLightOff);
remoteControl.onButtonWasPushed(0);
remoteControl.offButtonWasPushed(0);
remoteControl.onButtonWasPushed(1);
remoteControl.offButtonWasPushed(1);
}
}
3、解释器模式
1.意图:给定一个语言,定义它的文法的一种表示,并定义一个解释器,这个解释器使用该表示来解释语言中的句子。
2.适用性:
- ①当有一个语言需要解释执行,并且可将该语言中的句子表示为一个抽象语法树。
4、迭代器模式
1.意图:提供一种方法来顺序访问一个聚合对象中的各个元素而不需要暴露该对象的内部标识。
2.适用性:
- ①访问一个聚合对象的内容而无需暴露他的内部表示。
- ②支持对聚合对象的多种遍历。
- ③为遍历不同的聚合对象提供一个统一的接口。
5、中介者模式
1.意图:用一个中介对象来封装一系列的对象交互。中介者使各对象不需要显式地相互引用,从而使其耦合松散,而且可以独立地改变它们之间的交互。
2.适用性:
- ①一组对象以定义良好但是复杂的方式进行通信,产生的相互依赖关系结构混乱且难以理解。
3.结构图
4.结构图——软考20下原题
import java.util.*;
interface WebServiceMediator {
public (1);
public void SetAmazon(WebService amazon);
public void SetEbay(WebService ebay);
}
abstract class WebService {
protected (2) mediator;
public abstract void SetMediator(WebServiceMediator mediator);
public (3);
public abstract void search(double money);
}
class ConcreteServiceMediator implements WebServiceMediator {
private WebService amazon;
private WebService ebay;
public ConcreteServiceMediator() {
amazon = null;
ebay = null;
}
public void SetAmazon(WebService amazon) {
this.amazon = amazon;
}
public void SetEbay(WebService ebay) {
this.ebay = ebay;
}
public void buy(double money, WebService service) {
if (service == amazon)
amazon.search(money);
else
ebay.search(money);
}
}
class Amazon extends WebService {
public void SetMediator(WebServiceMediator mediator) {
this.mediator = mediator;
}
public void buyService(double money) {
(4);
}
public void search(double money) {
System.out.println("Amazon receive:" + money);
}
}
class Ebay extends WebService {
public void SetMediator(WebServiceMediator mediator) {
this.mediator = mediator;
}
public void buyService(double money) {
(5);
}
public void search(double money) {
System.out.println("Ebay receive:" + money);
}
}
6、备忘录模式
1.意图:在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,从而可以在以后将该对象恢复到原先保存的状态。
2.适用性:
- ①必须保存一个对象在某一时刻的状态,这样以后需要它时才能恢复到先前的状态。
- ②如果一个用接口来让其他对象直接得到这些状态,将会暴露对象的实现细节并破坏对象的封装。
3.结构图:
4.结构图——软考22上原题
import java.util.*;
class Memento {
private String state;
public Memento(String state) {
this.state = state;
}
public String getState() {
return state;
}
}
class Originator {
private String state;
public void setState(String state) {
this.state = state;
}
public String getState() {
return state;
}
public Memento saveStateToMemento() {
return (1) ;
}
public void getStateFromMemento(Memento Memento) {
state = (2) ;
}
}
class CareTaker {
private List<Memento> mementoList = new ArrayList<Memento>();
public (3) {
mementoList.add(state);
}
public (4) {
return mementoList.get(index);
}
}
class MementoPaneDemos {
public static void main(String[] args) {
Originator originator = new Originator();
CareTaker careTaker = new CareTaker();
originator.setState("State #1");
originator.setState("State #2");
careTaker.add( (5) );
originator.setState("State #3");
careTaker.add( (6) );
originator.setState("State #4");
System.out.println("Current State:" + originator.getState());
originator.getStateFromMemento(careTaker.get(0));
System.out.println("First saved State:" + originator.getState());
originator.getStateFromMemento(careTaker.get(1));
System.out.println("Second saved State:" + originator.getState());
}
}
7、观察者模式
1.意图:定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。
2.适用性:
- ①当一个抽象模型有两个方面,其中一个方面依赖于另一个方面,将这两者封装在独立的对象中以使他们可以各自独立的改变和复用
- ②当一个对象的改变需要同时改变其他对象,而不知道具体有多少对象待改变时
- ③当一个对象必须通知其他对象,而他又不能假定其他对象是谁,即不希望这些对象是紧耦合的
3.结构图
4.结构图——软考19下原题
import java.util.*;
interface Observer {
public (1);
}
interface Subject {
public void Attach(Observer obs);
public void Detach(Observer obs);
public void Notify();
public void setStatus(int status);
public int getStatus();
}
class OfficeDoc implements Subject {
private List<(2)> myObs;
private String mySubjectName;
private int m_status;
public OfficeDoc(String name) {
mySubjectName = name;
this.myObs = new ArrayList<Observer>();
m_status = 0;
}
public void Attach(Observer obs) { this.myObs.add(obs); }
public void Detach(Observer obs) { this.myObs.remove(obs); }
public void Notify() {
for (Observer obs : this.myObs) { (3); }
}
public void setStatus(int status) {
m_status = status;
System.out.println("SetStatus subject[" + mySubjectName + "]status:" + status);
}
public int getStatus() { return m_status; }
}
class DocExplorer implements Observer {
private String myObsName;
public DocExplorer(String name, (4) sub) {
myObsName = name;
sub.(5);
}
public void update() {
System.out.println("update observer[" + myObsName + "]");
}
}
class ObserverTest {
public static void main(String[] args) {
Subject subjectA = new OfficeDoc("subject A");
Observer observerA = new DocExplorer("observer A", subjectA);
subjectA.setStatus(1);
subjectA.Notify();
}
}
8、状态模式
1.意图:使得一个对象在其内部状态改变时通过调用另一个类中的方法改变其行为,使这个对象看起来如同修改了它的类。
2.适用性:
- ①一个对象的行为决定他的状态,并且他必须在运行时刻根据状态改变他的行为。
- ②一个操作中含有庞大的多分支的条件语句,且这些分支依赖该对象的状态。
3.结构图
4.结构图——软考18下原题
import java.util.*;
abstract class CState {
public int flyMiles; // 里程数
public (1); // 根据累积里程数调整会员等级
}
class CNoCustomer extends CState { // 非会员
public double travel(int miles, CFrequentFlyer context) {
System.out.println("Your travel will not account for points");
return miles; // 不累积里程数
}
}
class CBasic extends CState { // 普卡会员
public double travel(int miles, CFrequentFlyer context) {
if (context.flyMiles >= 25000 && context.flyMiles < 50000)
(2);
if (context.flyMiles >= 50000)
(3);
return miles;
}
}
class CGold extends CState { // 金卡会员
public double travel(int miles, CFrequentFlyer context) {
if (context.flyMiles >= 25000 && context.flyMiles < 50000)
(4);
if (context.flyMiles < 25000);
(5);
return miles + 0.5 * miles; // 累积里程数
}
}
class CSilver extends CState { // 银卡会员
public double travel(int miles, CFrequentFlyer context) {
if (context.flyMiles <= 25000)
context.setState(new CBasic());
if (context.flyMiles >= 50000)
context.setState(new CGold());
return (miles + 0.25 * miles); // 累积里程数
}
}
class CFrequentFlyer {
CState state;
double flyMiles;
public CFrequentFlyer() {
state = new CNoCustomer();
flyMiles = 0;
setState(state);
}
public void setState(CState state) { this.state = state; }
public void travel(int miles) {
double bonusMiles = state.travel(miles, this);
flyMiles = flyMiles + bonusMiles;
}
9、策略模式
1.意图:定义一系列算法,把它们一个个封装起来,并且使它们可相互替换。这一模式使得算法可独立于它的客户而变化。
2.适用性:
- ①许多相关的类仅仅是行为有异。
- ②当需要一个算法的不同变体。
- ③算法使用客户不应该知道的数据。
3.结构图
4.结构图——软考19上原题
import java.util.*;
interface BrakeBehavior {
public (1);
/* 其余代码省略 */
}
class LongWheelBrake implements BrakeBehavior {
public void stop() { System.out.println("模拟长轮胎刹车痕迹!"); }
/* 其余代码省略 */
}
class ShortWheelBrake implements BrakeBehavior {
public void stop() { System.out.println("模拟短轮胎刹车痕迹!"); }
/* 其余代码省略 */
}
abstract class Car {
protected (2) wheel;
public void brake() { (3); }
/* 其余代码省略 */
}
class ShortWheelCar extends Car {
public ShortWheelCar(BrakeBehavior behavior) {
(4);
}
/* 其余代码省略 */
}
class StrategyTest {
public static void main(String[] args) {
BrakeBehavior brake = new ShortWheelBrake();
ShortWheelCar car1 = new ShortWheelCar(brake);
car1.(5);
}
}
10、模板方法模式
1.意图:定义一个操作中的算法骨架,而将一些步骤延迟到子类中,使得子类可以不改变一个算法的结构即可重新定义算法的某些特定步骤。
2.适用性:
- ①一次性实现一个算法的不变的部分,并将可变的行为留给子类来实现。
- ②各子类公共的行为应被提取出来并集中到一个公共父类中,以避免代码重复。
- ③控制子类扩展。
11、访问者模式
1.意图:表示一个作用于某对象结构中的各元素的操作,使得在不改变各元素的类的前提下定义作用于这些元素的新操作。
2.适用性:
①一个对象结构包含很多类对象,他们有不同的接口,而用户想对这些对象实施一些依赖其具体类的操作
②定义对象结构的类很少改变,但经常需要在此结构上定义新的操作。
③需要对一个对象结构中的对象进行很多不同的并且不相关的操作,而又想避免这些操作“污染”这些对象的类。3.结构图
4.结构图——软考15上原题
import java.util.*;
interface LibraryVisitor {
(1);
(2);
void printSum();
}
class LibrarySumPrintVisitor implements LibraryVisitor { // 打印总页数
private int sum = 0;
public void visit(Book p_book) {
sum = sum + p_book.getNumberOfPages();
}
public void visit(Article p_article) {
sum = sum + p_article.getNumberOfPages();
}
public void printSum() {
System.out.println("SUM = " + sum);
}
}
interface LibraryItemInterface {
(3);
}
class Article implements LibraryItemInterface {
private String m_title; // 论文名
private String m_author; // 论文作者
private int m_start_page;
private int m_end_page;
public Article(String p_author, String p_title, int p_start_page, int p_end_page) {
m_title = p_title;
m_author = p_author;
m_start_page = p_start_page;
m_end_page = p_end_page;
}
public int getNumberOfPages() {
return m_end_page - m_start_page;
}
public void accept(LibraryVisitor visitor) {
(4);
}
}
class Book implements LibraryItemInterface {
private String m_title; // 书名
private String m_author; // 书作者
private int m_pages; // 页教
public Book(String p_author, String p_title,int p_ pages) {
m_title = p_title;
m_author = p_author;
m_pages = p_pages;
}
public int getNumberOfPages() {
return m_pages;
}
public void accept(LibraryVisitor visitor) {
(5);
}
}
开放原子开发者工作坊旨在鼓励更多人参与开源活动,与志同道合的开发者们相互交流开发经验、分享开发心得、获取前沿技术趋势。工作坊有多种形式的开发者活动,如meetup、训练营等,主打技术交流,干货满满,真诚地邀请各位开发者共同参与!
更多推荐
所有评论(0)