根据此类图,其目的是模拟几种类型文档的生成:
此处可用的尺寸更大:https://www.dropbox.com/s/heub3dmh7sznkih/document_generation.png?dl=0
客户端代码将使用DocumentGenerator类,它是一个Document工厂,描述所需文档的类型和服务(检查是可选的,只有派遣文档才需要)。
我正在努力学习红色的课程。如果所有保险公司都使用相同的文件模型来处理发票,估算等,那么这不是一个大问题。但是,有一家公司需要打印不同的调度文档模型,这很可能发生在更多的公司,不仅是发货,还包括其他文件。
猜猜如果我为每家公司专门设计每个文档子类会发生什么?这将是代码重复的噩梦。
两种设计模式(策略或 decorator )可能符合我的要求,以支持合成而非继承,但我无法弄清楚如何捕获想法。
欢迎提出任何建议。
这是此图表的XMI文件的链接,以防您想要使用它: https://www.dropbox.com/s/n1l5ohdnojvvkze/documents_generation.xmi?dl=0
修改
我知道如何做到这一点。也许不需要新班级。实现(PHP):
// DocumentGenerator Class
class DocumentGenerator {
const INVOICE_TYPE = 1;
const ESTIMATE_TYPE = 2;
const DISPATCH_TYPE = 3;
private __construct() {}
public function getInstance($type, Service $service)
{
switch($type) {
case self::ESTIMATE_TYPE:
$document = new Estimate($service);
break;
case self::DISPATCH_TYPE:
$document = new Dispatch($service);
break;
default:
case self::INVOICE_TYPE:
$document = new Invoice($service);
}
return $document;
}
}
// Document Class
abstract class Document {
protected $service;
public function __construct(Service $service)
{
$this->service = $service;
}
abstract protected function show();
// ....
}
// Invoice Class
class Invoice extends Document {
const PATH_SEGMENT = 'invoice';
public function show()
{
// the key point
$this->view->setPath(self::PATH_SEGMENT . '/' . $service->getCompanyName());
$this->view->create();
}
// ...
}
// creating an invoice, no matter the company
$document = DocumentGenerator::getInstance(DocumentGenerator::INVOICE_TYPE, $service);
$document->show();
公司名称和文档类型将导致视图使用正确的模板。我还不确定这是否是一个好的解决方案,因为我有硬编码的命名约定来达到特定的模板文件。
还有其他建议吗?
答案 0 :(得分:1)
如果您有不同的要求,则可能需要不同的实施方案。如果您有一些文档的通用格式,您可以创建一些覆盖该文档的超类。如果你对不同的公司有不同的实现,那么你需要实现完全不同的Dispatch / Estimate / Invoice类,你会发现一些概括(这将启用代码重用)。在任何情况下:不同的要求会导致不同的代码。我不明白这会如何导致噩梦。一种替代方案总是(尽管在大多数情况下由于封锁头不可能),它可以说服或统治一些常见的文档格式。