座標変換
座標変換を、要するに、特定のモデルによって座標他の座標に座標変化を言う;変換、異なる変換モデルを使用する必要性、例えばブルサ三次元空間の7つのパラメータ、モローホプキンスモデル。基準面3次元空間、四つのパラメータ、多項式フィットピアモデル。この論文では、主な用途ブルサ七パラメータモデルは、座標変換。
座標変換
ブルサモデル(7パラメータモデル)
詳細についてはウィキペディアを参照してください。 https://baike.baidu.com/item/%E4%B8%83%E5%8F%82%E6%95%B0
プログラムの実現
1.書き込みデータ変換クラス
分と秒のさまざまな形式が変換ラジアンとして計算し、そして結紮フォーマットにアークの分と秒の最終的な方法です。
システム使用; System.Collections.Genericを使用して、 System.Linqのを使用して、 System.Textのを使用して、 使用System.Threading.Tasks; System.Text.RegularExpressionsを使用して、 名前空間CoordTF { クラスDataCnversion { #region /// <まとめ> // /データは分と秒(□。□□□□)の全体に、フォーマットの形式合字 /// </要約> /// <PARAM NAME = "oldCoord">測地</ PARAM> /// <PARAM名= " dataFormat「>データ形式</ PARAM> /// <戻り値> </戻り> 公共ダブルDataFormatting(oldCoord文字、文字列のdataFormat) { ダブルnewCoord = 0.00。 スイッチング(データ形式) { ケース"度°分"秒"": newCoord = DMSA_RAD(oldCoord)。 ブレーク; 場合"度:分:秒": newCoord = DMSB_RAD(oldCoord)。 ブレーク; ケース"度:分": 破ります。 場合"度": newCoord = D_RAD(oldCoord)。 ブレーク; 場合"度分秒连写": newCoord = DMSLX_RAD(oldCoord)。 ブレーク; } newCoordを返します。 } #endregion ラジアンにそれぞれ度を形成#region ダブルD、M、S。 /// <要約> ///度°分'秒"格式转弧度 /// </要約> /// <PARAM NAME =" DMS ">格式为XX°XX' XX.XX "</ PARAM> /// <戻る> </戻り> 公共ダブルDMSA_RAD(文字列DMS) { ダブルラジアン。 VAR newdで= dms.Substring(0、dms.IndexOf( "°")); VAR NEWM = dms.Substring(dms.IndexOf( "°")+ 1、dms.IndexOf( "'") - 3)。 VARニュース= dms.Substring(dms.IndexOf( "'")+ 1、dms.Length-dms.IndexOf( "'") - 2)。 RAD =(double.Parse(newdで)+ double.Parse(NEWM)/ 60 +ダブル。 パース(ニュース)/ 3600)* にMath.PI / 180。 ラジアンを返します。 } /// <要約> ///度:分:秒の形式ラジアン /// </要約> /// <PARAM NAME = "DMS">フォーマット度:分:秒。</ param>の /// <戻り値> </戻ります> ダブルDMSB_RAD公開(文字列DMS) { ダブルRAD、 文字列[] = newDms dms.Split( ':'); [1] RAD =(double.Parse(newDms [0] .ToString())+ double.Parse(newDms .ToString())/ 60 + double.Parse(newDms [2] .ToString())/ 3600)*にMath.PI / 180; RADを返す; } /// <まとめ> ///結紮は分と秒(Xは度.xxxx)ラジアン /// </要約> /// <PARAM NAME = "DMS">形式のx。XXXX </ param>の /// <戻り値> </戻ります> 公共ダブルDMSLX_RAD(文字列DMS) { ダブルRAD; VAR = newDms double.Parse(DMS); D = Math.Floor(newDms); //度 VAR X =(newDms - D)×100; X =ダブル。解析(x.ToString( "N8")); M = Math.Floor(X); //点 Sの=(X - M)* 100; M / = 60; //第 S / = 3600; RAD =( D + M + S)/ 180 *(にMath.PI); //はラジアン RADを返す; } /// <まとめ> /// xx.xxxxフォーマット゜ラジアン /// </要約> /// <PARAM NAME = "DMS">角、フォーマット゜xx.xxxx </ PARAM> /// <>は<返し/リターン> 公共ダブルD_RAD(文字列DMS) { ダブルRAD。 = RAD(double.Parse(DMS)*にMath.PI / 180); RADを返す; } #endregion /// <まとめ> ///ラジアン回転角(xx.xxxxxx結紮フォーマット結果) /// </要約> /// <PARAM NAME = "RAD">ラジアン</ PARAM> /// <戻り値> </戻り> 公共ダブルRAD_DMS(文字列RAD) { ダブルDMS; VAR = newRad double.Parse(RAD); VAR D = newRad /にMath.PI * 180; // 度 VAR Dstrと= d.ToString( "N8"); D = double.Parse(Dstrと); VAR X = Math.Floor(D) ; VARのM =(D - X)* 60; //分 VAR MSTR = m.ToString( "N8")。 M = double.Parse(MSTR)。 VaRのF = Math.Floor(M)。 VAR S =(M - F)* 60。//秒 のvar SSTR = s.ToString( "N8")。 S = double.Parse(SSTR)。 DMS = X + F / 100 + S / 10000。 DMSを返します。 } } }
2.座標変換クラスを書きます
地球空間変換、ガウスSoid、計算の同じ座標系、ブルサ7計算変換パラメータ変化を含みます。
初心者のプログラミングを学ぶためにそこにしたい場合は、qunバックルああを学ぶ私たちのC / C ++の技術に来ることができる:フロント58,93は、C / C ++のチュートリアル内のシステム全体を送ること自由4,83-89を追っ!
システム使用; System.Collections.Genericを使用して、 System.Linqのを使用して、 System.Textのを使用して、 使用System.Threading.Tasks; のSystem.Windows.Formsを使用して、 使用MathNet.Numerics.LinearAlgebra.Double; 名前空間CoordTF { クラスCoordTransform { / // <まとめ> ///世界直角ターンの空間座標 /// </要約> /// <PARAM NAME = "B">緯度</ PARAM> / </// <PARAM NAME = "L">経度PARAM> /// <名前= "H">高度</ PARAM> PARAM /// <PARAM NAME = "A">半長楕円の軸は</ PARAM> /// <PARAM NAME = "FL">フラット相反</ param>の /// <リターン> </リターン> 公共ダブル[] BLH_XYZ(ダブルB、ダブルL、ダブルH、ダブル、ダブルFL、文字列 VaRのZ =(N×(1 - E2)+ H)* Math.Sin(B)。 dataFormat) { VARのF = 1 / FL。 VaRのE2 = 2 * F -のF * Fを、 DataCnversion dataCnversion =新しいDataCnversion(); B = dataCnversion.DataFormatting(B.ToString()、のdataFormat)。 L = dataCnversion.DataFormatting(L.ToString()、のdataFormat)。 VaRのW = Math.Sqrt(1 - E2×(Math.Sin(B)* Math.Sin(B)))。 VAR N = A / W。 VAR X =(N + H)* Math.Cos(B)* Math.Cos(L)。 VAR Y =(N + H)* Math.Cos(B)* Math.Sin(L)。 ダブル[] XYZ =新しいダブル[3]。 XYZ [0] = X。 XYZ [1] = Y。 XYZ [2] = Z; XYZを返します。 0) L = -L。 VAR = Rhoの206264.806247096363。 VaRのE2 = 2 * F -のF * Fを、 VaRのS = Math.Sqrt(X * X + Y * Y)。 VARエラー= 0.00001; VaRのB1 = Math.Atan(Z / S)。 ダブルB2; 一方、(TRUE) { VARのW1 = Math.Sqrt(1 - E2×(Math.Sin(B1)* Math.Sin(B1)))。 VAR N1は= / W1; B2 = Math.Atan((Z + N1 * E2 * Math.Sin(B1))/ S)。 - (B1)* Rhoの<=エラーMath.Abs(B2)の場合 、ブレーク B1 = B2。 } VARのB = B2。 VaRのW = Math.Sqrt(1 - E2×(Math.Sin(B)* Math.Sin(B)))。 VAR N = A / W。 VaRのH = S / Math.Cos(B) - N。 DataCnversion dataCnversion =新しいDataCnversion(); B = dataCnversion.RAD_DMS(B.ToString( "N8")); L = dataCnversion.RAD_DMS(L.ToString( "N8")); [3]二[] =新しい新しいダブルBLH ; BLH [0] Bが=、 BLH Lを= [1]; BLH [2] = H; BLHを返す; } /// <まとめ> ///変換ブルサ7つのパラメータ /// </要約> /// <PARAM名= "X">空間矩形X - </ PARAM> /// <PARAM NAME = "Y">空間矩形Y </ PARAM> /// <PARAM NAME = "Z">空間矩形Z </ PARAM > /// <PARAM NAME = "DX">翻訳パラメータX </ param>の /// <PARAM NAME = "DY" > 翻訳パラメータy </ PARAM> /// <PARAM NAME = "DZ">平移参数Z </ PARAM> ///ます。<param name = "RPX" > 回転パラメータX </ param>の /// <PARAM NAME = "RPY">旋转参数Y </ PARAM> /// <PARAM NAME = "RPZ">旋转参数Z </ PARAM> /// <PARAM NAME = "K">尺度参数K </ PARAM> /// <戻る> </戻り> 公共ダブル[] BursaTF(ダブルX、ダブルY、Z二重、二重DX、ダブルDY、DZ二重、 二重RPX、ダブルRPY、ダブルRPZ、ダブルK) { VARのRhoは206264.806247096355を=; //常数 ダブルA15、A16、A17、A24、A26、A27、A34、A35、A37。 A15 = Z / Rhoの。A16 = Y / Rhoの。A17 = X / 1000000。 A24 = Z / Rhoの。A26 = X / Rhoの。A27 = Y / 1000000。 A34 = Y / Rhoの。A35 = X / Rhoの。A37 = Z / 1000000。 VAR newX = X + DX - A15 * RPY + A16 * RPZ + A17 * K。 VAR newY = Y + Dyを+ A24 * RPX - A26 * RPZ + A27 * K; VAR新しいZ- = Z + DZ - A34 * RPX +でA35 * RPY + A37 * K、 ダブル[]結果= {newX、newY、新しいですZ-} ; リターン結果; } /// <まとめ> ///ガウスオペレータ /// </要約> /// <PARAM NAME = "B">測地緯度</ PARAM> /// <PARAM NAME =「L ">測地経度</ PARAM> /// <PARAM NAME =" L0 ">経度(度分秒°の中央子午線"形式)</ PARAM> /// <PARAM NAME = "A">主要な半径楕円体</ PARAM> /// <PARAM NAME = "F1"> </ PARAM>の平坦逆数 <PARAM NAME = "XCON"> /// Xパラメータ通常</ PARAM> /// <PARAM NAME = "yCon"> Y常参</ PARAM> /// <戻る> </戻ります> 公共ダブル[] BL_xy(ダブルB、ダブルL、二重L0、二重、二重F1、ダブルXCON、 ダブルyCon) { DataCnversion dataCnversion =新しいですDataCnversion(); VaRのF = 1 / F1; VaRのE2 = 2 * F -のF * Fを、 VAR E12 = E2 /(1 - E2)。 B = dataCnversion.DMSLX_RAD(B.ToString( "N8"))。 L = dataCnversion.DMSLX_RAD(L.ToString( "N8"))。 L0 = dataCnversion.DMSLX_RAD(L0.ToString( "N8"))。 VaRのL = L - L0。 VaRのA0 = 1 + 3 * E2 / 4 + 45 * Math.Pow(E2、2)/ 64 + 350 * Math.Pow(E2、3)/ 512 + 11025 * Math.Pow(E2、4)/ 16384; VaRのA2 = - (3 * E2 / 4 + 60 * Math.Pow(E2、2)/ 64 + 525 * Math.Pow(E2、3)/ 512 + 17640 * Math.Pow(E2、4)/ 16384) / 2。 VaRのA4 =(15 * Math.Pow(E2、2)/ 64 + 210 * Math.Pow(E2、3)/ 512 + 8820 * Math.Pow(E2、 4)/ 16384)/ 4。 VaRのA6 = - (35 * Math.Pow(E2、3)/ 512 + 2520 * Math.Pow(E2、4)/ 16384)/ 6。 VaRのA8 =(315 * Math.Pow(E2、4)/ 16384)/ 8。 VaRのX = *(1 - E2)*(A0 * B + A2 * Math.Sin(2 * B)+ A4 * Math.Sin(4 *のB)+ A6 * Math.Sin(6 *のB)+ A8 * Math.Sin(8 *のB))。 VAR M0 =のL * Math.Cos(B)。 VaRのT = Math.Tan(B)。 VAR N2 = E12 * Math.Pow(Math.Cos(B)、2)。 VaRのW = Math.Sqrt(1 - E2 * Math.Pow(Math.Sin(B)、2))。 VAR N = A / W。 VaRのNT = Nの*トン。 二重X = X +(NT * Math.Pow(M0、2)/ 2)+(NT *(5 - Math.Pow(T、2)+(9 * N 2)+(4 * Math.Pow(N2、 2)))* Math.Pow(M0、4)/ 24)+(NT *(61 - (58 * Math.Pow(T、2))+ Math.Pow(T、4)+(270 * N2) - (330 * N2 * Math.Pow(T、2)))* Math.Pow(M0、6)/ 720)。 二重Y =(N * M0)+(N *(1 - Math.Pow(T、2)+ N2)* Math.Pow(M0、3)/ 6)+(N *(5 - (18 *数学。 POW(T、2))+ Math.Pow(T、4)+(14 * N2) - (58 * N2 * Math.Pow(T、2)))* Math.Pow(M0、5)/ 120) ; X + = XCON。 Y + = yCon。 ダブル[]ポイント=新しいダブル[2]。 [0] = xを指します。 点[1] = Y。 ポイントを返します。 } ダブルyCon) X - = XCON。 IF(Math.Abs(Y)> = K) { { VAR K = 1000000。 VaRのK0 =(3 * E2 / 4 + 45 * Math.Pow(E2、2)/ 64 + 350 * Math.Pow(E2、3)/ 512 + 11025 VAR zoneNumber = Math.Floor(Y / K)。 Y - = zoneNumber。 } 、Y - = yCon。 VaRのF = 1 / F1; VaRのE2 = 2 * F -のF * Fを、 VAR E12 = E2 /(1 - E2)。 DataCnversion dataCnversion =新しいDataCnversion(); L0 = dataCnversion.DMSLX_RAD(L0.ToString( "N8"))。 VaRのA0 = 1 + 3 * E2 / 4 + 45 * Math.Pow(E2、2)/ 64 + 350 * Math.Pow(E2、3)/ 512 + 11025 * Math.Pow(E2、4)/ 16384; VaRのB0 = X /(*(1 - E2)* A0)。 * Math.Pow(E2、4)/ 16384)/ 2。 VaRのK2 = - (63 * Math.Pow(E2、2)/ 64 + 1108 * Math.Pow(E2、3)/ 512 + 58239 * Math.pow(E2、4)/ 16384)/ 3。 K4 =(604 * Math.pow(E2、3)/ 512 + 68 484 * Math.pow(E2、4)/ 16384)/ 3でした。 たR6 = - (26328 * Math.pow(E2、4)/ 16384)/ 3。 SB0 = Math.pow(Math.Sin(B0)、2)でした。 たBfは= B0 + Math.Sin(2 * B0)*(K0 + SB0 *(K2 + SB0(K4 + K6 * SB0)))。 たNF2 = E12 * Math.pow(Math.Cos(BF)、2)。 TF = Math.Tan(BF)でした。 TF2 =のtf * tfのでした。 TF4 = Math.pow(TF、4)でした。 Wfの= Math.sqrt(1 - E2(Math.pow(Math.Sin(BF)、2)))でした。 Nf = A / Wfがありました。 YNF = Y / NFがありました。 = 1 + NF2 VF2でした。 0.5 * VF2 *のTF(Math.pow(YNF、2) - - B = Bfはあった(5 + 3 *のTF2 + NF2 - 9 * NF2 * TF2)* Math.pow(注4)/ 12 +(61 + 90 * 45 * + TF2 TF4)* Math.pow)/ 360(注6)。 VaRのL =(INS - (1 + 2 + TF2 *のM -2)* Math.pow(注3)/ 6 +(5 + 28 * + 24 * TF2のTF4 + 6 + 8 * mを-2 * M -2 * TF2)*数学.Pow(注5)/ 120)/ Math.cos(BF)。 VaRのL = L0 + L。 B = dataCnversion.RAD_DMS(B.ToString( "N8"))。 L = dataCnversion.RAD_DMS(L.ToString( "N8"))。 ダブル[]ポイント=新しいダブル[2]。 点[0] = B。 点[1] = L。 ポイントを返します。 } /// <要約> /// <PARAM NAME = "X"> </ PARAM> ///同一坐标系下坐标换带 /// </要約> VaRのB = xy2BL [0]。 VaRのL = xy2BL [1]。 ダブル[] BL2xy = BL_xy(B、L、L2、F1、XCON、yCon)。 /// <PARAM NAME = "L1">换带前经度</ PARAM> /// <PARAM NAME = "L2">换带后经度</ PARAM> /// <PARAM NAME = ""> < / param>の /// <PARAM NAME = "F1"> </ param>の /// <PARAM NAME = "XCON"> </ param>の /// <PARAM NAME = "yCon"> </ param>の // / </復帰> <戻り> 公共ダブル[] CoordChangeBelt(ダブルX、ダブルY、ダブルL1、L2二重、二重、二重 F1、ダブルXCON、ダブルyCon) { ダブル[] xy2BL = Xy_BL(X、Y、 L1、F1、XCON、yCon)。 BL2xyを返します。 } } }
これにより、座標変換の使用に基づいて変換を完了するためにすべての基本クラスは、今度はクラス内のメソッドを呼び出します。