快捷搜索:  as

php设计模式介绍之注册模式

我们平日觉得避免应用全局变量是一种好的选择,是以,工具常常被作为参数从一段代码通报到另一 段。然则通报实例的一个问题便是工具无意偶尔候不知道将要通报给谁——?颠末一个函数后才被 通报到真正必要这个工具的函数。

为了编写,涉猎,改动代码的方便,最好能够削减不合工具的 数量,并且能够将大年夜量广泛应用的工具统一表示为一个单一,常用的工具。

问题:

你若何 经由过程单一的全局的工具来获取对其它工具的引用?

办理规划:

“注册模式” 就像“工具的电话簿”——储存并且能够取回对工具引用的挂号簿。(注:PHP中 的“联合数组”也起到了类似“电话簿”的功能。事实上,“注册模式 ”便是环抱PHP中强大年夜的数组完成的。)“注册模式”的一些特点常常被包孕在“ 单一模式”中(拜见第四章),使得“注册模式”成为你全部利用信息的抉择性滥觞。

注释:“注册模式”类主要参考了Martin Fowlerdescribes用Java说话实现的 Patterns of EntERPrise Application Architecture(企业利用法度榜样体系布局模型)。Marcus Baker谢 了一篇具体的PHP中利用“注册模式”的文章。该文章可在PHPPatterns.com的站点获的 (http://www.PHPpatterns.com/index.PHP/article/articleview/75/1/1/)。Baker也涉及了一些测试 considerations,示范了测试驱动的开拓措施。

样本代码:

正如Martin Flower在他的 “注册模式”一文中说起的样本代码所示,你可以用各类措施,供给各类接口实现“注 册模式”。让我们仔细商量这种设法主见,并建立PHP4中的“注册模式”的一些不合实现。

让我们以编写能储存并规复工具实例并能对“注册模式”供给全局造访的代码开始。 这个类的实例变量能够缓存工具,并且“注册模式”本身是一个“单一模式”。 像曩昔一样,测试抉择需求。我们的第一个测试要确定“注册模式”是一个“单件模式 ”类。

// PHP4

class ReGIStryPHP4TestCase extends UnitTestCase {

function testRegistryIsSingleton() {

$this->assertIsA($reg =& Registry::getInstance(), ‘Registry’);

$this->assertReference($reg, Registry::getInstance());

}

}

这里,要把你在曩昔几章“单件模式 ”中学到的常识用上,你应该能够很快写出能够经由过程该测试的类。以下是一个满意测试要求的 “注册模式”类(ignoring the code required to enforce no direct object creation):

class Registry {

function &getInstance() {

static $instance = array();

if (!$instance) $instance[0] =& new Registry;

return $instance [0];

}

}

一个简单的静态数组就足够记录这个单一实例了。

接下来, 让我们转到“注册模式”独特的特点上面。一个“注册模式”应该供给get() 和 set()措施来存储和取得工具(用一些属性key)而且也应该供给一个isValid()措施来确定一个给定的属 性是否已经设置。

这三个措施的一个简单实现在接下来评论争论。这里是两个isValid():措施的测试 措施。

代码:

class RegistryPHP4TestCase extends UnitTestCase

{function testRegistryIsSingleton() { /*...*/ }

function testEmptyRegistryKeyIsInvalid()

{$reg =& Registry::getInstance();

$this- >assertFalse($reg->isValid('key'));

}

function testEmptyRegistryKeyReturnsNull()

{$reg =& Registry::getInstance();

$this- >assertNull($reg->get('key'));

}

}

作者注: assertFalse()

assertFalse()仅仅是assertTrue()的不和,假如第一个参数预期是PHP中的布尔 值false,测试经由过程。

经由过程基于测试驱动的开拓要领,你可以编写尽可能少的代码来相符你现阶 段的测试需求,你也可以增添测试——假如你还未满意这个类的需求。

以下为满意前 述测试要求的最简单的代码:

代码:

class ReGIStry

{function isValid() {return false;}

function get() {}

function &getInstance()

{static $instance = array();

if (!$instance) $instance[0] =& new Registry;

return $instance[0];

}

}

确凿,isValid() 和 get()措施的代码片断并不是异常好 ,然则所有的测试经由过程了!下面我们添加更富厚的测试用例。

代码:

class RegistryPHP4TestCase extends UnitTestCase

{function testRegistryIsSingleton() { /*...*/ }

function testEmptyRegistryKeyIsInvalid() { /*...*/ }

function testEmptyRegistryKeyReturnsNull() { /*...*/ }

function testSetRegistryKeyBecomesValid ()

{$reg =& Registry::getInstance();

$test_value = 'something';$reg- >set('key', $test_value);

$this->assertTrue($reg->isValid ('key'));

}

}

您可能还会对下面的文章感兴趣: