设计模式学习

想自己建一个游戏框架……但是看了好多框架也没有一个从头教的,唉,先自己摸索吧

去看了别人介绍 PureMVC 的文章,不知道什么模式啥的,根本看不懂……先看设计模式吧

设计模式教程
https://www.runoob.com/design-pattern/factory-pattern.html

1.工厂模式

教程里面的代码是:

要用 funA 返回一个 classA
根据 funA 参数分情况讨论,返回经过不同处理的 classA
一般来说就直接通过 switch 就好了,但这个“不同处理”可以也可以用子类实现。
也就是说,根据 funA 参数分情况创建 classA 的不同子类 classA1,classA2……,并对这些子类调用相同的方法,而不同子类中对这个方法有不同的实现,最后 funA 把子类 classA1,classA2…… 转换到基类 classA,返回 classA

其实就是把 switch 的任务,使用相同的方法名,分到各个子类方法里面

伪代码:

直接使用一个函数解决问题:

funA(arg)
{
	switch(arg)
	{
		case 1: return fun1();
		case 2: return fun2();
		//...
	}
}

使用工厂模式解决问题:

funA(arg)
{
	ClassA ins;
	switch(arg)
	{
		case 1: ins = new classA1(); break;
		case 2: ins = new classA2(); break;
		//...
	}
	return ins.interfaceA();
}

// 也可以把这个 classA 叫做接口
classA
{
	interfaceA();
}

classA1 implement classA
{
	override interfaceA();
}

classA2 implement classA
{
	override interfaceA();
}

//...

classA1::interfaceA()
{
	return fun1();
}

classA2::interfaceA()
{
	return fun2();
}

//...

2.抽象工厂模式

感觉就是工厂模式的组合而已

伪代码:

直接使用一个函数解决问题:

funA(arg)
{
	Ans ans1;
	Ans ans2;
	switch(arg[0])
	{
		case 1: ans1 = fun1_1();
		case 2: ans1 = fun1_2();
		//...
	}
	switch(arg[1])
	{
		case 1: ans2 = fun2_1();
		case 2: ans2 = fun2_2();
		//...
	}
	return [ans1, ans2];
}

使用组合工厂模式解决问题:

funA(arg)
{
	ClassA ins1;
	ClassB ins2;
	switch(arg[0])
	{
		case 1: ins1 = new classA1(); break;
		case 2: ins1 = new classA2(); break;
		//...
	}
	switch(arg[1])
	{
		case 1: ins2 = new classB1(); break;
		case 2: ins2 = new classB2(); break;
		//...
	}
	return [ins1.interfaceA(), ins2.interfaceB()];
}

// 也可以把这个 classA 叫做接口
classA
{
	interfaceA();
}

classA1 implement classA
{
	override interfaceA();
}

classA2 implement classA
{
	override interfaceA();
}

//...

classA1::interfaceA()
{
	return fun1_1();
}

classA2::interfaceA()
{
	return fun1_2();
}

//...

// 也可以把这个 classB 叫做接口
classB
{
	interfaceB();
}

classB1 implement classB
{
	override interfaceB();
}

classB2 implement classB
{
	override interfaceB();
}

//...

classB1::interfaceB()
{
	return fun2_1();
}

classA2::interfaceA()
{
	return fun2_2();
}

//...

3.单例模式

类是可以实例化的
普通的类的成员可以实例化出来多份
想要这个类的某一个成员只有一份,就是希望单例

类的静态成员就是单例

还要考虑多个线程同时访问这个单例的情况

教程中的代码挺清晰

4.建造者模式

感觉跟组合工厂没啥区别……

5.原型模式

程序中需要多次用到 classA1 classA2 的实例,但是实例化这些类的代价高昂
如果 classA1 classA2 的实例只有有限个状态,那么可以提前对每一个类实例化不同状态下的实例,需要用的时候返回浅拷贝

伪代码:

运行时实例化:

funA()
{
	// start
	// do some things...
	ins1 = new classA();
	ins1 = process1(ins1);
	use1(ins1);
	ins2 = new classA();
	ins2 = process2(ins2);
	use2(ins2);
}

提前实例化,使用时返回浅拷贝:

funA()
{
	// start
	ins1 = new classA();
	ins1 = process1(ins1);
	ins2 = new classA();
	ins2 = process2(ins2);
	Map insMap;
	insMap.put(key1,ins1);
	insMap.put(key2,ins2);
	// do some things...
	use1(insMap[key1].shallowcopy());
	use2(insMap[key2].shallowcopy());
}

6.适配器模式

要在原来的 switch 上添加情况,可以用一个子类处理新的情况

伪代码:

直接使用一个函数解决问题:

旧版本:

funA(arg)
{
	switch(arg)
	{
		case 1: return fun1();
	}
}

新版本:

funA(arg)
{
	switch(arg)
	{
		case 1: return fun1();
		case 2: return fun2();
		//...
	}
}

使用适配器模式解决问题:

旧版本:

funA(arg)
{
	ClassA ins;
	switch(arg)
	{
		case 1: ins = new classA1(); break;
	}
	return ins.interfaceA();
}

// 也可以把这个 classA 叫做接口
classA
{
	interfaceA();
}

classA1 implement classA
{
	override interfaceA();
}

//...

classA1::interfaceA()
{
	return fun1();
}

//...

新版本:

funA(arg)
{
	ClassA ins;
	switch(arg)
	{
		case 1: ins = new classA1(); break;
		case 2: ins = new classA2(); break;
		//...
	}
	return ins.interfaceA();
}

// 也可以把这个 classA 叫做接口
classA
{
	interfaceA();
}

classA1 implement classA
{
	override interfaceA();
}

classA2 implement classA
{
	override interfaceA();
}

//...

classA1::interfaceA()
{
	return fun1();
}

// classA2 就是适配器
classA2::interfaceA()
{
	return fun2();
}

//...

7.桥接模式

一个类有若干个角度,每一个角度都有 n 个实现需求
那么通过继承就要创建 ∏ni 个子类,会很多

伪代码:

classAB(arg)
{
	classA insA;
	switch(arg[0])
	{
		case 1: insA = new classA1(); break;
		case 2: insA = new classA2(); break;
		//...
	}
	classB insB;
	switch(arg[1])
	{
		case 1: insB = new classB1(); break;
		case 2: insB = new classB2(); break;
		//...
	}
}

感觉跟组合没什么区别欸

8.过滤器模式

类提供一个可供筛选的 tag
现在有一个过滤器类,输入类的实例的列表,根据 tag 筛选出符合条件的类的实例的列表

9.组合模式

组件的组合……看过 ecs 了就不多解释了

10.装饰器模式

类 B 里面存类 A,基于类 A 的方法新建方法,但不继承类 A
好像跟桥接、组合也没区别……

这么看来还是组合最纯粹

11.外观模式

感觉跟工厂模式也是一样的,只是工厂模式是根据输入参数的不同调用不同的类,这个是根据使用函数的不同调用不同的类

12.享元模式

类的实例可能被多次用到,因此第一次用到时,创建好存在 Map 里面,要用到了就拿出来

13.代理模式

同样是类似适配器、装饰器的组合思路,基于类 A 实现方法,这个方法是用于控制的

14.责任链模式

一个链表,链表成员是不同的类的实例,他们有一个身份标识,实现相同的接口,知道 next。从头结点开始匹配身份标识,是则调用接口,不是则跳到 next

15.命令模式

把一个执行流程拆成请求者,请求,发送者

伪代码:

class Sender;
class Request;
class Receiver;
class Sender
{
	makeRequest();
}

Sender::makeRequest()
{
	return new Request();
}

class Request
{
	process();
}

class Receiver()
{
	List requestList;
	addRequestToList(Request);
	ProcessRequestList();
}

Receiver::addRequestToList(Request q)
{
	requestList.add(q);
}

Receiver::ProcessRequestList()
{
	for(q : requestList)
		q.process();
	requestList.clear();
}

16.解释器模式

跟过滤器很像,都是对一个东西条件匹配

17.迭代器模式

学过 C++ 的都知道

class Iterator 
{
	next();
}

class Container
{
	Iterator iter;
}

main()
{
	List containerList;
	for(Iterator iter = containerList[0];iter;)
	{
		// do some thing
		iter = iter.next();
	}
}

18.中介者模式

网状结构转化成星形结构,中介者就是星形的那个中间节点

19.备忘录模式

保存回滚对象的状态

更进一步,可以细分为
获取对象状态
对象状态仓库
恢复对象状态

20.观察者模式

定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。

原来我们改变一个类的实例的属性的时候就直接访问然后修改了
按照这个思路,假设我不知道谁动了这个属性,但我还是要知道什么时候这个属性变了的话,那我就只能在一个死循环里面不断查看这个属性,和旧值比较,不相等就是改变了

这样做是很简单但是很蠢的方法
为了性能,必须要做复杂一点,加些约束

那么这个约束就是,我规定修改这个类的实例的属性只能通过一个函数来修改
这样的话,其他人都用这个函数,我就知道,这个函数被调用的时候就是属性被修改的时候,其他任何时候属性都不会变

伪代码:

class Client
{
	Data data;
}

class ProcessWithNotify
{
	List observersList;
	Process(Client,function);
}

ProcessWithNotify::Process(Client c,function processFun)
{
	processFun(&(c.data))
	for(ob : observersList)
		ob.Update();
}

class Observer
{
	Update();
}

21.状态模式

状态机

22.空对象模式

在数据不可用的时候提供默认的行为
好像跟工厂模式也差不多……

伪代码:

funA(arg)
{
	ClassA ins;
	switch(isValid(arg))
	{
		case true: ins = new realClassA(); break;
		case false: ins = new emptyClassA(); break;
		//...
	}
	return ins.interfaceA();
}

// 也可以把这个 classA 叫做接口
classA
{
	interfaceA();
}

realClassAimplement classA
{
	override interfaceA();
}

emptyClassA implement classA
{
	override interfaceA();
}

//...

realClassA::interfaceA()
{
	return fun1();
}

emptyClassA::interfaceA()
{
	return fun2();
}

//...

23.策略模式

同样是运行时改变行为
状态机希望状态时长时间保持不变的
策略模式是对于每一次调用都可能改变行为
其他应该没有区别

24.模板模式

期望在子类中实现方法的细节
感觉就是普通的继承

25.访问者模式

一个类 A 对于 类 B1,B2,B3 的访问,有函数定义 fun1,fun2,fun3

26.MVC模式

模型保存数据
视图用于可视化
控制器处理数据

27.业务代表模式

感觉跟策略模式是一样的,只是用在服务器的语境下

28.组合实体模式

不断地组合下去……我也没看懂多层组合是用来干啥的

29.数据访问对象模式

数据库

30.前端控制器模式

控制器处理请求
控制器中有调度器,请求通过就使用自己的调度器成员
调度器控制视图

31.拦截过滤器模式

跟过滤器模式一样,得到具有符合条件的 tag 的实体

32.服务定位器模式

跟原型模式一样,把要用的东西缓存起来

33.传输对象模式

简单的传输数据

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值