16 votos

¿De dónde procede el radio de la Tierra por defecto en ST_Distance_Sphere?

MySQL dice en la documentación de ST_Distance_Sphere

Los cálculos utilizan una Tierra esférica y un radio configurable. El argumento opcional radio debe indicarse en metros. Si se omite, el El radio por defecto es de 6.370.986 metros. Si el argumento radio está presente pero no es positivo, se producirá un ER_WRONG_ARGUMENTS se produce un error.

PostGIS dice en los documentos de ST_Distance_Sphere (aunque los documentos ya no son precisos )

Utiliza una Tierra esférica y un radio de 6370986 metros.

¿De dónde han sacado los 6.370.986 metros por defecto? WGS84 dice que el radio del eje mayor es 6.378.137,0 m. PostGIS, que ahora utiliza un Radio Medio, utiliza esencialmente 6371008.

En en el código

#define WGS84_MAJOR_AXIS 6378137.0
#define WGS84_INVERSE_FLATTENING 298.257223563
#define WGS84_MINOR_AXIS (WGS84_MAJOR_AXIS - WGS84_MAJOR_AXIS / WGS84_INVERSE_FLATTENING)
#define WGS84_RADIUS ((2.0 * WGS84_MAJOR_AXIS + WGS84_MINOR_AXIS ) / 3.0)

es decir

-- SELECT 6378137.0 - 6378137.0 / 298.257223563;
WGS84_MINOR_AXIS = 6356752.314245179498
-- SELECT ( 2.0 * 6378137.0 + ( 6378137.0 - 6378137.0 / 298.257223563) ) / 3.0;
WGS84_RADIUS = 6371008.771415059833

Las versiones más recientes son mucho menos eficientes, más complejas y utilizan Pro4j, pero parecen hacer lo mismo.

¿Y de dónde sale 6370986?

22voto

jlehenbauer Puntos 7749

Ok, esto es hilarriuusss . He localizado esto. En una vieja copia de lwgeom/lwgeom_spheroid.c en PostGIS 1.0.0rc4 puedes ver esto,

/*
 * This algorithm was taken from the geo_distance function of the 
 * earthdistance package contributed by Bruno Wolff III.
 * It was altered to accept GEOMETRY objects and return results in
 * meters.
 */
PG_FUNCTION_INFO_V1(LWGEOM_distance_sphere);
Datum LWGEOM_distance_sphere(PG_FUNCTION_ARGS)
{
        const double EARTH_RADIUS = 6370986.884258304;

Pasando a los documentos de earthdistance encontrarás esto:

Tenga en cuenta que, a diferencia de la parte del módulo basada en cubos, aquí las unidades están conectadas de forma fija: si cambia la unidad earth() no afectará a los resultados de este operador.

Y ese número fijo: EARTH_RADIUS puede verse aquí

/* Earth's radius is in statute miles. */
static const double EARTH_RADIUS = 3958.747716;

Así que puedes hacer una simple.

EARTH_RADIUS * MILES_TO_METERS = EARTH_RADIUS_IN_METERS
 3958.747716 * 1609.344        = 6370986.884258304

Y usted tiene su 6370986.884258304 . Por supuesto, basta con truncarlo y almacenarlo en un long porque por qué no.

Así que en esencia, el radio en MySQL era extraído de una copia perezosa de PostGIS que convertir un radio en millas a metros de una oscura constante de un módulo aleatorio de PostgreSQL de hace 20 años .

earth_distance es un módulo pre-PostGIS de Bruce Momjian. Por la presente proclamo 6370986 la Constante Bmomjian: una buena aproximación de la Tierra en metros para satisfacer MySQL. Aunque tal vez no por mucho tiempo.

i-Ciencias.com

I-Ciencias es una comunidad de estudiantes y amantes de la ciencia en la que puedes resolver tus problemas y dudas.
Puedes consultar las preguntas de otros usuarios, hacer tus propias preguntas o resolver las de los demás.

Powered by:

X