1. 程式人生 > >大地測量——計算七引數(程式設計作業)

大地測量——計算七引數(程式設計作業)

張家誠 2016301610045


需求:通過A,B座標系中提供的六個已知同名點,獲得由A轉換到B座標系的七個引數。

邏輯框圖:                                                            介面如下:

                                         


程式碼:

1.檔案讀取部分

//儲存讀入資料的陣列
        double[,] _f1 = new double[6, 3];
        double[,] _f2 = new double[6, 3];
       
        /***************檔案讀取開始************************/
        private void button1_Click(object sender, EventArgs e)
        {
            openFileDialog1.Filter = "文字檔案(*.txt)|*.txt";//檔案過濾器
            if (DialogResult.OK == openFileDialog1.ShowDialog())
                textBox1.Text = openFileDialog1.FileName;
            StreamReader reader = new StreamReader(openFileDialog1.FileName);
            for (int i = 0; i < 6; i++)
            {
                string str = reader.ReadLine();
                string[] arr = new string[3];
                arr = str.Split(',');
                for (int j = 0; j < 3; j++)
                {
                    _f1[i, j] = double.Parse(arr[j]);
                }
            }
           
        }
        private void button2_Click(object sender, EventArgs e)
        {
            openFileDialog2.Filter = "文字檔案(*.txt)|*.txt";//檔案過濾器
            if (DialogResult.OK == openFileDialog2.ShowDialog())
                textBox2.Text = openFileDialog2.FileName;
            StreamReader reader = new StreamReader(openFileDialog2.FileName);          
            for (int i = 0; i < 6; i++)
            {
                string str = reader.ReadLine();
                string[] arr = new string[3];
                arr = str.Split(',');
                for (int j = 0; j < 3; j++)
                {
                    _f2[i, j] = double.Parse(arr[j]);
                }
            }
        }
        /***************檔案讀取結束************************/

2.資料匯入矩陣+計算+輸出

private void button3_Click(object sender, EventArgs e)
        {
               /*******************資料錄入對應矩陣開始**************/
            //計算第一點的B,L
                Matrix sumB = GetItsB(_f1[0, 0], _f1[0, 1], _f1[0, 2]);               
                Matrix sumL = new Matrix(3,1, new double[3] { _f2[0, 0], _f2[0, 1], _f2[0, 2] });
            //計算後續點的B,L 並將之按行新增到第一點末尾   
                for (int i = 1; i < 6; i++)
                { 
                    Matrix _B = GetItsB(_f1[i, 0], _f1[i, 1], _f1[i, 2]);
                   sumB=sumB.Addinend(_B); 
                   Matrix _L = new Matrix(3,1, new double[3] { _f2[i, 0], _f2[i, 1], _f2[i, 2] });
                   sumL=sumL.Addinend(_L);                    
                }
                /*******************資料錄入對應矩陣結束**************/

                /*******************計算開始*****************/
            //X陣求解,V陣求解
                Matrix N = new Matrix(sumB.Transpose() * sumB);
                N.InvertGaussJordan();
                Matrix X = new Matrix(N.Multiply(-1)*sumB.Transpose()*sumL);
                Matrix V = new Matrix(sumB * X + sumL);
                 /*******************計算結束*****************/


                /*******************結果輸出開始*****************/            
            double m0 = Math.Sqrt((V.Transpose()*V).elements[0] / 11);
            textBox3.Text = "平移X0:" + X.elements[0] + "m" +"\r\n"+
                          "平移Y0:" + X.elements[1] + "m   " + "\r\n" +
                          "平移Z0:" + X.elements[2] + "m  " + "\r\n" +
                          "尺度 K:" + Math.Pow(10, 6) * (X.elements[3] - 1) + "ppm   " + "\r\n" +
                          "旋轉 X:" + 180 * 60 * 60 * (X.elements[4] / X.elements[3]) / Math.PI + "s   " + "\r\n" +
                          "旋轉 Y:" + 180 * 60 * 60 * (X.elements[5] / X.elements[3]) / Math.PI + "s   " + "\r\n" +
                          "旋轉 Z:" + 180 * 60 * 60 * (X.elements[6] / X.elements[3]) / Math.PI + "s   " + "\r\n" +
                          "單位權中誤差m0:" + m0*Math.Pow(10,2) + "cm   ";
            /*******************結果輸出結束*****************/
            
                               
        }

        /**
         * 輸入一個點的z,y,z輸出其B矩陣
         */
        Matrix GetItsB(double X, double Y, double Z)
        {
            double[] toB = new double[21]{1,0,0,X,0,-Z,Y,
                                          0,1,0,Y,Z,0,-X,
                                          0,0,1,Z,-Y,X,0};
            Matrix B = new Matrix(3, 7, toB);
            return B.Multiply(-1);

        }

執行結果:




體悟與收穫:

本次的程式設計邏輯相對簡單。但對於程式設計思維掌握不是很熟練的我來說,算是一次非常合適的訓練。

1.這是我第一次寫程式處處用註釋,也是第一次先構思好程式的大部分再開始動手寫的程式。換言之,這是我第一次時刻自己明白自己要做什麼的程式設計。

2.以及,本次除錯我已經能熟練的時候斷點,監測和單步執行。這使得我差錯並沒有花上太多時間。以及,隨著不斷深入程式設計學習,我開始能觸類旁通。

3.本次完成程式總共耗時:  6h  

編寫讀入檔案:3h|一個晚上

這是最簡單的,但我在這犯錯最多。主要是因為:一開始時我是直接用split分隔資料。但split分隔空格使得連續空格處產生了空位“”。我試圖用陣列傳遞來解決這個問題,但後來程式執行效率低下,開啟檔案並讀取到陣列的時間延擱非常長。(約一分鐘左右)於是我反覆糾結我寫的程式碼,執行效率為何如此低下,結果耗時極長。)後來稍微修改了一下讀入txt,改成了txt中也以英文逗號分隔,執行效率低下問題才解決。

錄入矩陣並計算並輸出結果:1|早起到上課前一小時+2h|晚上

此處我花費時間主要還是因為,雖然這次我用了邏輯框架指導我的程式設計,但我程式設計的思路仍舊稍有混亂。外加必要的除錯時間。以及使用他人的矩陣類,併為之新寫addinend的時間,所以用了三個小時。


總之來說,本次程式設計我熟練不少;而且我的程式設計越來越熟練,這也使我振奮不已。總之,我應該繼續好好學習並時刻學習程式設計,並繼續培養良好的程式設計思想和習慣。