我在使用PHP json_encode函数时遇到一个问题。它将数字编码为字符串,例如
array('id' => 3)
变成
"{ ["id": "3", ...)
当js遇到这些值时,它将它们解释为字符串,并且对其执行数字操作失败。有谁知道防止json_encode
数字编码为字符串的方法?谢谢!
我在使用PHP json_encode函数时遇到一个问题。它将数字编码为字符串,例如
array('id' => 3)
变成
"{ ["id": "3", ...)
当js遇到这些值时,它将它们解释为字符串,并且对其执行数字操作失败。有谁知道防止json_encode
数字编码为字符串的方法?谢谢!
Answers:
我做了一个非常快速的测试:
$a = array(
'id' => 152,
'another' => 'test',
'ananother' => 456,
);
$json = json_encode($a);
echo $json;
如果我没记错的话,这似乎就像你所描述的那样?
我得到的输出:
{"id":152,"another":"test","ananother":456}
因此,在这种情况下,整数尚未转换为字符串。
尽管如此,这可能取决于我们使用的PHP版本:根据PHP版本,已经纠正了一些与json_encode相关的错误...
此测试已使用PHP 5.2.6进行;我在PHP 5.2.9和5.3.0中得到了同样的东西;我没有另一个5.2.x版本可以测试,尽管:-(
您正在使用哪个版本的PHP?还是您的测试用例比您发布的示例更复杂?
也许有关http://bugs.php.net/的一个错误报告?例如,错误#40503:json_encode整数转换与PHP不一致?
也许Bug#38680也可能引起您的兴趣,顺便说一句?
请注意,自PHP 5.3.3起,有一个用于自动转换数字的标志(在PHP 5.3.0中添加了options参数):
$arr = array( 'row_id' => '1', 'name' => 'George' );
echo json_encode( $arr, JSON_NUMERIC_CHECK ); // {"row_id":1,"name":"George"}
JSON_NUMERIC_CHECK
尝试通过尝试解析字符串来自动猜测字符串是否为数字。如果您考虑一下,那将是非常不可靠的。它将所有看起来数字的属性转换为数字(不仅是所需的数字),并且仅当它们看起来像数字时才这样做。如果不是不安全的话,那至少是摇晃的。使用产生的JSON的代码可能依赖于一种类型。如果这些期望得不到满足,就会发生奇怪的事情。如果您关心良好做法和安全性,则应该有选择地转换所需的值。
同样,我正在从数据库(PostgreSQL)读取数据,而一切都是字符串。我们遍历每一行,并用它来完成最终的结果数组,所以我使用了
$result_arr[] = array($db_row['name'], (int)$db_row['count']);
在循环中强制将其设为整数值。当我这样做json_encode($result_arr)
,现在,它正确格式化为一个数字。这使您可以控制来自数据库的数字是多少。
编辑:
该json_encode()
函数还具有使用该JSON_NUMERIC_CHECK
标志作为它的第二个参数来动态执行此操作的能力。您需要谨慎使用它,尽管如文档中此用户示例所示(复制如下):http : //uk3.php.net/manual/en/function.json-encode.php#106641
<?php
// International phone number
json_encode(array('phone_number' => '+33123456789'), JSON_NUMERIC_CHECK);
?>
然后,您将获得以下JSON:
{"phone_number":33123456789}
json_encode
功能。这是最正确的答案,但是要小心,因为JSON_NUMERIC_CHECK
还会转换电话号码和其他数字字符串值,这可能导致前导零或“ +”的问题。我建议在数据库读取功能中更正此问题。
尝试
$arr = array('var1' => 100, 'var2' => 200);
$json = json_encode( $arr, JSON_NUMERIC_CHECK);
但这仅适用于PHP 5.3.3。查看此PHP json_encode更改日志 http://php.net/manual/zh/function.json-encode.php#refsect1-function.json-encode-changelog
我遇到同样的问题(PHP-5.2.11 / Windows)。我正在使用此解决方法
$json = preg_replace( "/\"(\d+)\"/", '$1', $json );
它用数字本身替换用引号引起来的所有(非负整数)数字(“ 42”变为“ 42”)。
另请参见PHP手册中的此注释。
$json_array = json_encode($some_array, false);
因此false参数告诉PHP不要执行对象转换。
json_encode(array(-1=>'que', '0'=>'-1'))
$this->data = preg_replace("/\" *?: *?(\d+)/", '":"$1"', $this->data);
以下测试确认将类型更改为字符串会导致json_encode()返回一个数字作为JSON字符串(即,用双引号引起来)。使用settype(arr [“ var”],“ integer”)或settype($ arr [“ var”],“ float”)进行修复。
<?php
class testclass {
public $foo = 1;
public $bar = 2;
public $baz = "Hello, world";
}
$testarr = array( 'foo' => 1, 'bar' => 2, 'baz' => 'Hello, world');
$json_obj_txt = json_encode(new testclass());
$json_arr_txt = json_encode($testarr);
echo "<p>Object encoding:</p><pre>" . $json_obj_txt . "</pre>";
echo "<p>Array encoding:</p><pre>" . $json_arr_txt . "</pre>";
// Both above return ints as ints. Type the int to a string, though, and...
settype($testarr["foo"], "string");
$json_arr_cast_txt = json_encode($testarr);
echo "<p>Array encoding w/ cast:</p><pre>" . $json_arr_cast_txt . "</pre>";
?>
为了完整性(因为我还不能添加评论),让我也将此详细信息添加为另一个答案:
(编辑:要在意识到源数据(即,在OP的情况下,是数据库结果集)可能是问题之后(通过将数字列作为字符串返回)来读取,而json_encode()实际上不是问题的根源)
这两个“ mysql_fetch_array ”的手册页:
返回与获取的行相对应的字符串数组,
...和“ mysql_ fetch_ row ”:
返回与获取的行相对应的字符串的数字数组
明确指出:返回数组中的条目将是字符串。
(我在phpBB2中使用DB类(是的,我已经过时了!),该类的“ sql_fetchrow()”方法使用“ mysql_fetch_array()”)
没有意识到这一点,我最终还是找到了这个问题,并理解了这个问题!:)
正如Pascal Martin在其后续评论中所述,我相信一种解决方案可以从源头解决“不正确的类型”问题(即通过使用“ mysql_field_type() ”函数并在获取后立即进行转换),(或一般而言,其他提取方法(例如“对象”?))会更好。
所以Pascal MARTIN在这里没有得到足够的认可。对于具有数百个服务器端功能的现有项目,无法在每个JSON返回上检查数字值。
我用php-mysqlnd替换了php-mysql,问题消失了。数字是数字,字符串是字符串,布尔值是布尔值。
将值强制转换为int或float似乎可以解决问题。例如:
$coordinates => array(
(float) $ap->latitude,
(float) $ap->longitude
);
如果出现任何问题,您可以使用(int)!它将正常工作。
json_encode以JSON格式序列化一些数据结构,以通过网络发送。因此,所有内容均为字符串类型。就像当您从$ _POST或$ _GET接收到某些参数时一样。
如果必须对发送的值进行数字运算,只需先将它们转换为int(使用PHP中的intval()函数或Javascript中的parseInt()),然后执行这些运算即可。
好吧,PHP json_encode()返回一个字符串。
您可以在js代码中使用parseFloat()或parseInt():
parseFloat('122.5'); // returns 122.5
parseInt('22'); // returns 22
parseInt('22.5'); // returns 22