利用规则格网进行体积计算c#实现

1.界面及功能

2.夹角凸包

        向量积的计算为模乘以对应的夹角。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Tin
{
    class jiajiaotubao
    {
        public pointt P0;                                        //凸包多边形的基点
        public List<pointt> jiajiaodian_s = new List<pointt>();   //按夹角大小排序后的散点集
        public List<pointt> tubaodian_s = new List<pointt>();   //凸包点构成的散点列表
        //public List<Triangle> triangulation = new List<Triangle>();   //构建不规则三角网
        //scan扫描凸包算法 非快速凸包
        // 查找基点

        private pointt FindP0(List<pointt> sandianqi)//散点:数据点
        {
            pointt result = null;                     //用于查找基点的临时基点


            foreach (pointt sandian in sandianqi)
            {
                if (result == null)
                {
                    result = sandian;
                }
                else
                {
                    if (sandian.Y < result.Y)         //找到最小的纵坐标
                    {
                        result = sandian;
                    }
                    if (sandian.Y == result.Y)
                    {
                        if (sandian.X < result.X)    //如果Y相等则比较X
                        {
                            result = sandian;        //最小纵坐标的最小横坐标
                        }
                    }
                }
            }
            return result;
        }
        // 按夹角由小到大对所有点进行排序(基点,离散点)

        private List<pointt> Sort(pointt P0, List<pointt> sandianqi)
        {
            List<pointt> jiajiaodian = new List<pointt>();

            foreach (pointt point in sandianqi)
            {
                jiajiaodian.Add(point);                          //加入点
            }

            //遍历,排序 大的上浮
            for (int i = 0; i < jiajiaodian.Count; i++)
            {
                for (int j = i + 1; j < jiajiaodian.Count; j++)
                {
                    if (i == 0)
                    {
                        if (P0.id == jiajiaodian[j].id)         //查找基点
                        {
                            pointt temp = jiajiaodian[j];
                            jiajiaodian[j] = jiajiaodian[0];
                            jiajiaodian[0] = temp;              //第0行存基点
                        }
                    }

                    //  arctan(y/x)  从斜率->夹角     从j=2开始   都是增函数

                    else if (Math.Atan2(jiajiaodian[j].Y - P0.Y, jiajiaodian[j].X - P0.X) < Math.Atan2(jiajiaodian[i].Y - P0.Y, jiajiaodian[i].X - P0.X))
                    {
                        //jiajiaodian[j]跟上一行数据进行夹角大小的比较
                        pointt temp = jiajiaodian[j];
                        jiajiaodian[j] = jiajiaodian[i];
                        jiajiaodian[i] = temp;
                    }
                    else if (Math.Atan2(jiajiaodian[j].Y - P0.Y, jiajiaodian[j].X - P0.X) == Math.Atan2(jiajiaodian[i].Y - P0.Y, jiajiaodian[i].X - P0.X))
                    {
                        if (Math.Abs(jiajiaodian[j].X - P0.X) > Math.Abs(jiajiaodian[i].X - P0.X))          //取更远的(上浮),另一个在射线 上的某个位置
                        {
                            pointt temp = jiajiaodian[j];
                            jiajiaodian[j] = jiajiaodian[i];
                            jiajiaodian[i] = temp;
                        }
                        jiajiaodian.RemoveAt(j);
                        j--;
                    }
                }
            }
            return jiajiaodian;
        }
        // 建立由凸包点构成的列表或堆栈S

        //顺时针
        private List<pointt> Convex(List<pointt> jiajiaodian)
        {
            List<pointt> tubaodian = new List<pointt>();          //凸包点列表(动态)
            tubaodian.Add(jiajiaodian[0]);
            tubaodian.Add(jiajiaodian[1]);
            tubaodian.Add(jiajiaodian[2]);
            for (int i = 3; i < jiajiaodian.Count; i++)
            {
                //count-1 :当前;count-2:当前-1 ; jiajiaodian[i]:按夹角大小排序;i:当前

                //m:叉乘系数;
                //从角度最大的开始则是顺时针,点对应右转(m<0)

                double m = (tubaodian[tubaodian.Count - 2].X - tubaodian[tubaodian.Count - 1].X) * (jiajiaodian[i].Y - tubaodian[tubaodian.Count - 1].Y)
                    - (tubaodian[tubaodian.Count - 2].Y - tubaodian[tubaodian.Count - 1].Y) * (jiajiaodian[i].X - tubaodian[tubaodian.Count - 1].X);
                if (m > 0)
                {
                    tubaodian.RemoveAt(tubaodian.Count - 1);//count-1;
                    while (m > 0)
                    {
                        //等式一致,X*Ys-Y*Xs,夹角从大到小遍历
                        m = (tubaodian[tubaodian.Count - 2].X - tubaodian[tubaodian.Count - 1].X) * (jiajiaodian[i].Y - tubaodian[tubaodian.Count - 1].Y)
                            - (tubaodian[tubaodian.Count - 2].Y - tubaodian[tubaodian.Count - 1].Y) * (jiajiaodian[i].X - tubaodian[tubaodian.Count - 1].X);
                        //左转
                        if (m > 0)
                            tubaodian.RemoveAt(tubaodian.Count - 1);
                        //右转
                        else
                        {
                            tubaodian.Add(jiajiaodian[i]); //入栈
                            break;
                        }
                    }
                }
                else
                {
                    tubaodian.Add(jiajiaodian[i]);//这里要的是右转,顺时针开始
                }
            }

            return tubaodian;
        }
        public jiajiaotubao(List<pointt>sandianqi)
        {
            P0 = FindP0(sandianqi);
            jiajiaodian_s = Sort(P0,sandianqi);
            tubaodian_s = Convex(jiajiaodian_s);//建立凸包点构成的列表或堆栈s
        }
    }
}

 3.主程序代码

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace Tin
{
    public partial class Form1 : Form
    {
        jiajiaotubao jiajiaotubao;
        List<pointt> points = new List<pointt>();
        List<pointt> meiyoutubaodian = new List<pointt>();//没有凸包点
        List<pointt> known_point = new List<pointt>();
        List<pointt> four_point = new List<pointt>();
        List<pointt> tubao_s = new List<pointt>();//存放凸包点
        List<pointt> LP = new List<pointt>();
        double[] minmax=new double[4];
        double Xmax;
        double Ymax;
        double Xmin;
        double Ymin;
        int index;
        double zoom = 1;
        public List<gridpoint> gridps = new List<gridpoint>();//所有格网点g
        public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            OpenFileDialog dialog = new OpenFileDialog();
            dialog.Filter = "文本文件(*.txt)|*.txt|所有文件|*.*";
            dialog.Title = "打开数据文件";
            if (dialog.ShowDialog() == DialogResult.OK)
            {
                string s = string.Empty;
                string[] str;
                StreamReader file = new StreamReader(dialog.FileName,Encoding.Default);
                while (!file.EndOfStream)
                {
                    s = file.ReadLine();
                    str = s.Split(',');
                    points.Add(new pointt(str[0], Convert.ToDouble(str[1]), Convert.ToDouble(str[2]), Convert.ToDouble(str[3])));
                }
                DataTable dataTable = new DataTable();
                dataTable.Columns.Add("点名");
                dataTable.Columns.Add("X分量");
                dataTable.Columns.Add("Y分量");
                dataTable.Columns.Add("H分量");

                for (int i = 0; i < points.Count; i++)
                {
                    DataRow row = dataTable.NewRow();
                    row["点名"] = points[i].id;
                    row["X分量"] = points[i].X;
                    row["Y分量"] = points[i].Y;
                    row["H分量"] = points[i].H;
                    dataTable.Rows.Add(row);
                }
                dataGridView1.DataSource = dataTable;
            }
        }

        private void 导出报告ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            SaveFileDialog dialog = new SaveFileDialog();
            dialog.Filter = "文本文件(*.txt)|*.txt";
            dialog.FileName = "结果";
            if (dialog.ShowDialog() == DialogResult.OK)
            {
                string filename = dialog.FileName;
                FileStream fs = File.Open(filename, FileMode.Create, FileAccess.Write);
                StreamWriter sw = new StreamWriter(fs);
                foreach (string line in richTextBox1.Lines)
                {
                    sw.WriteLine(line);
                }
                sw.Flush();
                sw.Close();
                fs.Close();
            }
        }
        private int searchX(double num,List<pointt>points)//查找x
        {
            int i = 0;
            int index=0;
            for (i = 0; i < points.Count; i++)
            {
                if (points[i].X == num)
                {
                    index = i;
                }
            }
            return index;
        }
        private int searchY(double num, List<pointt> points)//查找y
        {
            int i = 0;
            int index = 0;
            for (i = 0; i < points.Count; i++)
            {
                if (points[i].Y == num)
                {
                    index = i;
                }
            }
            return index;
        }
        private void 凸包顶点ToolStripMenuItem_Click(object sender, EventArgs e)
        {   
            //查找四个顶点
            foreach (pointt t in points)
            {
                known_point.Add(t);//副本
            }

            Xmax = known_point.Max(t => t.X);
            four_point.Add(points[searchX(Xmax,points)]);
            known_point.Remove(points[searchX(Xmax, points)]);

            Xmin = known_point.Min(t => t.X);
            four_point.Add(points[searchX(Xmin, points)]);
            known_point.Remove(points[searchX(Xmin, points)]);

            Ymax = known_point.Max(t => t.Y);
            four_point.Add(points[searchY(Ymax, points)]);
            known_point.Remove(points[searchY(Ymax, points)]);

            Ymin = known_point.Min(t => t.Y);
            four_point.Add(points[searchY(Ymin, points)]);
            known_point.Remove(points[searchY(Ymin, points)]);

        }
        private void FindLeftPoint()
        {

        }
        int left_point(pointt p1,pointt p2,pointt p3)
        {
            int tem = (int)(p1.X * p2.Y - p2.X * p1.Y + p3.X * (p1.Y - p2.Y) + p3.Y * (p2.X - p1.X));
            if (tem > 0)
            {
                return 1;
            }
            else
                return -1;
           
        }
        private void 找出凸包点ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            int i = 1;
            double tem = 0;
            double x3 = Xmax;
            double y3 = four_point[0].Y;
            double x1 = Xmin;
            double y1 = four_point[1].Y;
            double x2 = four_point[2].X;
            double y2 = Ymax;
            double x4 = four_point[3].X;
            double y4 = Ymin;
            double []area=new double[known_point.Count];
            int []Index=new int[known_point.Count];
            
            for (int j = 0; j < known_point.Count; j++)
            {
                tem = x1 * y2 - x2 * y1 + known_point[j].X*(y1 - y2) + known_point[j].Y*(x2 - x1);
                if (tem > 0)//p1-p2左侧
                {
                    LP.Add(known_point[j]);//左边点集
                    int z = 0;
                    area[z] = Math.Abs(x1*(y2 - known_point[j].Y) + x2* (known_point[j].Y - y1) + known_point[j].X * (y1 - y2)) / 2;
                    Index[z] = j;
                    z++;
                    double area_max = area[0];
                    for (int zoom = 0; zoom < area.Count(); zoom++)
                    {
                        if (area_max <= area[zoom])
                        {
                            area_max = area[zoom];
                            index = zoom;
                        }
                    }
                    LP.Remove(known_point[Index[index]]);
                }

            }
            未完善
            if (LP.Count < 1)
            {
                //tubao_s.Add(four_point[1]);
            }
        }

        public void Draw(int a)
        {
            //位图            一推像素
            Bitmap bitmap = new Bitmap(a + 10, a + 10);
            //Image ge = bitmap;

            // 绘图图面
            Graphics g1 = Graphics.FromImage(bitmap);

            g1.Clear(Color.White);

            //找到点集合的最大最小值Xmax,Ymax,Xmin,Ymin

            //     =>:右侧注重返回值    lambda 运算符

            double Xmax = points.Max(t => t.X); //pointt t       
            double Ymax = points.Max(t => t.Y);

            double Xmin = points.Min(t => t.X);
            double Ymin = points.Min(t => t.Y);

            //坐标对应变化系数
            int m, n;
            if (Xmax - Xmin > Ymax - Ymin)
            {
                m = a;          // x轴
                n = (int)(a * (Ymax - Ymin) / (Xmax - Xmin));//正比缩放  y轴
            }
            else
            {
                n = a;
                m = (int)(a * (Xmax - Xmin) / (Ymax - Ymin));//增
            }

            //绘制点,指定大小初始化
            Bitmap oo = new Bitmap(3, 3);
            Image o = oo;
            for (int i = 0; i < 3; i++)
                for (int j = 0; j < 3; j++)
                    oo.SetPixel(i, j, Color.Blue);                    //点像素颜色

            foreach (pointt point in points)
            {
                Font f = new Font("宋体", (int)(3 * zoom));           //字体跟大小,7

                //指定位置(坐标)绘图    占比*比例       y的还需要用1减去占比(电脑的上绘制的原点在左上角,向右为X轴正轴,向下为Y轴正轴)
                g1.DrawImage(o, (int)((point.X - Xmin) / (Xmax - Xmin) * m), (int)(n - (point.Y - Ymin) / (Ymax - Ymin) * n));
                //g1.DrawImage(o, (int)((point.X - Xmin) / (Xmax - Xmin) * m), (int)( (point.Y - Ymin) / (Ymax - Ymin) * n));//错的

                //显示点名    Brushes:填充,id颜色
                g1.DrawString(point.id, f, Brushes.Blue, (int)((point.X - Xmin) / (Xmax - Xmin) * m), (int)(n - (point.Y - Ymin) / (Ymax - Ymin) * n));
            }
            if (jiajiaotubao != null)
            {
                Pen p = new Pen(Color.Red, 1);                      //画笔
                for (int i = 0; i < jiajiaotubao.tubaodian_s.Count - 1; i++)
                {
                    g1.DrawLine(p, (int)((jiajiaotubao.tubaodian_s[i].X - Xmin) / (Xmax - Xmin) * m), (int)(n - n * (jiajiaotubao.tubaodian_s[i].Y - Ymin) / (Ymax - Ymin)), (int)((jiajiaotubao.tubaodian_s[i + 1].X - Xmin) / (Xmax - Xmin) * m), (int)(n - n * (jiajiaotubao.tubaodian_s[i + 1].Y - Ymin) / (Ymax - Ymin)));
                }
                g1.DrawLine(p, (int)((jiajiaotubao.tubaodian_s[jiajiaotubao.tubaodian_s.Count - 1].X - Xmin) / (Xmax - Xmin) * m), (int)(n - n * (jiajiaotubao.tubaodian_s[jiajiaotubao.tubaodian_s.Count - 1].Y - Ymin) / (Ymax - Ymin)), (int)((jiajiaotubao.tubaodian_s[0].X - Xmin) / (Xmax - Xmin) * m), (int)(n - n * (jiajiaotubao.tubaodian_s[0].Y - Ymin) / (Ymax - Ymin)));

            }

            GetGridpoint(1);                //以L=1m计算网格中心点坐标 

            //绘制网格
            int L = 1;
            double w_num = Math.Ceiling((Ymax - Ymin) / L);    //图片中的横轴的网格数
            double h_num = Math.Ceiling((Xmax - Xmin) / L);     //图片中纵轴的网格数

            Brush bru = new SolidBrush(Color.Blue);               //定义画笔

            PointF p0 = new PointF();//画图的基准点
            double w_shrink = (Ymax - Ymin + L) / 473;
            double h_shrink = (Xmax - Xmin + L) / 268;
            double shrink = Math.Max(w_shrink, h_shrink);   //确定缩小比例
            //if (shrink == w_shrink)                    //使图形中心在图片的中心
            //{
            //    p0.X = 25;
            //    p0.Y = 268 - float.Parse(((268 - h_num * L / shrink) / 2).ToString());
            //}
            //else
            //{
            //    p0.X = float.Parse(((473 - w_num * L / shrink) / 2).ToString());
            //    p0.Y = 268 - 25;

            //}
            p0.X = 0;
            p0.Y = 80;
            //绘制网格
            for (int i = 0; i <= h_num; i++)    //绘制横线
            {
                g1.DrawLine(Pens.Black, p0.X, float.Parse((p0.Y - i * L / shrink).ToString()),
                    float.Parse((p0.X + w_num * L / shrink).ToString()),
                    float.Parse((p0.Y - i * L / shrink).ToString()));
            }
            for (int i = 0; i <= w_num; i++)    //绘制纵线
            {
                g1.DrawLine(Pens.Black, float.Parse((p0.X + i * L / shrink).ToString()), p0.Y,
                     float.Parse((p0.X + i * L / shrink).ToString()),
                     float.Parse((p0.Y - h_num * L / shrink).ToString()));
            }
            //gph1.Dispose();
            //Image ge1 = bitmap1;
            //pictureBox1.Image = ge1;
            //释放资源
            g1.Dispose();

            Image ge = bitmap;
            pictureBox1.Image = ge;
            tabControl1.SelectedTab = tabPage3;
        }
        


        private void 夹角排列ToolStripMenuItem_Click(object sender, EventArgs e)
        {
             jiajiaotubao = new jiajiaotubao(points);//scan凸包算法
             Draw((int)(200*zoom));

        }

                private void button2_Click(object sender, EventArgs e)
                {
                    if (100 * zoom < 1000)
                    {
                        zoom = zoom * 1.1;
                        Draw((int)(100 * zoom));
                        //wangge( 1, (int)(100*zoom));
                    }
                }

        private void button3_Click(object sender, EventArgs e)
        {
            if (100 * zoom > 50)
            {
                zoom = zoom * 0.9;
                Draw((int)(100 * zoom));
                //wangge(1, (int)(100 * zoom));
            }
        }

        private void button4_Click(object sender, EventArgs e)
        {
            zoom = 1;
            Draw((int)(100 * zoom));
        }
        private void waibaojuxing(List<pointt> four_point, int L)//L分别输入1 5 10
        {
            double length = Ymax - Ymin;//长
            double width = Xmax - Xmin;//宽
            double r = (length + width) * 0.4 / 2;
            int m = (int)(length / L);
            int n = (int)(width / L);
            for (int i = 0; i < m; i++)
            {
                for (int j = 0; j < n; j++)
                {
                    gridpoint gp = new gridpoint();
                }
            }

        }
        
        private void wangge( int L, int a)//绘制网格
        {
            Bitmap bitmap1 = new Bitmap(a + 10,a + 10);

             绘图图面
            Graphics gph1 = Graphics.FromImage(bitmap1);
           
            double w_num = Math.Ceiling((Ymax - Ymin) / L);    //图片中的横轴的网格数
            double h_num = Math.Ceiling((Xmax - Xmin) / L);     //图片中纵轴的网格数
                          
            Brush bru = new SolidBrush(Color.Blue);               //定义画笔

            PointF p0 = new PointF();//画图的基准点
            double w_shrink = (Ymax - Ymin + L) / 600;
            double h_shrink = (Xmax - Xmin + L) / 350;
            double shrink = Math.Max(w_shrink, h_shrink);   //确定缩小比例
           
            p0.X = 50;
            p0.Y = 50;
            //绘制网格
            for (int i = 0; i <= h_num; i++)    //绘制横线
            {
                gph1.DrawLine(Pens.Black, p0.X, float.Parse((p0.Y - i * L / shrink).ToString()),
                    float.Parse((p0.X + w_num * L / shrink).ToString()),
                    float.Parse((p0.Y - i * L / shrink).ToString()));
            }
            for (int i = 0; i <= w_num; i++)    //绘制纵线
            {
                gph1.DrawLine(Pens.Black, float.Parse((p0.X + i * L / shrink).ToString()), p0.Y,
                     float.Parse((p0.X + i * L / shrink).ToString()),
                     float.Parse((p0.Y - h_num * L / shrink).ToString()));
            }
            gph1.Dispose();
            gph1.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;
            Image ge1 = bitmap1;
            pictureBox1.Image = ge1;

            //g1.Dispose();

            //Image ge = bitmap;
            //pictureBox1.Image = ge;
            //tabControl1.SelectedTab = tabPage3;


        }
        private void GetGridpoint(int L)//生成所有网格点坐标
        {
            //格网边界
            Xmax =(points.Max(t => t.X)); //pointt t       
            Ymax =(points.Max(t => t.Y));

            Xmin = points.Min(t => t.X);
            Ymin = points.Min(t => t.Y);

            //搜索半径
            double r = (Ymax - Ymin + Xmax - Xmin) * 0.5 * 0.4;
            int m = (int)Math.Ceiling(Math.Round(((Ymax - Ymin) / L),3));//网格数
            int n = (int)Math.Ceiling(Math.Round((Xmax - Xmin) / L,3));
            //格网中线点坐标
            for (int i = 0; i < m; i++)
            {
                for (int j = 0; j < n; j++)
                {
                    gridpoint gp = new gridpoint();
                    gp.n = 0;
                    gp.x = (L / 2.0)+Xmin + j * L ;
                    gp.y = (L / 2.0)+Ymin + i * L ;
                    gridps.Add(gp);
                }
            }
        }
        private void 建立外包矩形ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            //double length = Ymax - Ymin;//长
            //double width = Xmax - Xmin;//宽
            //GetGridpoint(1);                //以L=1m计算网格中心点坐标 
            //wangge(1 , 100);//绘制网格
        }

        private void 中心点是否在凸包内ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            //GetGridpoint(1);                //以L=1m计算网格中心点坐标 
            List<gridpoint> newgridps = new List<gridpoint>();
            int z = 0;
            foreach (pointt tubao in jiajiaotubao.tubaodian_s)
            {
                tubao_s.Add(tubao);
               // richTextBox1.Text += "凸包x分量:" + tubao_s[z].X.ToString() + "\ty:" + tubao_s[z].Y.ToString() + "\th:" + tubao_s[z].H.ToString()+"\r\n";
                z++;

            }
            //foreach (gridpoint g in gridps)
            //{
            //    newgridps.Add(g);
            //}
            double x1;
            
            int count = 0;
            for (int j = 0; j < gridps.Count; j++)
            {
                int label = 0;
                for (int i = 0; i <tubao_s.Count()-1; i++)
                {
                    if (gridps[j].y < Math.Max(tubao_s[i].Y, tubao_s[(i + 1)%(tubao_s.Count() )].Y) && gridps[j].y > Math.Min(tubao_s[(i + 1) % (tubao_s.Count()) ].Y, tubao_s[i].Y))
                    {
                        x1 = (gridps[j].y - tubao_s[i].Y) * (tubao_s[(i + 1) % (tubao_s.Count())].X - tubao_s[i].X) / (tubao_s[(i + 1) % (tubao_s.Count())].Y - tubao_s[i].Y) + tubao_s[i].X;
                        if (x1 > gridps[j].x)
                        {
                            label++;
                        }
                    }
                }
                if (label % 2 == 1) 
                {
                    gridps[j].n = 1;
                    newgridps.Add(gridps[j]);
                    count++;
                    //richTextBox1.Text += j.ToString() + "\t" + label.ToString()+"\t" +count.ToString()+ "\r\n";

                }
            }
           
            int num=0;
            //num = get_in_grid_num(tubao_s);
            //int c = 0;
        }
        private int get_in_grid_num(List<pointt> convex_hull)        //输出有多少格网点在凸包内
        {
            int n = convex_hull.Count();
            int m = gridps.Count();
            int num = 0;
            for (int i = 0; i < m; i++)
            {
                for (int j = 0; j < n - 1; j++)
                {
                    if (gridps[i].y < Math.Max(convex_hull[j].Y, convex_hull[j + 1].Y) && gridps[i].y >  Math.Min(convex_hull[j].Y, convex_hull[j + 1].Y))
                    { gridps[i].n  += judge(gridps[i], convex_hull[j], convex_hull[j + 1]); }

                }
                if (gridps[i].n == 1) num++;
            }
            return num;
        }
        private int judge(gridpoint a, pointt b, pointt c)       //判断点a是否在b—c线的左边
        {
            double m = (c.X - b.X) / (c.Y - b.Y) * (a.y - b.Y) + b.X;
            if (m > a.x)
                return 1;
            else
                return 0;
        }

        private void 反距离加权法求格网高程ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            foreach (pointt point in points)
            {
                meiyoutubaodian.Add(point);
            }
            foreach (pointt tubao in tubao_s)
            {
                meiyoutubaodian.Remove(tubao);//去除凸包点的散点集,即无凸包点的散点集
            }
            double length = Ymax - Ymin;//长
            double width = Xmax - Xmin;//宽

            double r = (length + width) * 0.4 / 2;          //半径
            double d;
            double[] D = new double[meiyoutubaodian.Count];       //存放距离
            List<pointt> Q = new List<pointt>();                //离散点
            double[] quanzhong = new double[meiyoutubaodian.Count];//权重
            double h = 0;                       //网格高程
            int L = 1;
            for (int i = 0; i < gridps.Count; i++)
            {
                if (gridps[i].n == 1)
                {
                    double H_sum =
                               get_point_h(r, points, gridps[i].x - L / 2, gridps[i].y - L / 2) +
                               get_point_h(r, points, gridps[i].x - L / 2, gridps[i].y + L / 2) +
                               get_point_h(r, points, gridps[i].x + L / 2, gridps[i].y + L / 2) +
                               get_point_h(r, points, gridps[i].x + L / 2, gridps[i].y - L / 2);
                    //richTextBox1.Text += "插值高程:" + H_sum.ToString() + "\r\n";
                }
            }

        }
        double get_point_h(double r, List<pointt> pointt, double X, double Y)     //得到该点的高程
        {   
            double H = 0, Di_sum = 0;
            for (int i = 0; i < pointt.Count(); i++)
            {
                double D = Math.Sqrt((pointt[i].X - X) * (pointt[i].X - X) + (pointt[i].Y - Y) * (pointt[i].Y - Y));
                if (D <= r)
                {
                    H += pointt[i].H / D;
                    Di_sum += 1 / D;
                }
            }
            return H / Di_sum;
        }
        private double get_V(double r, double L, double height_datum, List<pointt> pointt)     //得到总的体积 
        {
            double V = 0;
            for (int i = 0; i < gridps.Count(); i++)                              //循环累加每个在凸包内的体积
            {
                if (gridps[i].n == 1)
                {
                    double H_sum =
                        get_point_h(r, pointt, gridps[i].x - L / 2, gridps[i].y - L / 2) +
                        get_point_h(r, pointt, gridps[i].x - L / 2, gridps[i].y + L / 2) +
                        get_point_h(r, pointt, gridps[i].x + L / 2, gridps[i].y + L / 2) +
                        get_point_h(r, pointt, gridps[i].x + L / 2, gridps[i].y - L / 2);
                    V = V + (H_sum / 4 - height_datum) * L * L;
                }
            }
            return V;
        }
        private void 体积计算ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            double v_total = 0;
            double length = Ymax - Ymin;//长
            double width = Xmax - Xmin;//宽
            double r = (length + width) * 0.4 / 2.0;          //半径

            v_total = get_V(r, 1, Convert.ToDouble(textBox1.Text), points);
            richTextBox1.Text += "总体积:" + v_total.ToString()+"\r\n";
        }

        private void 一键计算ToolStripMenuItem_Click(object sender, EventArgs e)
        {
           
                凸包顶点ToolStripMenuItem_Click(sender, e);
                //找出凸包点ToolStripMenuItem_Click(sender, e);
                夹角排列ToolStripMenuItem_Click(sender, e);
                建立外包矩形ToolStripMenuItem_Click(sender, e);
                中心点是否在凸包内ToolStripMenuItem_Click(sender, e);
                //li中心点凸包ToolStripMenuItem_Click(sender, e);
                反距离加权法求格网高程ToolStripMenuItem_Click(sender, e);
                体积计算ToolStripMenuItem_Click(sender, e);
            

        }

        private void button5_Click(object sender, EventArgs e)
        {
            一键计算ToolStripMenuItem_Click(sender, e);
        }

        private void li中心点凸包ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            int num = 0;
            num = get_in_grid_num(jiajiaotubao.tubaodian_s);
            richTextBox1.Text +="num:"+num.ToString();
        }

        private void 导出jpg图片ToolStripMenuItem_Click(object sender, EventArgs e)
        {

        }

        private void Form1_Load(object sender, EventArgs e)
        {

        }
    }
}

看代码,看注释。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值