ts / Multivariate.py
Shrina's picture
Upload
c2b9b65
Raw
History Blame Contribute Delete
4.08 kB
import pandas as pd
import numpy as np
import plotly.express as px
from pycaret.regression import *
from utilities import is_numeric
class Multivariate_Models:
def __init__(self, data, forecasting_horizon, target_column, date_column, time_interval, fold=3,
metric_to_opt="RMSLE", session_id=42):
#Pre-Processing Steps
data[date_column] = pd.to_datetime(data[date_column])
if time_interval == "daily":
data['month'] = data[date_column].map(lambda x: str(x.month))
data['day'] = data[date_column].map(lambda x: str(x.day))
elif time_interval == "weekly":
data['week'] = data[date_column].map(lambda x: str(x.week))
data['month'] = data[date_column].map(lambda x: str(x.month))
elif time_interval == "monthly":
data['month'] = data[date_column].map(lambda x: str(x.month))
elif time_interval == "yearly":
pass
data['trend'] = np.arange(1, data.shape[0]+1)
data.drop(columns=[date_column], inplace=True)
all_cols = set(data.columns) - set((date_column, target_column))
num_features = [col for col in all_cols if is_numeric(data[col])]
cat_features = [col for col in all_cols if col not in num_features]
data[cat_features] = data[cat_features].astype('category', copy=True)
self.train_data = data.iloc[:-forecasting_horizon]
self.test_data = data.iloc[-forecasting_horizon:]
# Initialization
self.s = setup(data=self.train_data, test_data=self.test_data, target=target_column,
numeric_features=num_features, categorical_features=cat_features,
categorical_imputation="mode", numeric_imputation="knn",
fold_strategy="timeseries", fold=fold,
session_id=session_id)
self.forcasting_horizon = forecasting_horizon
self.metric_to_opt=metric_to_opt
self.target_column = target_column
self.full_data = data.copy()
self.num_features = num_features
self.cat_features = cat_features
def get_stats(self):
return self.cat_features, self.num_features, self.train_data.describe()
def train_models(self):
best_model = compare_models(sort=self.metric_to_opt)
model_comp_df = pull()
self.best_model = tune_model(best_model, search_algorithm='grid')
best_mod_param_df = pd.DataFrame.from_dict(self.best_model.get_params(), orient='index')
return model_comp_df, best_mod_param_df, self.best_model
def get_plots(self):
plots_dict = {}
plots_name_dict = {'residuals': 'Residuals Plot', 'error': 'Prediction Error Plot',
'cooks': 'Cooks Distance Plot', 'rfe': 'Recursive Feat. Selection',
'learning': 'Learning Curve', 'vc': 'Validation Curve',
'manifold': 'Manifold Learning', 'feature_all': 'Feature Importance',
'tree': 'Decision Tree'} #'parameter': 'Model Hyperparameter',
for k,v in plots_name_dict.items():
# All plots are not available for all models
try:
plots_dict[v] = plot_model(self.best_model, plot = k, save=True)
except Exception as e:
print(f"[PLOT EXCEPTION] ==> {type(e).__name__} : {e}")
return plots_dict
def get_predictions(self):
self.y_hat = predict_model(self.best_model)
return self.y_hat[["prediction_label"]]
def plot_insample_and_forecast(self):
self.y_hat_all = predict_model(self.best_model, data=self.full_data)
outsam = px.line(self.y_hat, y=[self.target_column, 'prediction_label'], x='trend',
title="Actual vs Out-of-Sample Forecast")
insam = px.line(self.y_hat_all, y=[self.target_column, 'prediction_label'], x='trend',
title="Actual vs Forecast (Insample)")
return insam, outsam