J'essaie de trouver la distance entre deux points (pour lesquels j'ai des latitudes et des longitudes) en utilisant la technique décrite ici à Calculer la distance entre deux points de latitude-longitude? (Formule Haversine)
Les codes sont comme ci-dessous Javascript:
var R = 6371; // Radius of the earth in km
var dLat = (lat2-lat1).toRad(); // Javascript functions in radians
var dLon = (lon2-lon1).toRad();
var a = Math.sin(dLat/2) * Math.sin(dLat/2) +
Math.cos(lat1.toRad()) * Math.cos(lat2.toRad()) *
Math.sin(dLon/2) * Math.sin(dLon/2);
var c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1-a));
var d = R * c; // Distance in km
Mais quand j'essaye de l'implémenter, une erreur apparaît en disant Uncaught TypeError: Object 20 has no Method 'toRad'
.
Ai-je besoin d'une bibliothèque spéciale ou de quelque chose pour faire fonctionner .toRad ()? parce que ça semble bousiller sur la deuxième ligne.
Il vous manque une déclaration de fonction.
Dans dans ce castoRad()
doit d'abord être défini comme:
/** Converts numeric degrees to radians */
if (typeof(Number.prototype.toRad) === "undefined") {
Number.prototype.toRad = function() {
return this * Math.PI / 180;
}
}
selon le segment de code tout au en bas de la page
Ou dans mon cas, cela n'a pas fonctionné. C'est peut-être parce que j'avais besoin d'appeler toRad () dans jquery. Je ne suis pas sûr à 100%, j'ai donc fait ceci:
function CalcDistanceBetween(lat1, lon1, lat2, lon2) {
//Radius of the earth in: 1.609344 miles, 6371 km | var R = (6371 / 1.609344);
var R = 3958.7558657440545; // Radius of earth in Miles
var dLat = toRad(lat2-lat1);
var dLon = toRad(lon2-lon1);
var a = Math.sin(dLat/2) * Math.sin(dLat/2) +
Math.cos(toRad(lat1)) * Math.cos(toRad(lat2)) *
Math.sin(dLon/2) * Math.sin(dLon/2);
var c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1-a));
var d = R * c;
return d;
}
function toRad(Value) {
/** Converts numeric degrees to radians */
return Value * Math.PI / 180;
}
J'avais besoin de calculer beaucoup de distances entre les points pour mon projet, alors j'ai continué et j'ai essayé d'optimiser le code, j'ai trouvé ici. En moyenne, dans différents navigateurs, ma nouvelle implémentation fonctionne presque 3 fois plus vite que celle mentionnée ici.
function distance(lat1, lon1, lat2, lon2) {
var R = 6371; // Radius of the earth in km
var dLat = (lat2 - lat1) * Math.PI / 180; // deg2rad below
var dLon = (lon2 - lon1) * Math.PI / 180;
var a =
0.5 - Math.cos(dLat)/2 +
Math.cos(lat1 * Math.PI / 180) * Math.cos(lat2 * Math.PI / 180) *
(1 - Math.cos(dLon))/2;
return R * 2 * Math.asin(Math.sqrt(a));
}
Vous pouvez jouer avec mon jsPerf (qui a été considérablement amélioré grâce à Bart) et voir les résultats ici .
Pourquoi ne pas simplifier l'équation ci-dessus et même quelques calculs?
Math.sin(dLat/2) * Math.sin(dLat/2) = (1.0-Math.cos(dLat))/2.0
Math.sin(dLon/2) * Math.sin(dLon/2) = (1.0-Math.cos(dLon))/2.0
J'avais le même problème .. en regardant la réponse de Casper, je viens de faire une solution rapide: Ctrl+H
(Rechercher et remplacer), remplacé toutes les instances de .toRad()
par * Math.PI / 180
. Cela a fonctionné pour moi.
Aucune idée sur les vitesses de performance du navigateur, etc., cependant. Mon cas d'utilisation n'a besoin de cela que lorsque l'utilisateur clique sur une carte.
J'ai changé deux ou trois choses:
if (!Number.prototype.toRad || (typeof(Number.prototype.toRad) === undefined)) {
et, j'ai remarqué qu'il n'y avait aucune vérification pour le arguments
. Vous devez vous assurer que les arguments sont définis ET probablement faire une parseInt(arg, 10)
/parseFloat
là-bas.