PrototypeModeParallelInheritanceHierarchyUseFactoryModeIn:在大规模设计中,必须维护大量的产品类。(上文,称之为“特殊耦合”)这里我们介绍它的抽象工厂模式的一个变体:原型模式。它使用clone关键字来复制特定的产品类别,让特定的产品类别完成自我复制。(通俗介绍:工厂只负责产品的生产,选择生产什么产品不再由工厂自己决定,而是通过传递参数来确认。对比抽象工厂可以发现,我们再也找不到一大群特定产品的创造者,而只能找到一个高度灵活的创造者)问题假设我们在做一款类似文明(Cicilization)的网页游戏——你没玩过这么经典的游戏吗?承和制[滑稽]。(龙剑,点击送!)里面有一个战斗用的地理系统——海洋/平原森林/森林平原三种地形,按照抽象工厂+工厂模型,我们肯定可以得到这样的结果:(为什么我经常热泪盈眶,因为StartUML2.5难用而且深奥)但是我们要避免“大继承系统”——正如我开头所说的,这会造成替代耦合,所以我们来看看在解决原型模式吧!实施类Sea{}classEarthSeaextendsSea{}classMarsSeaextendsSea{}classPlains{}classEarthPlainsextendsPlains{}classMarsPlainsextendsPlains{}classForest{}classEarthForestextendsForest{}classMarsForestextendsForest{}classTerrainFactory{private$sea;私人$平原;私人$森林;function__construct(海洋$sea,平原$plains,森林$forest){$this->sea=$sea;$this->plains=$plains;$this->forest=$forest;}functiongetSea(){返回克隆$this->sea;}functiongetPlains(){返回克隆$this->plains;}functiongetForest(){返回克隆$this->forest;}$factory=newTerrainFactory(newEarthSea(),newEarthPlains(),newEarthForest());print_r($factory->getSea());print_r($factory->getPlains());print_r($factory->getForest());看完代码就明白了原型模式,创作者可以无脑制作一个“三种地形的战斗区”,你在地球式的海洋和森林火星式的平原上战斗?那么你只需要传递三个相应的参数,换句话说——创建者不再负责:我要构建什么。我们还可以增加一些灵活性,比如:海洋地形的航行难度——造成“索马里海/渤海”的差异(古代索马里海的船只条件相当恶劣)。类Sea{private$navigability=0;函数__construct($navigability){$this->navigability=$navigability;}}...省略部分代码...$factory=newTerrainFactory(newEarthSea(-1),newEarthPlains(),newEarthForest());可以预见这是多么灵活。额外提示:如果产品类包含其他外部类,记得使用__clone()方法,这样可以保证你得到深拷贝模式的归纳性。这一段没有结论(或者,这种模式很容易理解),这里是一种诱导和欺骗的模式:他们没有帮你决定CreateWho?无论是工厂模式、抽象工厂模式,还是原型模式,它们都只是在技术层面简化了类的数量和维护的复杂度。你仍然需要自己做决定:生产特定的产品——你会把这些决定留在整个代码系统中,当你需要改变一个地方时造成瘫痪。解决方案:操作单例类/存入数据库/甚至直接写入配置文件(.htaccess等)——包含大量标签/硬编码;个人推荐:单例类+配置文件,优点:修改方便,全局访问。(面向对象的设计模式-目录)
