用三维点阵图观察马氏距离

纵然是瞬间 提交于 2020-02-22 12:28:59

图片颜色由马氏距离计算而得//==================== 读入图片部分 =============================
Bitmap image = new Bitmap(“3obj.png”);// “Line.png” tree.png “x2.jpg” “hous.png” 白色的背景,黑区面积不要太多
int width = image.Width;
int height = image.Height;

        //====================  非托管[指针操作]部分  =============================
        double[][] xy0 = getMs(image, width, height, 320, 240, 320, 240);
        double[][] xy1 = getMs(image, width, height, 150, 355, 100, 100);
        double[][] xy2 = getMs(image, width, height, 487, 336, 100, 100);
        double[][] xy3 = getMs(image, width, height, 418, 112, 100, 100);


        //====================  矩阵准备部分  =============================

        //各分量的均值作为集合的中心:
        var means1 = Accord.Statistics.Tools.Mean(xy1);
        var means2 = Accord.Statistics.Tools.Mean(xy2);
        var means3 = Accord.Statistics.Tools.Mean(xy3);
        var means0 = Accord.Statistics.Tools.Mean(xy0);

        //先求出"协方差矩阵MC":
        double[,] MC1 = Accord.Statistics.Tools.Covariance(xy1);
        double[,] MC2 = Accord.Statistics.Tools.Covariance(xy2);
        double[,] MC3 = Accord.Statistics.Tools.Covariance(xy3);
        double[,] MC0 = Accord.Statistics.Tools.Covariance(xy0);


        //对"协方差矩阵MC"进行SVD分解,以替代"协方差矩阵MC"的逆:
        var svd1 = new Accord.Math.Decompositions.SingularValueDecomposition(MC1);
        var svd2 = new Accord.Math.Decompositions.SingularValueDecomposition(MC2);
        var svd3 = new Accord.Math.Decompositions.SingularValueDecomposition(MC3);
        var svd0 = new Accord.Math.Decompositions.SingularValueDecomposition(MC0);


        //====================  三维显示部分  =============================

        //总字典初始化:
        AxlesGL.GLB.DL7V = new Dictionary<string, List<AxlesGL.V7F>>();

        //以点集方式观察:
        List<AxlesGL.V7F> LV_Points = new List<AxlesGL.V7F>();

        //用马氏距离标注颜色:
        for (int i = 0; i < 99999; i++)
        {
            double cx = 320 + 320 * Math.Cos(i / 25.8147f) + 50;
            double cy = 240 + 240 * Math.Sin(i / 36.9258f) + 50;

            ////以下计算"马哈拉诺比斯"距离:
            double r1 = 1 + width * height / ((cx - means1[0]) * (cx - means1[0]) + (cy - means1[1]) * (cy - means1[1]));
            double r2 = 1 + width * height / ((cx - means2[0]) * (cx - means2[0]) + (cy - means2[1]) * (cy - means2[1]));
            double r3 = 1 + width * height / ((cx - means3[0]) * (cx - means3[0]) + (cy - means3[1]) * (cy - means3[1]));
            double kv1 = Accord.Math.Distance.Mahalanobis(new double[] { cx * r1, cy * r1 }, means0, svd1);//means1
            double kv2 = Accord.Math.Distance.Mahalanobis(new double[] { cx * r2, cy * r2 }, means0, svd2);//means2
            double kv3 = Accord.Math.Distance.Mahalanobis(new double[] { cx * r3, cy * r3 }, means0, svd3);//means3


            //double kv1 = Accord.Math.Distance.Mahalanobis(new double[] { cx - means1[0], cy - means1[1] }, means1, svd1);//means1
            //double kv2 = Accord.Math.Distance.Mahalanobis(new double[] { cx - means2[0], cy - means2[1] }, means2, svd2);//means2
            //double kv3 = Accord.Math.Distance.Mahalanobis(new double[] { cx - means3[0], cy - means3[1] }, means3, svd3);//means3

            double kv = (kv1 + kv2 + kv3);

            float ww = .2f;
            float rr = (float)(0.5 + 0.4 * Math.Cos(kv / 2.5f));
            float gg = (float)(0.5 + 0.3 * Math.Cos(kv / 3.5f));
            float bb = (float)(0.5 + 0.6 * Math.Cos(kv / 5.5f));

            LV_Points.Add(
                       new AxlesGL.V7F((float)cx / 5f, (float)cy / 5f, (float).5f, ww, rr, gg, bb)
                       );
        }


        //用马氏距离标注颜色:
        for (int i = 0; i < xy1.Length; i++)
        {
            ////以下计算"马哈拉诺比斯"距离:
            double kv = Accord.Math.Distance.Mahalanobis(new double[] { xy1[i][0], xy1[i][1] }, means1, svd1);
            float ww = .2f;
            float rr = (float)(0.5 + 0.5 * Math.Cos(kv * 13));
            float gg = (float)(0.5 + 0.5 * Math.Cos(kv * 15));
            float bb = (float)(0.5 + 0.5 * Math.Cos(kv * 19));
            LV_Points.Add(
                       new AxlesGL.V7F(((float)xy1[i][0] + 150) / 5f, ((float)xy1[i][1] + 355) / 5f, 0, ww, rr, gg, bb)
                       );
        }

        //用马氏距离标注颜色:
        for (int i = 0; i < xy2.Length; i++)
        {
            ////以下计算"马哈拉诺比斯"距离:
            double kv = Accord.Math.Distance.Mahalanobis(new double[] { xy2[i][0], xy2[i][1] }, means2, svd2);
            float ww = .2f;
            float rr = (float)(0.5 + 0.5 * Math.Cos(kv * 13));
            float gg = (float)(0.5 + 0.5 * Math.Cos(kv * 15));
            float bb = (float)(0.5 + 0.5 * Math.Cos(kv * 19));
            LV_Points.Add(
                       new AxlesGL.V7F(((float)xy2[i][0] + 487) / 5f, ((float)xy2[i][1] + 336) / 5f, 0, ww, rr, gg, bb)
                       );
        }

        //用马氏距离标注颜色:
        for (int i = 0; i < xy3.Length; i++)
        {
            ////以下计算"马哈拉诺比斯"距离:
            double kv = Accord.Math.Distance.Mahalanobis(new double[] { xy3[i][0], xy3[i][1] }, means3, svd3);
            float ww = .2f;
            float rr = (float)(0.5 + 0.5 * Math.Cos(kv * 13));
            float gg = (float)(0.5 + 0.5 * Math.Cos(kv * 15));
            float bb = (float)(0.5 + 0.5 * Math.Cos(kv * 19));
            LV_Points.Add(
                       new AxlesGL.V7F((float)(xy3[i][0] + 418) / 5f, (float)(xy3[i][1] + 112) / 5f, 0, ww, rr, gg, bb)
                       );
        }

        AxlesGL.GLB.DL7V.Add("Points", LV_Points);//  Points Points
        this.Refresh();
        //注:三维库由OpenGL搭建.
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!