提问人:TheMAn 提问时间:2/26/2015 更新时间:2/26/2015 访问量:1223
MySql 和浮点数或双裁剪我的数字,当我从 php 的每个查询更新它时
MySql and float or double crop my number when I update it per query from php
问:
我喜欢使用 InnoDB 以非常精确的方式将纬度和经度存储到我的 MySql 数据库中。但是,float 没有提供足够的内部小数位,所以我切换到 double。有点想知道自己,但 MySql 接受了大小高达 30 的 double,所以我使用了 double(30,27),因为只需要 3 个常规位置,其余的必须在逗号后面。
好吧,在到目前为止有效的 MySql 中,另一方面,我在 json_decode 上收到浮点数,当我回显它们时,逗号后面最多有 18 或 19 个位置。所以即使在这里,一切都如预期的那样。
但是当我构建一个更新查询来填充空的双字段(double 30/27)时,它只是用零填充所有数字,免除前 9 位数字。 或者有时违反规则,从 7 开始。数字,每行 9 秒。
例如,当我在 mysql 中更新 47.2608691999999877 – 无论是每个脚本还是每个 PhpMyAdmin,在点击保存按钮 47.260869199999999000000000000 出现在表格中时,47.26086919999999877000000000000 应该出现或
11.396251100000000633 更新到表中给了我一个 11.396251100000000000000000000
所以看起来它忽略了从 7 开始的可能位置。或者有时用 9 填充它,但在大多数情况下只有零。
任何人都可以给我一个解决这个问题的提示吗?
请记住,我也遇到了 PHPMyAdmin 的问题,但它是由 PHP 组成的。现在我不确定这是MySQL还是PHP问题。
谢谢
例如 我MYSql,我可以很容易地存储它,例如PHPMyAdmin:
答:
我不相信任何用于纬度/经度存储的浮点数,您几乎可以保证立即出现舍入错误。浮点数根本不那么准确。
您是否考虑过定点整数 ( 47.2608691999999877 通过乘以和除以 1000000000000000000000000 在需要显示/从输入返回时(甚至只是执行字符串操作进行显示)变得472608691999999877。
这种比例的数字应该相当舒适地适合 64 位整数的范围内(见鬼,你甚至可以得到小数点后 17 位,但仍然可以:P。
评论
您的脚本和 PHPMyAdmin 是在 PHP 上编写的,它使用精度来显示浮点数,但 mysql 和 php 尽可能准确地处理数字。
尝试更改.ini精度设置:http://php.net/manual/ru/ini.core.php#ini.precision
注意 DOUBLE(30, 27) 对 16-17 位有效数字有意义,然后失控了吗?
FLOAT 具有 24 位精度。这足以容纳大约 7 位有效数字。特别是,对于纬度和经度,这足以精确到 1.7 米(5.6 英尺)以内。对于大多数 lat/lng 应用来说,这已经足够了。因此,插入(从十进制转换为二进制)时存在舍入误差,读取(转换回十进制)时存在另一个错误并不重要。
DOUBLE 有 53 位精度,大约 16 位有效数字 -- 南北向或东西向 3.5 纳米!
DOUBLE(30, 27) -- 当 INSERTing 时,它说 (1) 四舍五入到小数点后 27 位,(2) 四舍五入到 53 位精度。阅读时,它会颠倒步骤,导致你遇到奇怪的混乱。
我从未见过在 FLOAT 或 DOUBLE 上使用 (M,N) 的有效需求。别这样。
For DECIMAL(M,N), you are storing exactly what will fit to N decimal places. For lat/lng purposes, consider DECIMAL(6,4) for latitude and (7,4) for longitude -- 16 meters (52 feet). Or, for more precision, (8,6) and (9,6) -- 16cm (6 inches).
Note further that a FLOAT takes 4 bytes (always), DOUBLE: 8, DECIMAL(6,4): 3, (7,4): 4, (8,6): 4, (9,6): 5. If you have billions of lat/lng entries, the bytes of storage adds up.
评论
DECIMAL