Пример #1
0
        virtual int ComputeModel(ModelSet& models, const Data& data, const std::set<int>& samples)
        {
            double meanX = 0, meanY = 0, meanXX = 0, meanYY = 0, meanXY = 0;
            for (std::set<int>::const_iterator it = samples.begin();it != samples.end(); it++)
            {
                const Datum& p = data[*it];
                meanX += p.x;
                meanY += p.y;
                meanXX += p.x * p.x;
                meanYY += p.y * p.y;
                meanXY += p.x * p.y;
            }
            int M = static_cast<int>(samples.size());
            meanX /= M;
            meanY /= M;
            meanXX /= M;
            meanYY /= M;
            meanXY /= M;
            double a = meanXX - meanX*meanX;
            double b = meanXY - meanX*meanY;
            double d = meanYY - meanY*meanY;

            Model model;
            if (fabs(b) > DBL_EPSILON)
            {
                // Calculate the first eigen vector of A = [a, b; b, d]
                // Ref. http://www.math.harvard.edu/archive/21b_fall_04/exhibits/2dmatrices/index.html
                double T2 = (a + d) / 2;
                double lambda = T2 - sqrt(T2 * T2 - (a * d - b * b));
                double v1 = lambda - d, v2 = b;
                double norm = sqrt(v1 * v1 + v2 * v2);
                model.a = v1 / norm;
                model.b = v2 / norm;
            }
            else
            {
                model.a = 1;
                model.b = 0;
            }
            model.c = -model.a * meanX - model.b * meanY;
            models.push_back(model);
            return 1;
        }