我正在使用地图数据,Latitude/Longitude
扩展到8位小数。例如:
Latitude 40.71727401
Longitude -74.00898606
我在Google document中看到了 使用:
lat FLOAT( 10, 6 ) NOT NULL,
lng FLOAT( 10, 6 ) NOT NULL
然而,他们的小数位只有6
我应该使用FLOAT(10, 8)
还是有其他方法来考虑存储这些数据,这样才能准确。它将与地图计算一起使用。谢谢!
答案 0 :(得分:504)
DECIMAL是用于精确算术的MySQL数据类型。与FLOAT不同,它的精度对于任何数量的大小都是固定的,因此通过使用它而不是FLOAT,可以避免在进行某些计算时出现精度错误。如果您只是在不计算的情况下存储和检索数字,那么在实践中FLOAT是安全的,尽管使用DECIMAL没有任何害处。通过计算FLOAT仍然大部分没问题,但绝对确定8d.p.精度你应该使用DECIMAL。
纬度范围从-90到+90(度),所以DECIMAL(10,8)就可以了,但经度范围从-180到+180(度),所以你需要DECIMAL(11,8)。第一个数字是存储的总位数,第二个数字是小数点后面的数字。
简而言之:lat DECIMAL(10, 8) NOT NULL, lng DECIMAL(11, 8) NOT NULL
This解释了MySQL如何使用浮点数据类型。
答案 1 :(得分:13)
此外,您会看到float
值已四舍五入。
// e.g: given values 41.0473112,29.0077011 float(11,7) | decimal(11,7) --------------------------- 41.0473099 | 41.0473112 29.0077019 | 29.0077011
答案 2 :(得分:6)
您可以将数据类型设置为有符号整数。将坐标存储到SQL时,可以设置为lat * 10000000和long * 10000000。当您选择距离/半径时,您将存储坐标划分为10000000.我用300K行测试它,查询响应时间很好。 (2 x 2.67GHz CPU,2 GB RAM,MySQL 5.5.49)
答案 3 :(得分:2)
使用小数列类型进行迁移
$table->decimal('latitude', 10, 8);
$table->decimal('longitude', 11, 8);
有关更多信息,see可用的列类型
答案 4 :(得分:1)
在我的情况下,最好的方法是将坐标保存为DOUBLE。
> python prog1.py | python prog2.py
它将保存整个值而不进行任何舍入。
如果您需要对值进行舍入,我的建议是此处理是在数据的原点完成的,例如在UI中。
答案 5 :(得分:1)
自从问这个问题以来,MySQL现在已经支持空间数据类型。因此,当前接受的答案是正确的,但是如果您要查找其他功能(例如查找给定面内的所有点),则可以使用POINT数据类型。
Checkout the Mysql Docs on Geospatial data types和spatial analysis functions
答案 6 :(得分:1)
CREATE TABLE your_table_name (
lattitude REAL,
longitude REAL
)
还可以考虑在您的经纬度声明中添加进一步的验证:
CREATE TABLE your_table_name (
lattitude REAL CHECK(lattitude IS NULL OR (lattitude >= -90 AND lattitude <= 90)),
longitude REAL CHECK(longitude IS NULL OR (longitude >= -180 AND longitude <= 180))
)
说明: https://dev.mysql.com/doc/refman/5.7/en/floating-point-types.html
答案 7 :(得分:0)
在rails上使用migrate ruby
class CreateNeighborhoods < ActiveRecord::Migration[5.0]
def change
create_table :neighborhoods do |t|
t.string :name
t.decimal :latitude, precision: 15, scale: 13
t.decimal :longitude, precision: 15, scale: 13
t.references :country, foreign_key: true
t.references :state, foreign_key: true
t.references :city, foreign_key: true
t.timestamps
end
end
end
答案 8 :(得分:0)
我认为在MySQL中存储Lat / Lng的最好方法是使用带有SPATIAL索引的POINT列(2D数据类型)。
CREATE TABLE `cities` (
`zip` varchar(8) NOT NULL,
`country` varchar (2) GENERATED ALWAYS AS (SUBSTRING(`zip`, 1, 2)) STORED,
`city` varchar(30) NOT NULL,
`centre` point NOT NULL,
PRIMARY KEY (`zip`),
KEY `country` (`country`),
KEY `city` (`city`),
SPATIAL KEY `centre` (`centre`)
) ENGINE=InnoDB;
INSERT INTO `cities` (`zip`, `city`, `centre`) VALUES
('CZ-10000', 'Prague', POINT(50.0755381, 14.4378005));