Regresión Fama-Macbeth en Python
- Regresión de Fama-Macbeth y su importancia
- Pasos para implementar la regresión Fama-Macbeth en Python
-
Usa
LinearModels
para implementar la regresión Fama-Macbeth en Python - Enfoque alternativo para implementar la regresión de Fama-Macbeth en Python
El artículo de hoy educa sobre la regresión de Fama-Macbeth, su importancia y su implementación.
Regresión de Fama-Macbeth y su importancia
En las teorías de valoración de activos, utilizamos factores de riesgo para describir los rendimientos de los activos. Estos factores de riesgo pueden ser microeconómicos o macroeconómicos.
Los factores de riesgo microeconómicos incluyen el tamaño de la empresa y las diferentes métricas financieras de la empresa, mientras que los factores de riesgo macroeconómicos son la inflación del consumidor y el desempleo.
La regresión de Fama-Macbeth es un modelo de regresión de dos pasos que se utiliza para probar los modelos de valoración de activos. Es un enfoque práctico para medir qué tan correctamente estos factores de riesgo describen los rendimientos de la cartera o de los activos.
Este modelo es útil para determinar la prima de riesgo asociada a la exposición a estos factores.
Ahora, el punto es, ¿por qué llamamos a Fama-Macbeth, un modelo de regresión de dos pasos? Descubramos estos pasos a continuación.
- Este paso consiste en realizar una regresión del rendimiento de cada activo frente a uno o varios factores de riesgo utilizando el enfoque de series temporales. Obtenemos la exposición de retorno a cada factor conocido como
betas
,cargas de factor
oexposición de factor
. - Este paso se trata de hacer una regresión de los rendimientos de todos los activos contra los activos
betas
adquiridos en el paso anterior (paso 1) usando un enfoque transversal. Aquí, obtenemos una prima de riesgo para cada factor.
La prima proyectada a lo largo del tiempo para la exposición de la unidad a cada factor de riesgo se calcula promediando los coeficientes una vez para cada elemento, según Fama y Macbeth.
Pasos para implementar la regresión Fama-Macbeth en Python
Según la actualización para reflejar las circunstancias de la biblioteca para Fama-Macbeth a partir del otoño de 2018, fama_macbeth
se ha erradicado del módulo pandas
de Python desde hace un tiempo.
Entonces, ¿cómo podemos implementar Fama-Macbeth si estamos trabajando con Python? Tenemos los siguientes dos enfoques que aprenderemos uno por uno en este tutorial.
- Podemos usar la función
fama_macbeth
enLinearModels
si usamos la versión 3 de Python. - Si no estamos obligados a usar
LinearModels
, o si estamos usando la versión 2 de Python, lo más probable es que el mejor caso sea escribir nuestra implementación para Fama-Macbeth.
Usa LinearModels
para implementar la regresión Fama-Macbeth en Python
-
Importe los módulos y bibliotecas necesarios.
import pandas as pd import numpy as np from pathlib import Path from linearmodels.asset_pricing import LinearFactorModel from statsmodels.api import OLS, add_constant import matplotlib.pyplot as plt import pandas_datareader.data as web import seaborn as sns import warnings warnings.filterwarnings("ignore") sns.set_style("whitegrid")
Primero, importamos todos los módulos y bibliotecas que necesitaremos para implementar Fama-Macbeth usando
LinearModels
. A continuación se hace una breve descripción de todos ellos:- Importamos
pandas
para trabajar con data frames ynumpy
para arrays. - El
pathlib
crea una ruta al archivo especificado colocando este script específico en el objetoPath
. - Importamos
LinearFactorModel
desdelinearmodels.asset_pricing
. Los modelos factoriales lineales relacionan la rentabilidad del activo con valores de un número restringido/limitado defactores
, con una relación que se describe mediante una ecuación lineal. - A continuación, importamos
OLS
para evaluar el modelo de regresión lineal yadd_constant
para añadir una columna de unos al array. Puede obtener más información sobrestatsmodels
aquí. - Después de eso, importamos
pandas_datareader
para acceder a los últimos datos remotos para usar conpandas
. Funciona para varias versiones depandas
. - Importamos las bibliotecas
matplotlib
yseaborn
para el trazado y visualización de datos. - Importamos
Warnings
para usar su métodofilterwarnings()
, que ignora las advertencias. - Por último, utilizamos el método
set_style()
del móduloseaborn
, que establece los parámetros que controlan el estilo general de las tramas.
- Importamos
-
Acceda al conjunto de datos de cartera de investigación y factor de riesgo remoto.
ff_research_data_five_factor = "F-F_Research_Data_5_Factors_2x3" ff_factor_dataset = web.DataReader( ff_research_data_five_factor, "famafrench", start="2010", end="2017-12" )[0]
Aquí, estamos utilizando el conjunto de datos de cartera de investigación y factores de riesgo actualizados (los cinco factores Fama-French) disponibles en su sitio web para volver a una frecuencia mensual que obtenemos para
2010-2017
como se indicó anteriormente.Usamos
DataReader()
para extraer datos del recurso de Internet especificado en el marco de datospandas
, que esff_factor_dataset
en nuestra valla de código. ElDataReader()
admite varias fuentes, por ejemplo,Tiingo
,IEX
,Alpha Vantage
y más que puede leer en esta página.print("OUTPUT for info(): \n") print(ff_factor_dataset.info())
A continuación, usamos los métodos
df.info()
ydf.describe()
dondeinfo()
imprime la información del marco de datos que incluye el número de columnas, tipos de datos de columnas, etiquetas de columna, índice de rango, memoria uso y el número de celdas en cada columna (valores no nulos).Puede ver la salida producida por
info()
a continuación.PRODUCCIÓN:
OUTPUT for info(): <class 'pandas.core.frame.DataFrame'> PeriodIndex: 96 entries, 2010-01 to 2017-12 Freq: M Data columns (total 6 columns): # Column Non-Null Count Dtype --- ------ -------------- ----- 0 Mkt-RF 96 non-null float64 1 SMB 96 non-null float64 2 HML 96 non-null float64 3 RMW 96 non-null float64 4 CMA 96 non-null float64 5 RF 96 non-null float64 dtypes: float64(6) memory usage: 5.2 KB None
A continuación, usamos el método
describe()
de la siguiente manera.print("OUTPUT for describe(): \n") print(ff_factor_dataset.describe())
El método
describe()
muestra el resumen estadístico del marco de datos; también podemos usar este método para la serie Python. Este resumen estadístico contiene la media, la mediana, el conteo, la desviación estándar, los valores percentiles de las columnas y el mínimo y el máximo.Puede encontrar el resultado del método
describe()
a continuación.PRODUCCIÓN:
OUTPUT for describe(): Mkt-RF SMB HML RMW CMA RF count 96.000000 96.000000 96.000000 96.000000 96.000000 96.000000 mean 1.158438 0.060000 -0.049271 0.129896 0.047708 0.012604 std 3.580012 2.300292 2.202912 1.581930 1.413033 0.022583 min -7.890000 -4.580000 -4.700000 -3.880000 -3.240000 0.000000 25% -0.917500 -1.670000 -1.665000 -1.075000 -0.952500 0.000000 50% 1.235000 0.200000 -0.275000 0.210000 0.010000 0.000000 75% 3.197500 1.582500 1.205000 1.235000 0.930000 0.010000 max 11.350000 7.040000 8.190000 3.480000 3.690000 0.090000
-
Acceda a 17 carteras de la industria y reste la tasa del factor de riesgo.
ff_industry_portfolio = "17_Industry_Portfolios" ff_industry_portfolio_dataset = web.DataReader( ff_industry_portfolio, "famafrench", start="2010", end="2017-12" )[0] ff_industry_portfolio_dataset = ff_industry_portfolio_dataset.sub( ff_factor_dataset.RF, axis=0 )
Aquí, usamos
DataReader()
para acceder a 17 carteras o activos de la industria con una frecuencia mensual y restamos la tasasin riesgo
(RF
) del marco de datos devuelto porDataReader()
. ¿Por qué? Es porque el modelo factorial trabaja con los rendimientos en exceso.Ahora, usaremos el método
info()
para obtener información sobre el marco de datos encadenado.print(ff_industry_portfolio_dataset.info())
PRODUCCIÓN:
<class 'pandas.core.frame.DataFrame'> PeriodIndex: 96 entries, 2010-01 to 2017-12 Freq: M Data columns (total 17 columns): # Column Non-Null Count Dtype --- ------ -------------- ----- 0 Food 96 non-null float64 1 Mines 96 non-null float64 2 Oil 96 non-null float64 3 Clths 96 non-null float64 4 Durbl 96 non-null float64 5 Chems 96 non-null float64 6 Cnsum 96 non-null float64 7 Cnstr 96 non-null float64 8 Steel 96 non-null float64 9 FabPr 96 non-null float64 10 Machn 96 non-null float64 11 Cars 96 non-null float64 12 Trans 96 non-null float64 13 Utils 96 non-null float64 14 Rtail 96 non-null float64 15 Finan 96 non-null float64 16 Other 96 non-null float64 dtypes: float64(17) memory usage: 13.5 KB None
De manera similar, describimos este marco de datos utilizando el método
describe()
.print(ff_industry_portfolio_dataset.describe())
PRODUCCIÓN:
Food Mines Oil Clths Durbl Chems \ count 96.000000 96.000000 96.000000 96.000000 96.000000 96.000000 mean 1.046771 0.202917 0.597187 1.395833 1.151458 1.305000 std 2.800555 7.904401 5.480938 5.024408 5.163951 5.594161 min -5.170000 -24.380000 -11.680000 -10.000000 -13.160000 -17.390000 25% -0.785000 -5.840000 -3.117500 -1.865000 -2.100000 -1.445000 50% 0.920000 -0.435000 0.985000 1.160000 1.225000 1.435000 75% 3.187500 5.727500 4.152500 3.857500 4.160000 4.442500 max 6.670000 21.940000 15.940000 17.190000 16.610000 18.370000 Cnsum Cnstr Steel FabPr Machn Cars \ count 96.000000 96.000000 96.000000 96.000000 96.000000 96.000000 mean 1.186979 1.735521 0.559167 1.350521 1.217708 1.279479 std 3.142989 5.243314 7.389679 4.694408 4.798098 5.719351 min -7.150000 -14.160000 -20.490000 -11.960000 -9.070000 -11.650000 25% -0.855000 -2.410000 -4.395000 -1.447500 -2.062500 -1.245000 50% 1.465000 2.175000 0.660000 1.485000 1.525000 0.635000 75% 3.302500 5.557500 4.212500 3.837500 4.580000 4.802500 max 8.260000 15.510000 21.350000 17.660000 14.750000 20.860000 Trans Utils Rtail Finan Other count 96.000000 96.000000 96.000000 96.000000 96.000000 mean 1.463750 0.896458 1.233958 1.248646 1.290938 std 4.143005 3.233107 3.512518 4.839150 3.697608 min -8.560000 -6.990000 -9.180000 -11.140000 -7.890000 25% -0.810000 -0.737500 -0.952500 -1.462500 -1.090000 50% 1.480000 1.240000 0.865000 1.910000 1.660000 75% 4.242500 2.965000 3.370000 4.100000 3.485000 max 12.980000 7.840000 12.440000 13.410000 10.770000
-
Calcule los rendimientos en exceso.
Antes de avanzar hacia el cálculo de los rendimientos en exceso, debemos realizar algunos pasos más.
data_store = Path("./data/assets.h5") wiki_prices_df = pd.read_csv( "./dataset/wiki_prices.csv", parse_dates=["date"], index_col=["date", "ticker"], infer_datetime_format=True, ).sort_index() us_equities_data_df = pd.read_csv("./dataset/us_equities_data.csv") with pd.HDFStore(data_store) as hdf_store: hdf_store.put("quandl/wiki/prices", wiki_prices_df) with pd.HDFStore(data_store) as hdf_store: hdf_store.put("us_equities/stocks", us_equities_data_df.set_index("ticker"))
Primero, creamos un archivo
assets.h5
en una carpeta dedatos
que reside en el directorio actual. A continuación, usamos el métodoread_csv()
para leer los archivoswiki_prices.csv
yus_equities_data.csv
en la carpetadataset
del mismo directorio.Después de eso, usamos
HDFStore()
como se indicó anteriormente para almacenar datos en formatoHDF5
.with pd.HDFStore("./data/assets.h5") as hdf_store: prices = hdf_store["/quandl/wiki/prices"].adj_close.unstack().loc["2010":"2017"] equities = hdf_store["/us_equities/stocks"].drop_duplicates() sectors = equities.filter(prices.columns, axis=0).sector.to_dict() prices = prices.filter(sectors.keys()).dropna(how="all", axis=1) returns_df = prices.resample("M").last().pct_change().mul(100).to_period("M") returns_df = returns.dropna(how="all").dropna(axis=1) print(returns_df.info())
En la valla de código anterior, leemos
/quandl/wiki/prices
y/us_equities/stocks
que acabamos de almacenar en el archivoassets.h5
y los guardamos en las variablesprices
yequities
.Luego, aplicamos algunos filtros en “precios” y “acciones”, volvemos a muestrear y eliminamos los valores faltantes. Finalmente, imprimimos la información de un data frame
returns_df
usando el métodoinfo()
; Puedes ver la salida a continuación.PRODUCCIÓN:
<class 'pandas.core.frame.DataFrame'> PeriodIndex: 95 entries, 2010-02 to 2017-12 Freq: M Columns: 1986 entries, A to ZUMZ dtypes: float64(1986) memory usage: 1.4 MB None
Ahora, ejecute el siguiente código para alinear los datos.
ff_factor_dataset = ff_factor_dataset.loc[returns_df.index] ff_industry_portfolio_dataset = ff_industry_portfolio_dataset.loc[returns_df.index] print(ff_factor_dataset.describe())
PRODUCCIÓN:
Mkt-RF SMB HML RMW CMA RF count 95.000000 95.000000 95.000000 95.000000 95.000000 95.000000 mean 1.206000 0.057053 -0.054316 0.144632 0.043368 0.012737 std 3.568382 2.312313 2.214041 1.583685 1.419886 0.022665 min -7.890000 -4.580000 -4.700000 -3.880000 -3.240000 0.000000 25% -0.565000 -1.680000 -1.670000 -0.880000 -0.965000 0.000000 50% 1.290000 0.160000 -0.310000 0.270000 0.010000 0.000000 75% 3.265000 1.605000 1.220000 1.240000 0.940000 0.010000 max 11.350000 7.040000 8.190000 3.480000 3.690000 0.090000
Ahora, estamos listos para calcular los rendimientos en exceso.
excess_returns_df = returns_df.sub(ff_factor_dataset.RF, axis=0) excess_returns_df = excess_returns_df.clip( lower=np.percentile(excess_returns_df, 1), upper=np.percentile(excess_returns_df, 99), ) excess_returns_df.info()
En el bloque de código anterior, restamos el factor de riesgo del
ff_factor_dataset
y guardamos el marco de datos devuelto enexcess_returns_df
.A continuación, usamos el método
.clip()
que recorta los valores en los umbrales de entrada especificados. Por último, utiliceinfo()
para imprimir la información del marco de datosexcess_returns_df
.PRODUCCIÓN:
<class 'pandas.core.frame.DataFrame'> PeriodIndex: 95 entries, 2010-02 to 2017-12 Freq: M Columns: 1986 entries, A to ZUMZ dtypes: float64(1986) memory usage: 1.4 MB
Antes de pasar a la primera etapa de la regresión de Fama-Macbeth, usamos el método
.drop()
, que elimina la etiqueta especificada de columnas o filas. Tenga en cuenta queaxis=1
significa una caída desde una columna, yaxis=0
significa una caída desde las filas.ff_factor_dataset = ff_factor_dataset.drop("RF", axis=1) print(ff_factor_dataset.info())
PRODUCCIÓN:
<class 'pandas.core.frame.DataFrame'> PeriodIndex: 95 entries, 2010-02 to 2017-12 Freq: M Data columns (total 5 columns): # Column Non-Null Count Dtype --- ------ -------------- ----- 0 Mkt-RF 95 non-null float64 1 SMB 95 non-null float64 2 HML 95 non-null float64 3 RMW 95 non-null float64 4 CMA 95 non-null float64 dtypes: float64(5) memory usage: 4.5 KB None
-
Implemente el paso 1 de la regresión de Fama-Macbeth: Exposición de factores.
betas = [] for industry in ff_industry_portfolio_dataset: step_one = OLS( endog=ff_industry_portfolio_dataset.loc[ff_factor_dataset.index, industry], exog=add_constant(ff_factor_dataset), ).fit() betas.append(step_one.params.drop("const")) betas = pd.DataFrame( betas, columns=ff_factor_dataset.columns, index=ff_industry_portfolio_dataset.columns, ) print(betas.info())
El fragmento de código anterior implementa el primer paso de la regresión de Fama-Macbeth y accede a las estimaciones de carga de 17 factores. Aquí, usamos
OLS()
para evaluar el modelo de regresión lineal yadd_constant()
para agregar una columna de unos a la matriz.PRODUCCIÓN:
<class 'pandas.core.frame.DataFrame'> Index: 17 entries, Food to Other Data columns (total 5 columns): # Column Non-Null Count Dtype --- ------ -------------- ----- 0 Mkt-RF 17 non-null float64 1 SMB 17 non-null float64 2 HML 17 non-null float64 3 RMW 17 non-null float64 4 CMA 17 non-null float64 dtypes: float64(5) memory usage: 1.3+ KB None
-
Implemente la regresión de Fama-Macbeth paso 2: Prima de riesgo.
lambdas = [] for period in ff_industry_portfolio_dataset.index: step_two = OLS( endog=ff_industry_portfolio_dataset.loc[period, betas.index], exog=betas ).fit() lambdas.append(step_two.params) lambdas = pd.DataFrame( lambdas, index=ff_industry_portfolio_dataset.index, columns=betas.columns.tolist() ) print(lambdas.info())
En el segundo paso, realizamos noventa y seis regresiones de rendimientos de
período
para la sección cruzada de la cartera sobre cargas factoriales.PRODUCCIÓN:
<class 'pandas.core.frame.DataFrame'> PeriodIndex: 95 entries, 2010-02 to 2017-12 Freq: M Data columns (total 5 columns): # Column Non-Null Count Dtype --- ------ -------------- ----- 0 Mkt-RF 95 non-null float64 1 SMB 95 non-null float64 2 HML 95 non-null float64 3 RMW 95 non-null float64 4 CMA 95 non-null float64 dtypes: float64(5) memory usage: 6.5 KB None
Podemos visualizar los resultados de la siguiente manera:
window = 24 # here 24 is the number of months axis1 = plt.subplot2grid((1, 3), (0, 0)) axis2 = plt.subplot2grid((1, 3), (0, 1), colspan=2) lambdas.mean().sort_values().plot.barh(ax=axis1) lambdas.rolling(window).mean().dropna().plot( lw=1, figsize=(14, 5), sharey=True, ax=axis2 ) sns.despine() plt.tight_layout()
PRODUCCIÓN:
-
Implementa la regresión de Fama-Macbeth con el módulo
LinearModels
.model = LinearFactorModel( portfolios=ff_industry_portfolio_dataset, factors=ff_factor_dataset ) result = model.fit() print(result)
Aquí, usamos los
Modelos lineales
para implementar el procedimiento Fama-Macbeth de dos pasos que produce el siguiente resultado. Podemos usarprint(result.full_summary)
en lugar deprint(result)
para obtener el resumen completo.PRODUCCIÓN:
LinearFactorModel Estimation Summary ================================================================================ No. Test Portfolios: 17 R-squared: 0.6879 No. Factors: 5 J-statistic: 15.619 No. Observations: 95 P-value 0.2093 Date: Mon, Oct 24 2022 Distribution: chi2(12) Time: 20:53:52 Cov. Estimator: robust Risk Premia Estimates ============================================================================== Parameter Std. Err. T-stat P-value Lower CI Upper CI ------------------------------------------------------------------------------ Mkt-RF 1.2355 0.4098 3.0152 0.0026 0.4324 2.0386 SMB 0.0214 0.8687 0.0246 0.9804 -1.6813 1.7240 HML -1.1140 0.6213 -1.7931 0.0730 -2.3317 0.1037 RMW -0.2768 0.8133 -0.3403 0.7336 -1.8708 1.3172 CMA -0.5078 0.5666 -0.8962 0.3701 -1.6183 0.6027 ============================================================================== Covariance estimator: HeteroskedasticCovariance See full_summary for complete results
Enfoque alternativo para implementar la regresión de Fama-Macbeth en Python
Podemos usar este enfoque si no queremos usar Modelos lineales
o usar la versión 2 de Python.
-
Importe los módulos y bibliotecas.
import pandas as pd import numpy as np import statsmodels.formula.api as sm
Importamos
pandas
para trabajar con marcos de datos,numpy
para jugar con matrices ystatsmodels.formula.api
, que es una interfaz conveniente para especificar modelos a través de cadenas de fórmulas y marcos de datos. -
Leer y consultar el conjunto de datos.
Supongamos que tenemos activos/carteras de la industria francesa de Fama en el panel como se indica a continuación (también hemos calculado algunas variables, por ejemplo,
beta
yrendimientos
pasados para utilizar como nuestras variablesx
)data_df = pd.read_csv("industry_data.csv", parse_dates=["caldt"]) data_df.query("caldt == '1995-07-01'")
PRODUCCIÓN:
industry caldt ret beta r12to2 r36to13 18432 Aero 1995-07-01 6.26 0.9696 0.2755 0.3466 18433 Agric 1995-07-01 3.37 1.0412 0.1260 0.0581 18434 Autos 1995-07-01 2.42 1.0274 0.0293 0.2902 18435 Banks 1995-07-01 4.82 1.4985 0.1659 0.2951
-
Utilice
groupby()
para calcular el modelo de regresión transversal mes a mes.def ols_coefficient(x, formula): return sm.ols(formula, data=x).fit().params gamma_df = data_df.groupby("caldt").apply( ols_coefficient, "ret ~ 1 + beta + r12to2 + r36to13" ) gamma_df.head()
Aquí usamos
groupby
porque Fama-Macbeth implica calcular el modelo de regresión transversal exacto mes a mes. Podemos crear una función que acepte un marco de datos (que es devuelto porgroupby
) y una fórmulapastosa
; luego se ajustará al modelo y devolverá las estimaciones de los parámetros.PRODUCCIÓN:
Intercept beta r12to2 r36to13 caldt 1963-07-01 -1.497012 -0.765721 4.379128 -1.918083 1963-08-01 11.144169 -6.506291 5.961584 -2.598048 1963-09-01 -2.330966 -0.741550 10.508617 -4.377293 1963-10-01 0.441941 1.127567 5.478114 -2.057173 1963-11-01 3.380485 -4.792643 3.660940 -1.210426
-
Calcule la media y el error estándar de la media.
def fm_summary(p): s = p.describe().T s["std_error"] = s["std"] / np.sqrt(s["count"]) s["tstat"] = s["mean"] / s["std_error"] return s[["mean", "std_error", "tstat"]] fm_summary(gamma_df)
A continuación, calculamos la media, la prueba t (puede usar las estadísticas que desee) y el error estándar en la media, que es algo como lo anterior.
PRODUCCIÓN:
mean std_error tstat Intercept 0.754904 0.177291 4.258000 beta -0.012176 0.202629 -0.060092 r12to2 1.794548 0.356069 5.039896 r36to13 0.237873 0.186680 1.274230
-
Mejora la velocidad y utiliza la función
fama_macbeth
.def ols_np(dataset, y_var, x_var): gamma_df, _, _, _ = np.linalg.lstsq(dataset[x_var], dataset[y_var], rcond=None) return pd.Series(gamma_df)
Este paso es importante si nos preocupa la eficiencia. Si es así, podemos cambiar de
statsmodels
anumpy.linalg.lstsq
.Para realizar estimaciones
ols
, podemos escribir una función similar a la anterior. Tenga en cuenta que no estamos haciendo nada para verificar los rangos de estas matrices.Si está utilizando la versión anterior de
pandas
, entonces lo siguiente debería funcionar. Pongamos un ejemplo usandofama_macbeth
enpandas
.print(data_df) fm = pd.fama_macbeth(y=data_df["y"], x=data_df[["x"]]) print(fm)
Aquí, observe la estructura a continuación. El
fama_macbeth
quiere quex-var
ey-var
tengan un índice múltiple confecha
como primera variable e id deacción/empresa/entidad
como segunda variable en el índice.PRODUCCIÓN:
y x date id 2012-01-01 1 0.1 0.4 2 0.3 0.6 3 0.4 0.2 4 0.0 1.2 2012-02-01 1 0.2 0.7 2 0.4 0.5 3 0.2 0.1 4 0.1 0.0 2012-03-01 1 0.4 0.8 2 0.6 0.1 3 0.7 0.6 4 0.4 -0.1 ----------------------Summary of the Fama-Macbeth Analysis------------------------- Formula: Y ~ x + intercept # betas : 3 ----------------------Summary of the Estimated Coefficients------------------------ Variable Beta Std Err t-stat CI 2.5% CI 97.5% (x) -0.0227 0.1276 -0.18 -0.2728 0.2273 (intercept) 0.3531 0.0842 4.19 0.1881 0.5181 --------------------------------End of the Summary---------------------------------
Tenga en cuenta que estamos llamando a
fm.summary
simplemente imprimiendofm
como lo hicimos en la cerca de código anterior. Además, elfama_macbeth
agrega automáticamente elintercepto
yx-var
debe ser un marco de datos.Podemos hacer lo siguiente si no queremos tener “intercepción”.
fm = pd.fama_macbeth(y=data_df["y"], x=data_df[["x"]], intercept=False)