虽然这个问题是关于解决这个问题的方法,但我特别感兴趣的是干净的OO设计和符合当前PHP最佳实践的解决方案。提前谢谢你看看。
我有以下界面:
<?php
interface Tool {
/**
* Return the unique name of the tool
*/
public function getName();
}
在我的项目中实现此接口的大多数类看起来像这样:
<?php
class Drill implements Tool {
protected $toolName = 'drill';
public function getName() {
return $this->toolName;
}
}
所以问题是我有几十个重复这个逻辑的类,复制$ toolName属性和getName()逻辑,打破了“不要重复自己”的简单规则
我考虑过的一个解决方案如下:
<?php
abstract class BaseTool implements Tool {
public function getName() {
return $this->toolName;
}
}
然后只需要工具类扩展抽象BaseTool类:
<?php
class Drill extends BaseTool {
protected $toolName = 'drill';
}
然而,现在这意味着如果扩展BaseTool类,我将失去强制实现类来定义函数getName()的能力,这会导致不正确的实现。
我还认为通过让BaseTool类返回$ this-&gt; toolName,它会对实现类进行假设并打破封装。
我使用了一个简单的例子来演示问题,但希望你能得到我想要解决的问题,而且这个问题也可能与更复杂的情况有关。欣赏你的想法。
答案 0 :(得分:3)
答案 1 :(得分:1)
你的尝试看起来不错。没什么好说的。
然而,现在这意味着如果扩展BaseTool类,我将失去强制实现类来定义函数getName()的能力,这会导致不正确的实现。
你仍然强迫他们,他们需要继承一个实现它们的类或者自己实现它们。
如果所有应该实现Tool
的类都不可能从BaseTool
扩展,请随意创建更多实现getName()
的基类或直接实现它,如您所愿。
顺便说一句,如果您计划所有工具都应该扩展BaseTool
,那么根本不需要接口,至少不是这个用例。接口用于并非所有用于实现它的类都从同一基类继承的情况。
答案 2 :(得分:0)
如何避免在PHP中重复实现的getter函数
抽象类通常用于对重复的代码进行分组。你走在正确的道路上。至于你对选择的怀疑......
然而,现在这意味着如果扩展BaseTool类,我将失去强制实现类来定义函数getName()的能力,这会导致不正确的实现。
通过扩展BaseTool类,类继承 getName()
(这就是在抽象类中定义它的想法)。我不确定为什么会导致错误的实现,或者为什么你必须“强制实现类来定义它”。他们通过扩展抽象类来自动获取它。
我还认为通过让BaseTool类返回$ this-&gt; toolName,它会对实现类进行假设并打破封装。
如果在抽象类中定义toolName
并在构造函数中设置其值可能会更清晰?
<?php
abstract class BaseTool implements Tool {
protected $toolName;
public function __construct($toolName)
{
$this->toolName = $toolName;
}
public function getName() {
return $this->toolName;
}
}
您可以在扩展类中定义构造函数以将其名称设置为:
<?php
class Drill extends BaseTool {
public function __construct()
{
parent::__construct("drill");
}
}