假设我们在\Base\Form\命名空间中有两个类:
class Field {
protected $name;
protected $value;
}
class DropdownField extends Field {
protected $options = [];
// with functions like setOptions(), addOption(), removeOption() etc.
}
Run Code Online (Sandbox Code Playgroud)
现在,在另一个命名空间中,存在一个扩展的类Field,它具有一个附加'layout_position'属性:
namespace Integrations;
class IntegrationsField extends \Base\Form\Field {
const LAYOUT_POSITION_LEFT = 'left';
const LAYOUT_POSITION_RIGHT = 'right';
protected $layoutPosition = self::LAYOUT_POSITION_LEFT;
}
Run Code Online (Sandbox Code Playgroud)
现在,您可能会看到这一个即将到来,但如果IntegrationsField这也可以是下拉列表:
namespace Integrations;
class IntegrationsDropdownField extends \Base\Form\DropdownField {}
Run Code Online (Sandbox Code Playgroud)
当然,这个也应该有$layoutPosition,应该继承IntegrationsField,但由于我们不能扩展两个类,这里最好的解决方案是什么?
PHP不支持多重继承.但是,您可以使用特征来重写逻辑,以(模拟)模拟它.
class Field {
protected $name;
protected $value;
}
trait Dropdown {
protected $options = [];
// with functions like setOptions(), addOption(), removeOption() etc.
}
interface IntegrationPositions {
const LAYOUT_POSITION_LEFT = 'left';
const LAYOUT_POSITION_RIGHT = 'right';
}
trait Integration {
protected $layoutPosition = IntegrationPositions::LAYOUT_POSITION_LEFT;
}
class DropdownField extends Field {
use Dropdown;
}
class IntegrationField extends Field {
use Integration;
}
class DropdownIntegrationField extends Field {
use Integration,Dropdown;
}
Run Code Online (Sandbox Code Playgroud)
更新:由于@Adambean注意到traits不能有常量.因此,我使用枚举更新了示例.
如果必须声明一个特征内部的枚举,那就觉得很奇怪,但据我所知,PHP似乎不允许任何其他机制实现这一点,我对任何其他想法持开放态度.
| 归档时间: |
|
| 查看次数: |
3365 次 |
| 最近记录: |