php - 改进 PHP 中的类结构而不是使用多重继承

标签 php oop design-patterns inheritance

我有一个设计问题,我的类是这样设置的:

abstract class Advertiser        abstract class AdvertiserCampaign
      |                                    |
      |                                    |
class AdvUno extends Advertiser  class AdvUnoCampaign extends AdvertiserCampaign
class AdvDos extends Advertiser  class AdvDosCampaign extends AdvertiserCampaign
class AdvTre extends Advertiser  class AdvTreCampaign extends AdvertiserCampaign

问题是 AdvUnoAdvUnoCampaign 都需要一种特殊的身份验证方法,而其他方法则不需要。现在我已将其放置在 AdvUno 中,但是 AdvUnoCampaign (以及以这种方式设置的许多其他类)将再次需要它。

  • 我无法让 AdvUnoCampaign 扩展 AdvUno,因为 PHP 中没有多重继承,而且还因为它通常不是一种良好、简洁的设计实践。
  • 如果我使 AdvertiserCampaign 扩展 Advertiser,则下面的所有扩展类(AdvUnoCampaignAdvDosCampaign、等)必须实现一堆与他们无关的抽象方法,并且这些方法已经在每个 Advertiser 类中实现。

简而言之,在这种情况下最好的设计实践是什么?我不想只是将代码复制并粘贴到所有 AdvOne 类中。任何帮助或建议将不胜感激。谢谢!

最佳答案

Parallel Inheritance Hierarchies被认为是代码异味,应该重构。

Martin Fowler 在“重构”中建议:

The general strategy for eliminating the duplication is to make sure that instances of one hierarchy refer to instances of the other. If you use Move Method and Move Field, the hierarchy on the referring class disappears.

但我认为你可以更进一步。我不知道您为每个广告商及其广告事件创建子类的决定是基于什么,但我会质疑这个决定。一个值得遵循的好习惯是 Favor Composition over Inheritance .

你可以这样开始:

class Advertiser
{
  protected $authentication;
}

class AdvertiserCampaign
{
  protected $authentication;
}

interface AdvertiserAuthentication
{
}

class SpecialAuthenticationForAdvertiserUno implements AdvertiserAuthentication
{
}

class NoSpecialAuthenticationForOtherAdvertisers implements AdvertiserAuthentication
{
}

现在,广告商之间的第一个区别已转移到另一个类别中。继续处理其他差异,直到每个广告商只是以不同方式组成的 Advertiser 对象。竞选事件也是如此。我想更具体一些,但正如之前所说,我不知道为什么您的广告商首先都有自己的类。

关于php - 改进 PHP 中的类结构而不是使用多重继承,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15417766/

相关文章:

c# - 结构化顺序处理的最佳设计模式

java - 如何覆盖java变量并使变量成为必填字段

android - Android TextView 中的 Linkify

php - 我可以从新的 Laravel 5 安装中删除哪些文件夹和文件

php - 需要合并2个表

java - 类中的私有(private)接口(interface)

C++ 对象创建和内存分配

java - 如何根据instanceof对对象进行操作?

php - 启用 PHP Apache2

php - Laravel 5 Illuminate\Http\Request 有不允许静态调用的方法