Json_encode дает ошибку рекурсии
Warning: json_encode(): recursion detected in [Directory]
Что это за ошибка, я не могу решить эту проблему. Он генерирует BIG BIG log за ошибку 500. 133 000 000 байт. Он рассылает журнал до максимальной памяти.
<?php
include('simple_html_dom.php');
if(isset($_REQUEST['type']) && $_REQUEST['type'] = "getmoredetails"){
retrievemore($_REQUEST['htmlsource']);
}
function retrievemore($htmlcode){
$retrievetitle = retrievechTitle($htmlcode);
$retrievermb = retrievechRMB($htmlcode);
echo json_encode(array("error"=>0,"rmb"=>$retrievermb,"title"=>$retrievetitle));
}
function retrievechTitle($htmlcode){
$html = str_get_html($htmlcode);
$title = $html->find('div[class=tb-detail-hd]h3');
return $title[0];
}
function retrievechRMB($htmlcode){
$html = str_get_html($htmlcode);
$rmb = $html->find('[class=tb-rmb-num]');
return $rmb[0];
}
?>
Я пытаюсь извлечь данные из файла HTML, другое извлечение работает отлично, за исключением вышеописанного, что дает много проблем. Я даже выделил этот набор кода специально для одного файла PHP для обработки и той же проблемы.
Любая идея? Я использую jQuery Ajax с несколькими функциями на домашней странице с помощью $.ajax({
Я новичок в Ajax, это нормально, если у вас есть несколько Ajax на одной странице?
Ответы
Ответ 1
Проблема заключается в том, что вы пытаетесь вызвать json_encode
на то, что не подходит для него:
echo json_encode(array("error"=>0,"rmb"=>$retrievermb,"title"=>$retrievetitle));
Что, мы можем спросить, есть $retrievetitle
? Какая это ценность? Ну, мы находим это в определении функции:
$html = str_get_html($htmlcode);
$title = $html->find('div[class=tb-detail-hd]h3');
return $title[0];
Так ясно, что это какой-то объект. Я не знаком с библиотекой simple_html_dom
, но, предположительно, это объект, принадлежащий этой библиотеке, и представляет собой элемент HTML. Возможно, это родной объект DOMElement
; Я не знаю.
Ясно, однако, что это какая-то рекурсивная структура. То есть, в некотором смысле он содержит себя. Это вполне возможно в PHP, но невозможно представить в строке JSON. Например, в PHP:
class Foo {
public $self;
public function __construct() {
$this->self = $this;
}
}
$foo = new Foo;
$foo->self
- это тот же объект, что и $foo
. Действительно, вы могли бы сделать $foo->self->self->self
, и все будет хорошо. Это очень простая рекурсивная структура. Возможно, вы немного сложнее, но не принципиально. Это невозможно представить в JSON. json_encode
будет ошибочно, когда он встретит рекурсию.
Я предполагаю, что вы, вероятно, захотели сохранить текстовое содержимое заголовка, а не сам элемент заголовка. Коротко прочитав API-документацию для библиотеки, кажется, вам нужно свойство plaintext
. Я не совсем уверен, как это работает (APi, скажем так, разрежен), но я предполагал следующее:
return $title[0]->plaintext;
Но это всего лишь образованная догадка.
Ответ 2
Простой пример для воссоздания проблемы
<?php
$o = new StdClass;
$o->arr = array();
$o->arr[] = $o;
json_encode($o);
Как только json_encode() встретит $o- > arr [0] == $o, ему нужно будет снова начать с $o, достигнуть $o- > arr [0], начать снова с $o и т.д. ad infinitum, Чтобы предотвратить это, функция "запоминает" каждый node, который уже обработан. Если он "видит" тот же самый node снова, он выдает предупреждение о рекурсии.
Объекты simple_html_dom, которые вы возвращаете из своих функций, вероятно, имеют ссылку на их родительские объекты или что-то подобное, вызывая рекурсию.
Таким образом, возможно, return (string)$title[0];
и return (string)$rmb[0];
исправят проблему.
Ответ 3
Что вы пытаетесь выполнить, используя метод POST для отправки HTML-источника. Затем разбор его на стороне сервера немного переборщил.
<?php
include('simple_html_dom.php');
if(isset($_REQUEST['type']) && $_REQUEST['type'] = "getmoredetails"){
>> echo $_REQUEST['htmlsource'];
>> return;
retrievemore($_REQUEST['htmlsource']);
}
function retrievemore($htmlcode){
$retrievetitle = retrievechTitle($htmlcode);
$retrievermb = retrievechRMB($htmlcode);
>> gettype($retrievetitle) . ' – ' . gettype($retrievermb);
>> return;
echo json_encode(array("error"=>0,"rmb"=>$retrievermb,"title"=>$retrievetitle));
}
function retrievechTitle($htmlcode){
$html = str_get_html($htmlcode);
$title = $html->find('div[class=tb-detail-hd]h3');
return $title[0];
}
function retrievechRMB($htmlcode){
$html = str_get_html($htmlcode);
$rmb = $html->find('[class=tb-rmb-num]');
return $rmb[0];
}
?>
Как выглядит ваш вызов AJAX? Вы установили параметр типа "POST"?
$.ajax({
type: "POST",
url: "/echo/json/",
data: { name: "John", location: "Boston" }
}).done(function(json)
console.log(json);
});
также вы должны попробовать просто вызвать функцию json_encode() самостоятельно. если вы получили сообщение об ошибке.
echo json_encode(array("error"=>0,"rmb"=>"rmb","title"=>"title"));
Ответ 4
Иногда simple_html_dom.php не будет приводиться к строке, как ожидалось.
Я решил проблему с помощью синтаксиса строковой строки:
$HTML_DOM = new simple_html_dom();
$HTML_DOM->load($HTML_Template,true,false); // Preserve line breaks
$Content_Box_Data = $HTML_DOM->find('div.Content_Box_Data',0); // find()
$Content_Box_Data->innertext = "Some Content";
$HTML_Template = (string)$HTML_DOM;