從本地讀取兩個陣列,計算一元線性迴歸

王程根的技术博客發表於2024-06-07
#include <iostream>
#include <fstream>
#include <sstream>
#include <string>
#include <vector>
#include <numeric>

struct LinearRegression {
    double slope;
    double intercept;
 
    LinearRegression(const std::vector<double>& x, const std::vector<double>& y) {
        size_t n = x.size();
        double sum_x = std::accumulate(x.begin(), x.end(), 0.0);
        double sum_y = std::accumulate(y.begin(), y.end(), 0.0);
        double sum_xy = 0.0;
        double sum_xx = 0.0;
 
        for (size_t i = 0; i < n; ++i) {
            sum_xy += x[i] * y[i];
            sum_xx += x[i] * x[i];
        }
 
        slope = (n * sum_xy - sum_x * sum_y) / (n * sum_xx - sum_x * sum_x);
        intercept = (sum_y - slope * sum_x) / n;
    }
 
    double predict(double x) const {
        return slope * x + intercept;
    }
};

void GetVec(std::ifstream &file,std::vector<double> &vec)
{
    std::string line("");
    if (std::getline(file, line)) 
    {
         std::stringstream ss(line);
         std::string str;
         
         while(getline(ss, str, ' '))
         {
             double number = std::stod(str);
             vec.emplace_back(number);
         }
    }     
}

void ReadFile(const char *pFile, std::vector<double> &vecx,std::vector<double> &vecy)
{
    std::ifstream file(pFile); // 替換為你的檔名

    if (file.is_open()) {
        //讀取兩行        
        GetVec(file,vecx);
        GetVec(file,vecy);
        
        file.close();
    } else {
        std::cout << "Open File Failed!" << std::endl;
    }    
}
 
int main() {
    std::vector<double> vecx;
    std::vector<double> vecy;

    ReadFile("test.txt",vecx,vecy);
    if (vecx.empty() || (vecx.size() != vecy.size()))
    {
        std::cout << "Check Input Failed!"<< std::endl;
        return -1;
    }
 
    LinearRegression model(vecx, vecy);
 
    std::cout << "Slope: " << model.slope << std::endl;
    std::cout << "Intercept: " << model.intercept << std::endl;
    
    return 0;
}

相關文章