经纬度纠偏

民用地图不能反映真实经纬度坐标,存在一定偏差,感兴趣的一定知道为什么,不做过多解释

经纬度纠偏工具包,全文只有代码~~~

  • mapbar地图纠偏
  • 百度地图纠偏
  • 火星坐标纠偏
  • 经纬度距离计算
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
using System;
namespace L.MapUtil
{
class LngLatUtil
{
#region cmpte 2point distance
private const double ParaE1 = 6.69438499958795E-03;//椭球体第一偏心率
private const double Parak0 = 1.57048687472752E-07;//有关椭球体的常量
private const double Parak1 = 5.05250559291393E-03;//有关椭球体的常量
private const double Parak2 = 2.98473350966158E-05;//有关椭球体的常量
private const double Parak3 = 2.41627215981336E-07;//有关椭球体的常量
private const double Parak4 = 2.22241909461273E-09;//有关椭球体的常量
private const double ParaC = 6399596.65198801;//极点子午圈曲率半径
private const double EARTH_RADIUS = 6378.137;//地球半径
private void ComputeXYGeo(double x, double y, ref double B, ref double L, double center, int n)
{
double y1, bf, e, se, v, t, N, nl, vt, yn, t2, cbf;
y1 = y - 500000 - 1000000 * n;//减去带号
e = Parak0 * x;
se = Math.Sin(e);
bf = e + Math.Cos(e) * (Parak1 * se - Parak2 * Math.Pow(se, 3) + Parak3 * Math.Pow(se, 5) - Parak4 * Math.Pow(se, 7));
t = Math.Tan(bf);
nl = ParaE1 * Math.Pow(Math.Cos(bf), 2);
v = Math.Sqrt(1 + nl);
N = ParaC / v;
yn = y1 / N;
vt = Math.Pow(v, 2) * t;
t2 = Math.Pow(t, 2);
B = bf - vt * Math.Pow(yn, 2) / 2.0 + (5.0 + 3.0 * t2 + nl - 9.0 * nl * t2) * vt * Math.Pow(yn, 4) / 24.0 - (61.0 + 90.0 * t2 + 45 * Math.Pow(t2, 2)) * vt * Math.Pow(yn, 6) / 720.0;
cbf = 1 / Math.Cos(bf);
L = cbf * yn - (1.0 + 2.0 * t2 + nl) * cbf * Math.Pow(yn, 3) / 6.0 + (5.0 + 28.0 * t2 + 24.0 * Math.Pow(t2, 2) + 6.0 * nl + 8.0 * nl * t2) * cbf * Math.Pow(yn, 5) / 120.0 + center;
}
private static double rad(double d)
{
return d * Math.PI / 180.0;
}
public static double GetDistance(double lat1, double lng1, double lat2, double lng2)
{
double radLat1 = rad(lat1);
double radLat2 = rad(lat2);
double a = radLat1 - radLat2;
double b = rad(lng1) - rad(lng2);
double s = 2 * Math.Asin(Math.Sqrt(Math.Pow(Math.Sin(a / 2), 2) +
Math.Cos(radLat1) * Math.Cos(radLat2) * Math.Pow(Math.Sin(b / 2), 2)));
s = s * EARTH_RADIUS;
s = Math.Round(s * 10000) / 10000;
return s;
}
#endregion
#region 2_mapbar
public void gps2mapbar(double in_lng, double in_lat, out double out_lng, out double out_lat)
{
double x = in_lng * 100000 % 36000000;
double y = in_lat * 100000 % 36000000;
var _X = (int)(((Math.Cos(y / 100000)) * (x / 18000)) + ((Math.Sin(x / 100000)) * (y / 9000)) + x);
var _Y = (int)(((Math.Sin(y / 100000)) * (x / 18000)) + ((Math.Cos(x / 100000)) * (y / 9000)) + y);
out_lng = _X / 100000.0;
out_lat = _Y / 100000.0;
}
#endregion
#region 2_mars
double casm_rr,casm_x1,casm_y1,casm_x2,casm_y2,casm_f;
uint casm_t1,casm_t2;
double yj_sin2(double x)
{
double tt;
double ss;
int ff;
double s2;
int cc = 0;
ff = 0;
if (x < 0)
{
x = -x;
ff = 1;
}
cc = (int)(x / 6.28318530717959);
tt = x - cc * 6.28318530717959;
if (tt > 3.1415926535897932)
{
tt = tt - 3.1415926535897932;
if (ff == 1)
ff = 0;
else if (ff == 0)
ff = 1;
}
x = tt;
ss = x;
s2 = x;
tt = tt * tt;
s2 = s2 * tt;
ss = ss - s2 * 0.166666666666667;
s2 = s2 * tt;
ss = ss + s2 * 8.33333333333333E-03;
s2 = s2 * tt;
ss = ss - s2 * 1.98412698412698E-04;
s2 = s2 * tt;
ss = ss + s2 * 2.75573192239859E-06;
s2 = s2 * tt;
ss = ss - s2 * 2.50521083854417E-08;
if (ff == 1)
ss = -ss;
return ss;
}
double Transform_yj5(double x, double y)
{
double tt;
tt = 300 + 1 * x + 2 * y + 0.1 * x * x + 0.1 * x * y + 0.1 * Math.Sqrt(Math.Sqrt(x * x));
tt = tt + (20 * yj_sin2(18.849555921538764 * x) + 20 * yj_sin2(6.283185307179588 * x)) * 0.6667;
tt = tt + (20 * yj_sin2(3.141592653589794 * x) + 40 * yj_sin2(1.047197551196598 * x)) * 0.6667;
tt = tt + (150 * yj_sin2(0.2617993877991495 * x) + 300 * yj_sin2(0.1047197551196598 * x)) * 0.6667;
return tt;
}
double Transform_yjy5(double x, double y)
{
double tt;
tt = -100 + 2 * x + 3 * y + 0.2 * y * y + 0.1 * x * y + 0.2 * Math.Sqrt(Math.Sqrt(x * x));
tt = tt + (20 * yj_sin2(18.849555921538764 * x) + 20 * yj_sin2(6.283185307179588 * x)) * 0.6667;
tt = tt + (20 * yj_sin2(3.141592653589794 * y) + 40 * yj_sin2(1.047197551196598 * y)) * 0.6667;
tt = tt + (160 * yj_sin2(0.2617993877991495 * y) + 320 * yj_sin2(0.1047197551196598 * y)) * 0.6667;
return tt;
}
double Transform_jy5(double x, double xx)
{
double n;
double a;
double e;
a = 6378245;
e = 0.00669342;
n = Math.Sqrt(1 - e * yj_sin2(x * 0.0174532925199433) * yj_sin2(x * 0.0174532925199433));
n = (xx * 180) / (a / n * Math.Cos(x * 0.0174532925199433) * 3.1415926);
return n;
}
double Transform_jyj5(double x, double yy)
{
double m;
double a;
double e;
double mm;
a = 6378245;
e = 0.00669342;
mm = 1 - e * yj_sin2(x * 0.0174532925199433) * yj_sin2(x * 0.0174532925199433);
m = (a * (1 - e)) / (mm * Math.Sqrt(mm));
return (yy * 180) / (m * 3.1415926);
}
double random_yj()
{
int t;
int casm_a;
int casm_c;
casm_a = 314159269;
casm_c = 453806245;
casm_rr = casm_a * casm_rr + casm_c;
t = (int)(casm_rr / 2);
casm_rr = casm_rr - t * 2;
casm_rr = casm_rr / 2;
return (casm_rr);
}
void IniCasm(uint w_time, uint w_lng, uint w_lat)
{
int tt;
casm_t1 = w_time;
casm_t2 = w_time;
tt = (int)(w_time / 0.357);
casm_rr = w_time - tt * 0.357;
if (w_time == 0)
casm_rr = 0.3;
casm_x1 = w_lng;
casm_y1 = w_lat;
casm_x2 = w_lng;
casm_y2 = w_lat;
casm_f = 3;
}
uint wgtozhlb(int wg_flag, uint wg_lng, uint wg_lat, int wg_heit, int wg_week, uint wg_time, ref uint china_lng, ref uint china_lat)
{
double x_add;
double y_add;
double h_add;
double x_l;
double y_l;
double casm_v;
double t1_t2;
double x1_x2;
double y1_y2;
if (wg_heit > 5000)
{
china_lng = 0;
china_lat = 0;
return 0xFFFF95FF;
}
x_l = wg_lng;
x_l = x_l / 3686400.0;
y_l = wg_lat;
y_l = y_l / 3686400.0;
if (x_l < 72.004)
{
china_lng = 0;
china_lat = 0;
return 0xFFFF95FF;
}
if (x_l > 137.8347)
{
china_lng = 0;
china_lat = 0;
return 0xFFFF95FF;
}
if (y_l < 0.8293)
{
china_lng = 0;
china_lat = 0;
return 0xFFFF95FF;
}
if (y_l > 55.8271)
{
china_lng = 0;
china_lat = 0;
return 0xFFFF95FF;
}
if (wg_flag == 0)
{
IniCasm(wg_time, wg_lng, wg_lat);
china_lng = wg_lng;
china_lat = wg_lat;
return 0x00000000;
}
casm_t2 = wg_time;
t1_t2 = (double)(casm_t2 - casm_t1) / 1000.0;
if (t1_t2 <= 0)
{
casm_t1 = casm_t2;
casm_f = casm_f + 1;
casm_x1 = casm_x2;
casm_f = casm_f + 1;
casm_y1 = casm_y2;
casm_f = casm_f + 1;
}
else
{
if (t1_t2 > 120)
{
if (casm_f == 3)
{
casm_f = 0;
casm_x2 = wg_lng;
casm_y2 = wg_lat;
x1_x2 = casm_x2 - casm_x1;
y1_y2 = casm_y2 - casm_y1;
casm_v = Math.Sqrt(x1_x2 * x1_x2 + y1_y2 * y1_y2) / t1_t2;
if (casm_v > 3185)
{
china_lng = 0;
china_lat = 0;
return (0xFFFF95FF);
}
}
casm_t1 = casm_t2;
casm_f = casm_f + 1;
casm_x1 = casm_x2;
casm_f = casm_f + 1;
casm_y1 = casm_y2;
casm_f = casm_f + 1;
}
}
x_add = Transform_yj5(x_l - 105, y_l - 35);
y_add = Transform_yjy5(x_l - 105, y_l - 35);
h_add = wg_heit;
x_add = x_add + h_add * 0.001 + yj_sin2(wg_time * 0.0174532925199433) + random_yj();
y_add = y_add + h_add * 0.001 + yj_sin2(wg_time * 0.0174532925199433) + random_yj();
china_lng = (uint)((x_l + Transform_jy5(y_l, x_add)) * 3686400);
china_lat = (uint)((y_l + Transform_jyj5(y_l, y_add)) * 3686400);
return (0x00000000);
}
public bool gps2mars(double in_lat, double in_lon, out double out_lat, out double out_lon)
{
const double BASE = 3686400.0;
uint lon, lat;
lon = (uint)(in_lon * BASE);
lat = (uint)(in_lat * BASE);
uint ret = wgtozhlb(1, lon, lat, 0, 0, 0, ref lon, ref lat);
out_lon = lon / BASE;
out_lat = lat / BASE;
return (0 == ret);
}
#endregion
#region 2_baidu
const double x_pi = 3.14159265358979324 * 3000.0 / 180.0;
public void gps2baidu(double in_lat, double in_lng, out double out_lat, out double out_lng)
{
double lat = 0, lng = 0, _lat = 0, _lng = 0;
gps2mars(in_lat, in_lng, out lat, out lng);
bd_encrypt(lat, lng, out _lat, out _lng);
out_lat = _lat;
out_lng = _lng;
}
private void bd_encrypt(double gg_lat, double gg_lon, out double bd_lat, out double bd_lon)
{
double x = gg_lon, y = gg_lat;
double z = Math.Sqrt(x * x + y * y) + 0.00002 * Math.Sin(y * x_pi);
double theta = Math.Atan2(y, x) + 0.000003 * Math.Cos(x * x_pi);
bd_lon = z * Math.Cos(theta) + 0.0065;
bd_lat = z * Math.Sin(theta) + 0.006;
}
#endregion
}
}
坚持原创技术分享,您的支持将鼓励我继续创作!
分享