4

我对 OOP 比较陌生,所以浏览 Simple HTML DOM 的文档时,我想知道它的方法如何同时使用方法链接和返回值/对象的常规行为。

例如我可以这样做:

 $html = new simple_html_dom();
 $html -> find('something'); // Returns object or array of objects

但我也可以这样做:

 $html -> find('something') -> find('something_else');

如果我正确理解方法链接,这意味着find()返回$thisie 本身。

我也理解使用方法链接你 return $this,之后你使用 getter 方法来实际返回一个你可以使用/想要的值。例如:

$object -> add(1) -> add(2) -> getNumber();

我在这里想念什么?提前致谢!

4

2 回答 2

2

实际上,在 find 的返回值上调用 find 是没有意义的,因为该返回值应该是一个数组。

您最终可以向您添加第二个参数,find(string, array&)以便您可以执行以下操作:

$result1 = [];
$resilt2 = [];

$html -> find('something', $result1)
      -> fint('something else', $result2);

var_dump($result1, $result2);

和 :

public function find($search, & $output) {
    $output = ...
    return $this;
}

取决于你的口味。仅当您想在同一个对象上调用多个方法(特别不返回任何内容)以避免每次都重写变量名并因此缩短代码时,链调用才有用。

编辑:如果你想做类似的事情:

" $html -> find('div#results') -> find('li a'); "

你有一个问题,因为 $html 代表一个 DOM,而 find 返回的值不是一个 DOM,而是一组结果。您的 find 函数最终可能会创建并返回一个较小的 DOM,其中 #result 作为根(这将是与 $html 相同类的对象,而不是数组),然后调用 find 将在该新根上执行搜索文档的根目录,但这看起来有点不直观。

于 2013-04-11T19:18:37.553 回答
1

您所指的链接类型涉及返回 not $this,而是返回一个表示找到的数据的新对象。诀窍是使用“魔术方法”预定义接口使该对象数组或标量一样可用。

SimpleXML 扩展广泛使用了这个概念,因此每个对象都可以同时以多种方式使用:

  • __toString(),以便转换为字符串,或在明确的字符串上下文中使用,例如echo为您提供 XML 节点的文本内容
  • ArrayAccess以便您可以使用它$a['href']来访问属性,并$li[42]访问多个匹配节点之一
  • 迭代器,以便您可以foreach进行多个匹配
  • __get()__set()通过标签名称搜索和覆盖子元素

(实际上,SimpleXML 是一个二进制扩展,所以有点作弊,但理论上它的大部分功能都可以使用上述方法在纯 PHP 中实现。)

因此,例如以下语句:

echo $simplexml_element->foo[42]->bar['baz'];

看起来包含数组、散列和字符串,但实际上是一个完整的对象调用链,如下所示:

echo $simplexml_element->__get('foo')->offsetGet(42)->__get('bar')->offsetGet('baz')->__toString();
于 2013-04-11T20:40:36.310 回答