Bridge Strategy 和State的区别
首先需要申明的是本文不是介绍Bridge Strategy 和State模式,而是讨论它们的区别,所以需要你对它们先有所了解。
Bridge模式用一句话来说就是将抽象和实现分离。这句话如何理解,在《Design Pattern Explained》一书中做了很详细的解释。说实话,我现在已经记不清它是怎么说的了。
我是这样理解的:对一个事物进行抽象,得到了一个行为。 比如对Shape进行抽象,得到了Draw的行为。Draw是在哪里实现的?不是在它抽象而来的类Shape,而是在另外一个类实现的。哪个类呢?Drawing类。
Draw是从Shape抽象出来的行为,但是不在Shape中予以实现。这就是抽象和实现分离。
为什么要这样呢?因为Draw的方法可能不同,比如可以用实线,也可以用虚线。为了更好的隐藏变化,所以将其分离。由于本文不是介绍Bridge模式,不再深入介绍它的好处。
(BTW在吕震宇的文章中似乎并不是Bridge模式,因为缺少被抽象的行为,但是具有Bridge模式的思想Favor composition than inheritance,不过在这三个模式中都有这个思想,所以大家很难分清。)
说到这里,你有没有想到Template Method模式。为什么不用它来实现?
错! Template Method重在Template。你这里只是根据不同的方法(实线,虚线)重写Draw方法。那个Template方法你并没用到。
这样我们就引出了Bridge和Strategy的区别。
Bridge就是将抽象出的行为交给别人做,抽象方法中就是一个简单的委托,没有使用模板方法。
而Strategy就是有模板方法的Bridge。如下:
所以区别的关键在于那个抽象方法是不是Template方法。
再来看Strategy和State模式。同样这里不会细谈State模式,相关内容可以见DP。(State模式主要描述的是有限自动机的思想)
其实这两个模式区别比较大,不过在Gof的图中没体现出来。
就拿DP书中的例子来说:
关键就在于那个TCPState对TCPConnection的引用。
为什么书中没有这条线?因为TCPConnection是作为函数参数(Open(TCPConnection tp))传给TCPState的。TCPState本身并没有TCPConnection的引用。
为什么要有这条线,在这里强调的是在各个方法中会改变TCP连接的状态。比如当目前TCP连接处于Closed状态,那么调用Open自然会改变当前的状态使之变为TCPEstablished,而要想改变TCPConnection的state对象,自然要传入TCPConnection的引用,然后调用SetState方法。
另外要说的是TCPConnection中的状态的变化是由TCPState来控制的,其他任何对象都不应该控制。也就是说SetState函数也只能有TCPState来调用。(其实这里应该采用类似C++友元的机制比较好)而Stradegy中的具体算法是由外界设置和改变的,而不是模式的内部活动。
现在你明白他们的区别了吗?比你相像的要大吧。
不过他们的目的都是两个:
Find what vary and encapsulate it.
Favor composition than inheritance.