Как я могу сделать эту функцию хвостовой рекурсивной?
Мне интересно, если мой алгоритм хвостовой рекурсии; Я только что сделал эту функцию для красивой печати массива в PHP:
function get_pretty_output($value, $first=true, $indent = ''){
if (!is_array($value)) { return $value.PHP_EOL; }
if (empty($value)) { if ($first) { return 'Array()'.PHP_EOL; } else { return preg_replace('/ /', '', $indent, 1).')'.PHP_EOL; }}
if ($first) {
$output = 'Array'.PHP_EOL.$indent.'('.PHP_EOL;
$indent .=' ';
$first = false;
} else {
$output = '';
}
reset($value);
$key = key($value);
return $output .= $indent .
'[' .
$key .
'] => ' .
get_pretty_output(array_shift($value), true, $indent) .
get_pretty_output($value, $first, $indent);
}
потому что ни
$pretty_string = print_r($array, true);
ни
ob_start();
var_dump($array);
$pretty_string = ob_get_contents();
ob_end_clean();
кажется, работает, когда клиент отключается даже с ignore_user_abort(true)
(PHP 5.6).
Я даже не знаю, получает ли PHP выгоду от хвостовой рекурсии (мне сказали, что это не так), но в любом случае я хотел бы знать, будет ли это верным примером. Я так не думаю (нужно сохранить контекст функции для использования во втором вызове), но я не могу найти эквивалентный алгоритм хвостовой рекурсии. Есть ли способ, которым я могу следовать?
1 ответ
Это не будет примером хвостовой рекурсии, потому что вычисления все еще выполняются в более ранних рекурсивных вызовах ПОСЛЕ возврата значения. Рассмотрим пример, приведенный в предыдущем посте Stackru ( Что такое хвостовая рекурсия?). В этом случае оператор ".=" Завершит объединение, и ТО вернет результат в функцию.
Чтобы сделать этот хвост рекурсивным, вы должны изменить свой код, напечатав переменную output перед выполнением рекурсивного вызова.