def generate_final_predictions(df_coords, lag_order=3, display=False): ''' Uses the best lag_order (from testing_harness) to train the full model and forecast mean coordinates for the years 2022 and 2023. Returns a DF ''' model = VAR(endog=df_coords) model = model.fit(lag_order) forecast = model.forecast(model.y, steps=2) df_forecast = pd.DataFrame(forecast, columns=['future_latitude', 'future_longitude']) df_forecast['year'] = [2022, 2023] df_forecast = df_forecast[['year', 'future_latitude', 'future_longitude']] if display: print() print('Final model information:') print() print(model.summary()) print() print('Future hotspot forecasts:') print() print(df_forecast) return df_forecast
def test_summaries_exog(reset_randomstate): y = np.random.standard_normal((500, 6)) df = pd.DataFrame(y) cols = (["endog_{0}".format(i) for i in range(2)] + ["exog_{0}".format(i) for i in range(4)]) df.columns = cols df.index = pd.date_range('1-1-1950', periods=500, freq="MS") endog = df.iloc[:, :2] exog = df.iloc[:, 2:] res = VAR(endog=endog, exog=exog).fit(maxlags=0) summ = res.summary().summary assert 'exog_0' in summ assert 'exog_1' in summ assert 'exog_2' in summ assert 'exog_3' in summ res = VAR(endog=endog, exog=exog).fit(maxlags=2) summ = res.summary().summary assert 'exog_0' in summ assert 'exog_1' in summ assert 'exog_2' in summ assert 'exog_3' in summ
class dieboldLi(nelsonSiegel): """ The dieboldLi class generates a curve based on the D&L parameters. This class is also capable of calibrating the parameters based on the input data. This class inherits the features of the nelsonSiegel class. """ def __init__(self, parameters=None): super(dieboldLi, self).__init__(parameters=parameters) self._parametersHistorical = None self._tenorsHistorical = None self._yieldsHistorical = None def parametersHistorical(self): """ This method shows the historical values of the parameters: tau, level, slope and curvature. """ return pd.DataFrame(self._parametersHistorical, columns=('tau', 'b0', 'b1', 'b2'), index=pd.to_datetime(self._dates)) def calibrateParametersHistorical(self, tenors, yields, tau=1): """ This method calculates the historical parameters for the provided tenors and yields. The inputs are an array of tenors, an array of yields, and tau (an integer). inputs: array, array, float output: DataFrame """ yieldCurve = yields.values param = [] x0 = np.array([0.1, 0.1, 0.1]) for y in yieldCurve: x0 = leastsq(self.nelsonSiegelCurveResiduals, x0, args=(tenors, y, tau)) x0 = x0[0] param.append([tau] + x0.tolist()) self._tenorsHistorical = tenors self._yieldsHistorical = yields self._parametersHistorical = param return param def parametersAR(self, lag=1): # OLS(self.parametersHistorical()['b0'], self.parametersHistorical()['b0'][]) # self._arModel = (AR(self.parametersHistorical()['b0']).fit(lag), AR(self.parametersHistorical()['b1']).fit(lag), AR(self.parametersHistorical()['b2']).fit(lag)) self._varModel = VAR(self.parametersHistorical()[['b0', 'b1', 'b2']]).fit(lag) self._varModel.summary() return True def calibrateDieboldLi(self, yields, tenor, tau=1, lag=1): yieldCurve = yields tenors = tenor par = self.calibrateParametersHistorical(np.array(tenors), yieldCurve, tau=tau) self._dates = yields.index self.parametersAR(lag=lag) return par def setNSParameters(self, position=-1): self._parameters = self._parametersHistorical[position] self._tenors = self._tenorsHistorical[position] self._yields = self._yieldsHistorical[position] def forecastDLParameters(self, initialParameters=None, steps=1, alpha=0.05): #Función que proyecta parámetros Diebold Li a futuro """ inputs : array, int output: array """ assert not isinstance( self._varModel, VAR), "Theres no model yet. Run calibrateDieboldLi first" if initialParameters is None: initialParameters = self._parameters parameters = np.array([initialParameters[1:4]]) return self._varModel.forecast_interval(parameters, steps, alpha=alpha), initialParameters def plotForecastedCurve(self, tenor, initialParameters=None, steps=1, alpha=0.05, style='fivethirtyeight', error=True): #Función que grafica forecast de curva, junto con error forecast, initialParameters = self.forecastDLParameters( initialParameters=initialParameters, steps=steps, alpha=alpha) baseParameter = initialParameters fcParameter = [baseParameter[0]] + forecast[0][-1].tolist() topParameter = [baseParameter[0]] + forecast[1][-1].tolist() bottomParameter = [baseParameter[0]] + forecast[2][-1].tolist() with plt.style.context(style, after_reset=True): plt.plot(tenor, self.nelsonSiegelCurve(tenor, baseParameter), linewidth=2.0) plt.plot(tenor, self.nelsonSiegelCurve(tenor, fcParameter), 'w.') if error: plt.plot(tenor, self.nelsonSiegelCurve(tenor, topParameter), 'w--') plt.plot(tenor, self.nelsonSiegelCurve(tenor, bottomParameter), 'w--') plt.text(0.2, 0.7, """$\\alpha$ = %s""" % alpha, transform=plt.gca().transAxes) plt.ylabel('%') plt.title('%s Months Projection for %s calibrated curve' % (str(steps), self._currency)) plt.show()
class yieldCurve(object): def __init__(self): self.parameters = [] def nelsonSiegelCurve(self, tenors, parameters = None): #A partir de los tenores ingresados entrega los puntos de la curva de tasas para los parámetros ingresados o lo guardados """ Based on the provided tenors and parameters, this method calculates the rates for each point of the curve. The input can be an array (of tenors) and a list or another array (of parameters). The output is an array that contains the rates for each of the tenors. input: array, list or array output: array """ if parameters is None: parameters = self._parameters if parameters is None: print("""There are no parameters calibrated for the curve. Run calibrateParameters first.""") return False b0, b1, b2 = parameters[1:4] tau = float(parameters[0]) yc = b0 + b1*(1 - np.exp(-tenors/tau))/(tenors/tau) + b2*((1 - np.exp(-tenors/tau))/(tenors/tau) - np.exp(-tenors/tau)) return yc def nelsonSiegelCurveResiduals(self, p, tenors, yields, tau): """ The residuals method calculates the error between the actual yields and what the model computes with the parameters obtained from the least square optimization. the inputs are an array of parameters, an array of tenors, an array of yields and the parameter tau (integer). inputs: array, array, array, int output: array """ b0, b1, b2 = p err = yields - self.nelsonSiegelCurve(tenors, [tau, b0, b1, b2]) err = err.astype(float) return err def calibrateCurveParametersHistorical(self, tenors, yields, tau = 1): """ This method calculates the historical parameters for the provided tenors and yields. The inputs are an array of tenors, an array of yields, and tau (an integer). inputs: array, array, float output: DataFrame """ yieldCurve = yields.values.astype(float) param= [] x0 = np.array([0.1, 0.1, 0.1]) for y in yieldCurve: x0 = leastsq(self.nelsonSiegelCurveResiduals, x0, args = (tenors, y, tau)) x0 = x0[0] param.append([tau] + x0.tolist()) self._tenorsHistorical = tenors self._yieldsHistorical = yields self._parametersHistorical = param return param def parametersVAR(self, tenors, yields, lag = 1, steps = 1, alpha = 0.01): params = pd.DataFrame(data=self.calibrateCurveParametersHistorical(tenors, yields),columns=['tau','b0','b1','b2'], index = yields.index) self._varModel = VAR(params[['b0','b1','b2']]).fit(lag) self._varModel.summary() fparam = self._varModel.forecast_interval(params.tail(1)[['b0','b1','b2']].values, steps, alpha = alpha) return fparam, params.tail(1)[['b0','b1','b2']].values def plotForecastedCurve(self, tenors, yields, steps = 1, alpha = 0.05, tau = 1, style = 'fivethirtyeight', error = True): #Función que grafica forecast de curva, junto con error forecast, initialParameters = self.parametersVAR(tenors, yields, steps = steps, alpha = alpha) baseParameter = initialParameters.tolist() fcParameter = forecast[0].tolist() topParameter = forecast[1].tolist() bottomParameter = forecast[2].tolist() shock_level = -0.25*1 shock_slope = 0 shock_curvature = 0 with plt.style.context(style, after_reset = True): plt.plot(tenors,yields.tail(1).values[0],'g.') plt.plot(tenors,self.nelsonSiegelCurve(tenors, [tau, baseParameter[0][0] + shock_level, baseParameter[0][1], baseParameter[0][2]]), linewidth = 1.0) plt.plot(tenors,self.nelsonSiegelCurve(tenors, [tau, fcParameter[0][0] + shock_level, fcParameter[0][1], fcParameter[0][2]]), 'b.') if error: plt.plot(tenors,self.nelsonSiegelCurve(tenors, [tau, topParameter[0][0] + shock_level, topParameter[0][1], topParameter[0][2]]), 'b--', linewidth = 1.0) plt.plot(tenors,self.nelsonSiegelCurve(tenors, [tau, bottomParameter[0][0] + shock_level, bottomParameter[0][1], bottomParameter[0][2]]), 'b--', linewidth = 1.0) # plt.text(0.2, 0.8, """$\\alpha$ = %s"""%alpha, transform = plt.gca().transAxes) plt.ylabel('%') # plt.title('%s Months Projection for CLP calibrated curve'%(str(steps))) plt.show()