0

这个想法是创建一个类似 DOM 的树。但是有一些限制,只有某些类型实际上可以包含其他类型。

我想使用接口|抽象类|超类来实现一些众所周知的 js 函数,如 appendChild、replaceChild 等。

我正在使用类页面、块和项目,其中页面可以包含块,块可以包含块或项目。

示例:Page 是网页,block 可以是列表元素,item 可以是列表项元素。

但这些对象不仅仅包含 html 数据,而且这些概念不仅仅是纯 HTML 表示。这是管理项目的总体思路,无论它们具有实际表示还是只是抽象对象。这个概念本身适用于许多不同的层次结构。

我想要实现的是尽可能多地重用父类的代码(添加子类对所有类基本相同),但不同的类型提示以匹配作为子类添加的允许类型。

我发现自己基本上有四种方法:

  1. 我使用一个接口,它允许我输入超类的提示,但不能更改这些。
  2. 我使用带有公共方法的超类,所以我可以重新定义类型提示(这在继承先决条件时完全违背了通常的做法)。
  3. 我使用带有受保护方法的超类,这似乎仍然很古怪。
  4. 我摆脱了任何超类,只是多次定义几乎相同的类。
  5. 尽管有类型提示的功能,但我使用一种方法来检查类型。

所以,如果有人仍然愿意回答,我很高兴有任何提议、想法或提示,选择哪个选项。我希望我能很好地描述这个问题。

如果有什么我错过了,我很感激听到它;)

代码

超类方式(有效,但打破了先决条件继承实践)

class Base {

    public|protected function appendChild(Base $child) {
        // do stuff
    }
}

class Block extends Base {

   public function appendChild(Block $child) {
       parent::appendChild($child);
   }

}

接口方式(不行,一定不行)

interface Interface1 {

    public function appendChild(Base $child);

}

class Base implements Interface1 {

    public|protected function appendChild(Base $child) {
        // do stuff
    }
}

class Block extends Base{

   public function appendChild(Block $child) {
       parent::appendChild($child);
   }

}

编辑部分加粗

4

1 回答 1

0

界面对我来说最有意义。你可以让一个类扮演多个角色,因为它可以实现多个接口。

// you don't need any methods in the interfaces
class Foo implements Inline, Block {} 

将与两者一起使用:

appendChild(Inline $foo); and appendChild(Block $foo);

和接口可以相互扩展,所以你的所有对象都可以有一个通用的接口。

您仍然可以使用继承来重用实现,并且您可以灵活地严格使用继承树来重用实现,不受页面逻辑的限制(您永远不会被迫进行StaticSimpleton扩展HeavyDatabaseyWidget)。

如果不是接口,我会选择选项 5:只需appendChild拨打电话$child->canBeChildOf($this)和/或$this->accepts($child). 同样,逻辑和实现将是独立的,您的逻辑将有很大的自由度。

PHP 在运行 tmie 时会进行类型检查,因此无论如何使用类型系统并不会为您带来太多好处。

于 2010-01-28T23:57:36.700 回答