我正在搜索将Lambet72坐标转换为纬度/经度的算法。 因此,例如Lambert72坐标148990,169450必须转换为50.83546802746704,4.354415218851164,但大多数算法都有一点偏移(见附件)。
这是我发现的算法之一,它很接近,但仍有错误。
有人有更好的算法吗?
static void Lambert72ToLatLong(double x, double y, ref double longitude, ref double latitude)
{
const double n = 0.77164219;
const double F = 1.81329763;
const double thetaFudge = 0.00014204;
const double e = 0.08199189;
const double a = 6378388;
const double xDiff = 150000;
const double yDiff = 5400088.44;
const double theta0 = 0.07604294;
double xReal = xDiff-x;
double yReal = yDiff-y;
double rho = Math.Sqrt(xReal*xReal + yReal * yReal);
double theta = Math.Atan(xReal/-yReal);
longitude = (theta0 + (theta + thetaFudge) / n) * 180 / Math.PI;
latitude = 0;
for(int i=0; i<10; ++i)
{
latitude = (2 * Math.Atan(Math.Pow(F * a / rho, 1 / n) * Math.Pow((1 + e * Math.Sin(latitude)) / (1 - e * Math.Sin(latitude)), e / 2))) - Math.PI / 2;
}
latitude *= 180 / Math.PI;
}
答案 0 :(得分:0)
您必须更正
的值 xDiff
和
yDiff
正确的值应为
xDiff=149910;
yDiff=5400150;
您还必须更正
i<10
成为
i<5
用于计算纬度的for循环内部的。然后你会得到想要的结果。 希望这些帮助!
答案 1 :(得分:0)
您似乎正在尝试将Lambert72(比利时Dattum 72 LCC 3p)转换为 WGS84 GPS坐标。因此,在转换为球面纬度后 经度坐标,必须执行额外的步骤才能结束 使用WGS84坐标。这是C#中的替代代码,具有完整转换 Lambert72到WGS74的符合所需的十进制数,如 您可以轻松验证引用图像中显示的坐标。
static void Lambert72toWGS84latlong(double X, double Y)
{
double LongRef = 0.076042943; //
double nLamb = 0.7716421928;
double aCarre = Math.Pow(6378388.0,2.0);
double bLamb = 6378388.0 * (1.0 - (1.0 / 297.0));
double eCarre = (aCarre - Math.Pow(bLamb, 2.0)) / aCarre;
double KLamb = 11565915.812935;
double eLamb = Math.Sqrt(eCarre);
double eSur2 = eLamb / 2.0;
double Tan1 = (X - 150000.012) / (5400088.437 - Y);
double Lambda = LongRef + (1.0 / nLamb) * (0.000142043 + Math.Atan(Tan1));
double RLamb = Math.Sqrt(Math.Pow((X - 150000.012) , 2.0) + Math.Pow ((5400088.437 - Y) ,2.0));
double TanZDemi = Math.Pow((RLamb / KLamb),(1.0 / nLamb));
double Lati1 = 2.0 * Math.Atan(TanZDemi);
double eSin;
double Mult1, Mult2, Mult;
double LatiN, Diff;
double lat, lng ;
int i=0;
do
{
eSin = eLamb * Math.Sin(Lati1);
Mult1 = 1.0 - eSin;
Mult2 = 1.0 + eSin;
Mult = Math.Pow((Mult1 / Mult2) , (eLamb / 2.0));
LatiN = (Math.PI / 2.0) - (2.0 * (Math.Atan(TanZDemi * Mult)));
Diff = LatiN - Lati1;
Lati1 = LatiN;
i++;
} while (Math.Abs(Diff)> 0.0000000277777);
lat=LatiN;
lng=Lambda;
double SinLat = Math.Sin(lat);
double SinLng = Math.Sin(lng);
double CoSinLat = Math.Cos(lat);
double CoSinLng = Math.Cos(lng);
double dx = -125.8;
double dy = 79.9;
double dz = -100.5;
double da = -251.0;
double df = -0.000014192702;
double LWf = 1.0 / 297.0;
double LWa = 6378388.0;
double LWb = (1 - LWf) * LWa;
double LWe2 = (2.0 * LWf) - (LWf * LWf);
double Adb = 1.0 / (1.0 - LWf);
double Rn = LWa / Math.Sqrt(1.0 - LWe2 * SinLat * SinLat);
double Rm = LWa * (1 - LWe2) /Math.Pow((1.0 - LWe2 * lat * lat) ,1.5);
double DLat = -dx * SinLat * CoSinLng - dy * SinLat * SinLng + dz * CoSinLat;
DLat = DLat + da * (Rn * LWe2 * SinLat * CoSinLat) / LWa;
DLat = DLat + df * (Rm * Adb + Rn / Adb) * SinLat * CoSinLat;
DLat = DLat / (Rm + 0.0);
double DLng = (-dx * SinLng + dy * CoSinLng) / ((Rn + 0.0) * CoSinLat);
double Dh = dx * CoSinLat * CoSinLng + dy * CoSinLat * SinLng + dz * SinLat;
Dh = Dh - da * LWa / Rn + df * Rn * lat * lat / Adb;
double LatWGS84 = ((lat + DLat) * 180.0) / Math.PI;
double LngWGS84 = ((lng + DLng) * 180.0) / Math.PI;
MessageBox.Show("WGS84-Latitude=" + LatWGS84.ToString("###.######") +
"--WGS84 Longitude=" + LngWGS84.ToString("###.######"));
}
希望这些有用。