В этом проекте мы пытаемся спрогнозировать чистую почасовую выработку энергии (EP) электростанции с комбинированным циклом, используя метод линейной регрессии.
Этот набор данных взят из Репозитория машинного обучения UCI https://archive.ics.uci.edu/ml/datasets/Combined+Cycle+Power+Plant
Мы попытаемся предсказать выход энергии, которая является непрерывной величиной, используя четыре различных функции в качестве входных данных. Для такого рода проблем хорошо подходит модель линейной регрессии. Мы будем использовать специальную технику оптимизации, называемую методом стохастического градиентного спуска (SGD), чтобы получить оптимизированные параметры.
# basic libraries import numpy as np import pandas as pd import matplotlib.pyplot as plt import seaborn as sns
Данные
Наши данные состоят из четырех почасовых характеристик окружающей среды
- Температура (Т)
- Давление окружающей среды (АР)
- Относительная влажность (RH)
- Выпускной вакуум (V)
- Наша целевая переменная – выход энергии (EP).
ccpp = pd.read_csv(‘Data/CCPP/ccpp.csv’) ccpp.head() + — — — -+ — — — -+ — — — -+ — — — — -+ — — — -+ — — — — + | S.no. | AT | V | AP | RH | EP | + — — — -+ — — — -+ — — — -+ — — — — -+ — — — -+ — — — — + | 0 | 8.34 | 40.77 | 1010.84 | 90.01 | 480.48 | | 1 | 23.64 | 58.49 | 1011.4 | 74.2 | 445.75 | | 2 | 29.74 | 56.9 | 1007.15 | 41.91 | 438.76 | | 3 | 19.07 | 49.69 | 1007.22 | 76.79 | 453.09 | | 4 | 11.8 | 40.66 | 1017.13 | 97.2 | 464.43 |
Исследовательский анализ данных
Количество строк и столбцов в фрейме данных
print('No. of Rows: ', ccpp.shape[0])
print('No. of Columns: ', ccpp.shape[1])
No. of Rows: 9568
No. of Columns: 5
Разделение функций и целевого значения
# Features x = ccpp.iloc[:, :-1] y = ccpp.iloc[:, -1]
Блочная диаграмма
Блочная диаграмма данных для понимания масштаба данных
# Scale of Data ccpp.boxplot(color = "black") plt.xlabel("Attributes") plt.ylabel("Scale"); plt.savefig("boxplot.jpg")
Как видно из рисунка, разные функции имеют разный масштаб
Тепловая карта
Поиск корреляции между переменными признаков, чтобы выяснить, какие отношения имеют разные переменные.
sns.heatmap(x.corr(), cmap="YlGnBu", linewidths=0.8, annot=True) plt.savefig("heatmap.png")
Распределение
Как видно из данных, большинство функций нормально распределены, что хорошо для линейной регрессии.
fig, ax = plt.subplots(2,2) col = iter(x.columns) # iterator for i in [0,1]: for j in [0,1]: sns.kdeplot(x[next(col)],color = "dodgerblue", fill = True, ax = ax[i,j]) plt.tight_layout() plt.savefig("images/Distribution.jpg")
Выборка данных
Мы разделим данные на две равные части, где пятьдесят процентов стоек пойдут на обучение данных, а остальные пятьдесят процентов — на тестирование. Мы будем случайным образом перемешивать данные, чтобы избежать выбора шаблона в данных обучения или тестирования.
Мы будем использовать функцию sklearn traintestsplit()
, которая будет автоматически перемешивать и разделять данные для нас.
# split the data into test and training sets from sklearn.model_selection import train_test_split x_train, x_test, y_train, y_test= \ train_test_split(x,y,test_size=0.50, random_state=20)
Тренировочные данные
Как видно из рисунка, тестовые данные сохранили характерное распределение набора данных и являются репрезентативными для генеральной совокупности.
# Training set is well representative subset of the actual dataset fig, ax = plt.subplots(2,2) col = iter(x_train.columns) # iterator for i in [0,1]: for j in [0,1]: sns.kdeplot(x_train[next(col)],color = “magenta”, fill = True, ax = ax[i,j]) plt.tight_layout()
Масштабирование
Поскольку мы используем алгоритм SGD в качестве оптимизатора, важно, чтобы мы масштабировали наши данные, чтобы избежать проблемы взрывающегося градиента
Мы будем использовать метод Standard Scaler, используя стандартную оценку z, заданную
где
x — образец
μ среднее значение
σ – стандартное отклонение
Использование функции Sklearn StandardScaler()
автоматически масштабирует данные
# Scaling training data from sklearn.preprocessing import StandardScaler scalar = StandardScaler() x_scaled_train = scalar.fit_transform(x_train) x_scaled_test = scalar.transform(x_test)
Линейная регрессия
Теперь мы реализуем нашу линейную регрессию, используя технику регрессии SGD, чтобы вычислить коэффициент нашей линейной модели. Мы можем использовать функцию SGDRegressor
из sklearn для расчета коэффициентов.
from sklearn.linear_model import SGDRegressor sgr = SGDRegressor(max_iter=1000, eta0 = 0.01) sgr.fit(x_scaled_train, y_train) print(sgr.coef_) [-14.83958743 -2.86265782 0.28195519 -2.30598442]
Точность
Мы рассчитаем точность этой модели, используя среднеквадратичную ошибку (RMSE)
sgrmse = mean_squared_error(y_test, y_pred) rmse = np.sqrt(sgrmse) print(rmse) 4.638256925600261
Поскольку значение RMSE довольно низкое, мы можем сделать вывод, что наша модель хорошо предсказывает целевую переменную