我正在使用 FQL 从 Facebook 检索用户列表。为了保持一致性,我得到 JSON 格式的结果。这会导致一个问题——因为返回的 JSON 将用户 ID 编码为数字,所以 json_decode() 会将这些数字转换为浮点值,因为有些数字太大而无法放入 int;当然,我需要这些 ID 作为字符串。
由于 json_decode() 在不接受任何行为标志的情况下做自己的事情,我很茫然。关于如何解决这个问题的任何建议?
我正在使用 FQL 从 Facebook 检索用户列表。为了保持一致性,我得到 JSON 格式的结果。这会导致一个问题——因为返回的 JSON 将用户 ID 编码为数字,所以 json_decode() 会将这些数字转换为浮点值,因为有些数字太大而无法放入 int;当然,我需要这些 ID 作为字符串。
由于 json_decode() 在不接受任何行为标志的情况下做自己的事情,我很茫然。关于如何解决这个问题的任何建议?
json_decode()可以将大整数转换为字符串,如果你在函数调用中指定一个标志:
$array = json_decode($json, true, 512, JSON_BIGINT_AS_STRING)
我通过添加&format=json-strings
到我的 FQL api 调用解决了这个问题,如下所示:
$myQuery = "SELECT uid2 FROM friend WHERE uid1=me()";
$facebook->api("/fql?q=" . urlencode($myQuery) . "&format=json-strings")
这告诉 facebook 将所有数字括在引号中,这导致 json_decode 既不使用 int-s 也不使用浮点数。
因为我担心这个问题不仅限于 FQL,而是所有选择将某些 ID 表示为 BIG-INT 的图形 API 调用我已经尽可能修补 facebook 的 PHP SDK 以强制 Facebook 返回其所有数字作为字符串。
我已将这一行添加到_graph
函数中。
这将是 facebook_base.php 版本 3.1.1 中的第 738 行
$params['format'] = 'json-strings';
确定修复
我有一个类似的问题,json_decode
即将最近的推特/推文 ID 转换为指数数字。
如果您希望您的 BIGINT 成为字符串并且拥有 PHP 5.3+,Björn 的回答非常棒。如果这些都不成立,另一种选择是提高 PHP 的浮点精度。这可以通过不同的几种方式来完成......
precision
值并将其更改为precision = 20
ini_set('precision', 20);
到您的 PHP 应用程序php_value precision 20
到应用程序的 .htaccess 或虚拟主机文件又快又脏,现在似乎可以工作:
$sJSON = preg_replace('/:(\d+)/', ':"${1}"', $sJSON);
我使用它,它几乎工作得很好。
json_decode(preg_replace('/("\w+"):(\d+)/', '\\1:"\\2"', $jsonString), true)
当包含地理数据时,json 会中断,例如。{"lat":54.2341}
结果是"lat":"54".2341
解决方案:
$json = preg_replace('/("\w+"):(\d+)(.\d+)?/', '\\1:"\\2\\3"', $json);
这(preg_replace('/("\w+"):(\d+)(.\d+)?/', '\\1:"\\2\\3"', $json);)
对我有用(用于解析来自 facebook api 的结果)
PHP 的一个主要疏忽是浏览器不会阻塞以 BigInt(64 位)开头的整数,但在此之前(53 位)。当 JSON 不支持 BigInt 时,将 BigInt 引入现代浏览器并没有多大帮助。所以我正在努力解决这个问题。
我的方法是处理解码后的数组(在可能将其重新编码为字符串之前):
function fix_large_int(&$value)
{
if (is_int($value) && $value > 9007199254740991)
$value = strval($value);
}
$json_arr = json_decode($json_str, flags: JSON_BIGINT_AS_STRING | JSON_OBJECT_AS_ARRAY);
echo('before: ' . json_encode($json_arr) . '<br />' . PHP_EOL);
array_walk_recursive($json_arr, 'fix_large_int');
echo('after: ' . json_encode($json_arr) . '<br />' . PHP_EOL);
数字 9007199254740991 是 JavaScript 的 Number.MAX_SAFE_INTEGER 值。在这里阅读:https ://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Number/MAX_SAFE_INTEGER
(顺便说一句,我到了这里,因为 Twitter API 的stringify_ids
参数 for blocks/ids
andfriends/ids
对我不起作用。不过,我能找到的任何地方似乎都没有提到这一点。)