我今天遇到了这个坑点。从PHP.net文档中得知:
以下是
问题在于
因此,
我猜我有几个解决方案:
serialize
函数有以下注意事项:
- 对象的私有成员在成员名前面加上类名;受保护的成员在成员名前面加上 '*',而这些前缀值两侧都有null字节。
json_encode
编码。它内部使用序列化程序来生成跟踪数据。以下是
json_encode
的(部分)输出:{"\u0000MyObject\u0000my_var":[]}
问题在于
json_decode
无法处理此问题,它会抱怨空字节。因此,
json_encode
快乐地写入空字节,而json_decode
无法解码。这对我来说似乎有点奇怪。我希望json_encode
可以处理必要的转义,或者至少json_decode
可以解析由json_encode
生成的任何内容,但事实似乎并非如此。我猜我有几个解决方案:
- 从跟踪中删除空字节,我不太关心反序列化对象,我只想要一个字符串表示。
- 完全从跟踪中删除私有变量。
- 修复
json_encode
,使其不产生空字节 - 修复
json_decode
,使其接受空字节
<?php
class MyClass {
public $mypublic = 1;
private $myprivate = 2;
public function myfunc() {
return debug_backtrace();
}
}
$c = new MyClass();
$json = json_encode(call_user_func_array(array($c, "myfunc"), new MyClass()));
echo $json;
echo json_decode($json); // <-- Fatal error: Cannot access property started with '\0' in test.php on line 12
解决方案
自 PHP 5.3 开始,当
call_user_func_array
的第二个参数不是数组时,会抛出警告。在此之前,您需要自行检查。
serialize()
,从你的话和空字节来看;实际上,json_encode()
不会保留protected
和private
属性:只有公共属性存在于返回的字符串中。*(我刚刚测试过;在json_encode()
手册页面上也有很多评论)* - Pascal MARTINcall_user_func_array
(这里的_array
非常重要)。传递的参数不是数组。在我的实际代码中,它是一个实现了Countable
、ArrayAccess
和IteratorAggregate
的对象,但仍然是一个对象。而且这个对象有一个私有参数。现在的问题是...我该怎么办? :D - Halcyonjson_decode
函数将 lambda 函数名称解析为null+'lambda_'+counter
... - Christian