在尝试解码由 json_encode 生成的字符串时,json_encode 和/或 json_decode 似乎有一个奇怪的地方:
$object = new stdClass;
$object->namespace = 'myCompany\package\subpackage';
$jsonEncodedString = json_encode($object);
echo $jsonEncodedString;
// Result of echo being:
// {"namespace":"myCompany\\package\\subpackage"}
$anotherObject = json_decode($jsonEncodedString);
echo $anotherObject->namespace;
// Result of echo being:
// myCompany\package\subpackage
$yetAnotherObject = json_decode('{"namespace":"myCompany\\package\\subpackage"}');
// Result should be:
// myCompany\package\subpackage
// But returns an invalid string sequence error instead...
echo json_last_error_msg();
在此之前我从未遇到过问题,因为直到今天我都不必捕获其中包含反斜杠的字符串。在查看上面的代码时,我可以使用 PHP 的内置组件进行编码/解码。但是,如果我尝试解码由该编码器生成的字符串,则会收到一条错误消息。我读过像“Predefined Constants”这样的文档项目和像“how remove the backslash (“\”) in the json response using php?”这样的其他堆栈问题。但我似乎找不到为什么我无法解码由 json_encode 生成的字符串的原因。我用来测试这段代码的 PHP 版本是 5.5.9。
我知道我可能会因为遗漏某些东西而完全无能为力,但是如果我尝试在其他地方使用它,我是否应该以不同的方式处理由 json_encode 生成的字符串?
最佳答案
答案在问题中:
$jsonEncodedString = json_encode($object);
echo $jsonEncodedString;
// Result of echo being:
// {"namespace":"myCompany\\package\\subpackage"}
您不必去除任何斜线。相反。您必须将回显文本表示为 PHP 源代码。
$yetAnotherObject = json_decode('{"namespace":"myCompany\\\\package\\\\subpackage"}');
反斜杠 (\
) 在 PHP 和 JSON 中都是特殊字符。两种语言都使用它来转义字符串中的特殊字符,并且为了在字符串中正确表示反斜杠,您必须在其前面加上另一个反斜杠,无论是在 PHP 还是 JSON 中。
让我们尝试对上面的字符串执行 PHP 解析器的工作。在左括号之后它遇到一个 string enclosed in single quotes .单引号字符串中有两个特殊字符需要转义:撇号 ('
) 和反斜杠 (\
)。虽然撇号总是需要转义,但 PHP 解释器是宽容的,只要不造成混淆,就允许使用未转义的反斜杠。但是,单引号字符串中反斜杠的正确表示是 \\
。
传递给函数json_decode()
的字符串是
{"namespace":"myCompany\\package\\subpackage"}
请注意,这是在运行时处理的确切字符列表,而不是用 PHP 或任何其他语言表示的字符串。这些语言有表示特殊字符的特殊规则。这只是纯文本。
上面的文本由函数 json_decode()
解释,它期望它是一段 JSON
。 JSON
是一门小型语言,它对字符串中特殊字符的编码有着特殊的规则。反斜杠是这些字符之一,当它出现在字符串中时,必须在前面加上另一个反斜杠。 JSON
不宽容;当遇到反斜杠时,它始终将其视为字符串中下一个字符的转义字符。
在成功解析您传递给它们的 JSON 表示后,由 json_decode()
创建的对象包含一个名为 namespace
的属性,其值为:
myCompany\package\subpackage
再次注意,这是实际的字符串,而不是任何语言的表示形式。
出了什么问题?
回到你的代码:
$yetAnotherObject = json_decode('{"namespace":"myCompany\\package\\subpackage"}');
PHP 解析器使用 PHP 规则解释上面的代码。它理解必须使用文本 {"namespace":"myCompany\package\subpackage"}
作为参数调用 json_decode()
函数。
json_decode()
使用其规则并尝试将上面的文本解释为一段 JSON 表示形式。 myCompany
之前的引号 ("
) 告诉它必须将 "myCompany\package\subpackage"
解析为字符串。 之前的反斜杠package
被解释为 p
的转义字符,但 \p
不是 JSON 中字符串的有效转义序列。这就是它拒绝继续并返回的原因NULL
.
关于php - 如何处理json字符串中的反斜杠php,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32056940/