я наткнулся на множество примеров метода построения цепочки в PHP, но не смог найти ничего об этом, так что я прошу помочь вам, ребята;)Метод цепочки без окончательного метода
Моя проблема - может Я каким-то образом узнаю, является ли метод в цепочке последним? В большинстве случаев люди используют какой-то окончательный метод (execute, send, ..), чтобы указать, когда цепочка заканчивается и возвращает соответствующий результат. Но мне интересно, есть ли какой-нибудь скрытый магический метод или техника, чем можно проверить все методы в цепочке и определить, нет ли следующего метода? Без конечного метода он отлично работает для строк (в очень простом примере), но не для того, чтобы вернуть массив.
Вот мой сниппет:
class Chain {
private $strArray;
function __call($name, $args) {
$this->strArray[] = $args[0];
return $this;
}
function __toString() {
return implode('-', $this->strArray);
}
}
// example 1
$c = new Chain();
$x = $c->foo('hi')->bar('stack'); // need array('hi', 'stack')
// example 2
$c = new Chain();
$x = $c->foo('hi')->bar('stack')->foobar('overflow'); // need array('hi', 'stack', 'overflow')
// example 3
$c = new Chain();
echo $c->foo('hi')->foobar('overflow'); // prints 'hi-overflow'
// example 4
$c = new Chain();
echo $c->foo('hi')->bar('stack')->foobar('overflow'); // prints 'hi-stack-overflow'
Вы видите, когда я хочу, чтобы распечатать результат цепи, я могу изменить результат в методе __toString
, но что, если я нужен массив (пример 1, 2)? Есть ли способ достичь этого, не вызывая какого-то дополнительного «окончательного» метода?
Большое спасибо за помощь и сообщите мне, если вам нужна дополнительная информация.
EDIT: После обратной связи от @bandi я попытался расширить ArrayObject
вот так.
class Chain extends ArrayObject {
function __call($name, $args) {
$this->append($args[0]);
return $this;
}
function __toString() {
return implode('-', $this->getIterator()->getArrayCopy());
}
}
// returned ref. to object, works fine in loop or accessing offset
$obj = new Chain;
$x = $obj->foo('hi')->bar('stack')->foobar('overflow'); // need array('hi', 'stack', 'overflow')
foreach ($x as $y) {
echo $y, "\n";
}
var_dump($x[0], $x[1], $x[2]);
// returned String
$c = new Chain;
echo $c->foo('hi')->foobar('overflow'); // prints 'hi-overflow'
Это то, что я хотел, но я не чувствую себя так хорошо о $this->getIterator()->getArrayCopy()
части. Есть ли простой способ доступа к массиву (внутренне в ["storage":"ArrayObject":private]
)? Thanks
ОК, спасибо. Как правило, я хотел бы возвращать массив при назначении переменной, но у меня есть опция open для строки в строку. Когда я возвращаю $ this, я не получаю свойство класса ($ strArray), а целую ссылку на класс, что нежелательно, и это заставляет меня реализовать «окончательный» метод. Но, возможно, самый простой способ - передать второй аргумент TRUE последнему методу в цепочке, как вы предложили. Я посмотрю, придут ли дополнительные советы;) – lp1051
кстати. как вы имели в виду - «Другой вариант может состоять в том, чтобы изменить класс, чтобы он вел себя как массив, за исключением того, что он напечатан». ?? Я не уверен, что понимаю – lp1051
@ lp1051 Я не совсем знаком с системой классов php в более новых версиях, поэтому я не знаю, возможно ли это или нет: я имел в виду, что вы вывели свой класс из класса «array» и затем добавьте два собственных метода. – bandi