【发布时间】:2010-05-07 03:37:23
【问题描述】:
我有一个问题困扰了我很久。我正在构建一个模板引擎,它有两个主要类Template.php 和Tag.php,还有一堆扩展类,如Img.php 和String.php。
程序是这样工作的:
一个模板对象创建一个标签对象。每个标签对象决定实现哪个扩展类(img、string等)。
Tag类的重点是为每个扩展类提供帮助函数如wrap('div'),addClass('slideshow')等
每个 Img 或 String 类 用于呈现特定于所需内容的代码,因此$Img->render() 会给出类似<img src='blah.jpg' /> 的代码
我的问题是:
我是否应该像这样封装 Tag 对象中的所有扩展功能:
Tag.php
function __construct($namespace, $args) {
// Sort out namespace to determine which extension to call
$this->extension = new $namespace($this); // Pass in Tag object so it can be used within extension
return $this; // Tag object
}
function render() {
return $this->extension->render();
}
Img.php
function __construct(Tag $T) {
$args = $T->getArgs();
$T->addClass('img');
}
function render() {
return '<img src="blah.jpg" />';
}
用法:
$T = new Tag("img", array(...);
$T->render();
....或者我应该创建更多的继承结构,因为“Img 是一个标签”
Tag.php
public static create($namespace, $args) {
// Sort out namespace to determine which extension to call
return new $namespace($args);
}
Img.php
class Img extends Tag {
function __construct($args) {
// Determine namespace then call create tag
$T = parent::__construct($namespace, $args);
}
function render() {
return '<img src="blah.jpg" />';
}
}
用法:
$Img = Tag::create('img', array(...));
$Img->render();
我确实需要一个用于创建自定义标签的通用接口,即我可以实例化 Img(...) 然后实例化 String(...),我确实需要使用 Tag 实例化每个扩展。
编辑:也只是为了澄清:Tag 类具有所有扩展类共有的功能,Tag 类中不应该有任何方法需要在扩展类中实现。标签类仅提供辅助函数。
我知道这是一个有点模糊的问题,我希望你们中的一些人过去已经处理过这个问题,并且可以预见到选择每种设计模式时会遇到某些问题。如果您有任何其他建议,我很想听听。
谢谢! 马特·穆勒
【问题讨论】:
标签: php design-patterns templates