Maneira computacional mais eficiente de converter coordenadas cartesianas em geodésicas

8

Até onde eu entendo a literatura, existem várias maneiras de converter um conjunto de coordenadas cartesianas geoecêntricas em coordenadas geodésicas

Qual seria a maneira mais eficiente de converter coordenadas cartesianas em coordenadas geodésicas - o significado mais eficiente mais rápido (e mais direto) ao ser implementado em um computador?

oschrenk
fonte
1
Você precisa realizar conversões para alturas geodésicas arbitrárias ou apenas na superfície nominal do solo (alturas zero)?
whuber
1
A superfície do solo servirá por enquanto, mas também estou interessado em alturas geodésicas arbitrárias a longo prazo.
oschrenk

Respostas:

4

Depende dos seus requisitos de precisão. Uma iteração do Heiskanen é eficiente, mas são necessárias três iterações para corresponder à precisão de uma única iteração do método de Bowring de 1985. Mesmo o algoritmo de Lin e Wang não pode corresponder à eficiência de Bowring, se as otimizações trigonométricas incluídas abaixo forem usadas. Portanto, para todo o desempenho, eu recomendaria o algoritmo de Bowring, de 1985.

   -- Based on B. R. Bowring's 1985 algorithm (single iteration)
   -----------------------------------------------------------------------------
   function ECEF_to_Geo(ECEF  : Vector3;
                        Datum : Datum_Id_Type) return Geographic_Type is
      Spheroid : Spheroid_Type := EARTH.DATUMS.Spheroid(Datum);
      x    : Meters   renames ECEF(1);
      y    : Meters   renames ECEF(2);
      z    : Meters   renames ECEF(3);
      a    : Meters   renames Models(Spheroid).Semi_Major_Axis;
      b    : Meters   renames Models(Spheroid).Semi_Minor_Axis;
      e2   : Unitless renames Models(Spheroid).Eccentricity_Squared;
      eb2  : Unitless renames Models(Spheroid).Second_Eccen_Squared;
      a2   : Scalar := a**2;
      d    : Meters := eb2*b;
      Ome2 : Unitless := 1.0 - e2;
      p2, p, r, tu, tu2, su3, cu3, Phi, Lam, tp, cp, sp, h : Scalar;
      Lat : Radians;
      Lon : Radians;
      Alt : Meters;
      Geo : Geographic_Type;
   begin -- ECEF_to_Geo
      if ((x = 0.0) and (y = 0.0)) then
         r   := abs(z);
         Phi := Scalar'copy_sign(Half_Pi, z);
         Lam := 0.0;
         h   := r - b;
      elsif (z = 0.0) then
         Phi := 0.0;
         Lam := arctan(y, x);
         p   := sqrt(x**2 + y**2);
         h   := p - a;
      else
         p2  := x**2 + y**2;
         p   := sqrt(p2);
         r   := sqrt(p2 + z**2);
         tu  := b*z*(1.0 + d/r)/(a*p);
         tu2 := tu**2;
         cu3 := (1.0/sqrt(1.0 + tu2))**3;
         su3 := cu3*tu2*tu;
         tp  := (z + d*su3)/(p - e2*a*cu3);
         Phi := arctan(tp);
         Lam := arctan(y, x);
         cp  := 1.0/sqrt(1.0 + tp**2);
         sp  := cp*tp;
         h   := p*cp + z*sp - a*sqrt(1.0 - e2*sp**2);
      end if;
      Lat := Radians(Phi);
      Lon := Radians(Lam);
      Alt := h;
      Geo := Make_Geo(Lat, Lon, Alt, Datum);
      return Geo;
   end ECEF_to_Geo;
Charles P. Gilbertson
fonte