<jupyter_start><jupyter_text>Simulación de procesos financieros. **Nombres:** <NAME>, <NAME>**Fecha:** 07 de mayo del 2021.**Expediente** : if72622, if721861.**Profesor:** <NAME>. Tarea 11: Clase 24 [Liga al repositorio](https://github.com/PintorOD1997/ProyectoConjunto_LEspinosa_DPintor.git)  Enunciado de tarea Realizar la valuación de las opciones barrera para las acciones de Microsoft, siguiendo los siguientes lineamientos:1. Realizar la valuación para el tipo de opción barrera 'CALL'- down-and-out, usando la suposición de rendimientos normales y usando el método del histograma. Para ambas valuaciones, comparar los resultados de la evaluación obtenida con los resultados obtenidos por la valuación Europea. Como se realizó en clase.2. Repetir el inciso anterior pero en esta ocasión para el caso de 'PUT'- Up-and-out.**Nota:** Analice los datos descargados y según el método ya sea `down-and-out` o `Up-and-out` defina un strike price usando la volatility smile vista en la clase de opciones europeas y basado en el spot price y el strike defina una barrera adecuada.Se habilitará un enlace en canvas para subir un cuaderno de python, con la solución.**Criterio de revisión.**> Se te calificará de acuerdo a los resultados finales que reportes, basados en tu análisis.  Solución Lyha Espinosa<jupyter_code>#importar los paquetes que se van a usar
import pandas as pd
import pandas_datareader.data as web
import numpy as np
import datetime
import matplotlib.pyplot as plt
import scipy.stats as st
import seaborn as sns
%matplotlib inline
#algunas opciones para Pandas
pd.set_option('display.notebook_repr_html', True)
pd.set_option('display.max_columns', 6)
pd.set_option('display.max_rows', 10)
pd.set_option('display.width', 78)
pd.set_option('precision', 3)
# Función para descargar precios de cierre ajustados:
def get_adj_closes(tickers, start_date=None, end_date=None):
    # Fecha inicio por defecto (start_date='2010-01-01') y fecha fin por defecto (end_date=today)
    # Descargamos DataFrame con todos los datos
    closes = web.DataReader(name=tickers, data_source='yahoo', start=start_date, end=end_date)
    # Solo necesitamos los precios ajustados en el cierre
    closes = closes['Adj Close']
    # Se ordenan los índices de manera ascendente
    closes.sort_index(inplace=True)
    return closes

####### Calculation of log-returns
def calc_daily_ret(closes):
    return np.log(closes/closes.shift(1)).dropna()<jupyter_output><empty_output><jupyter_text>1. Opción barrera 'CALL'- down-and-out<jupyter_code>closes = get_adj_closes(['MSFT'], '2017-01-01')
closes_micro = closes.loc[:,'MSFT']
closes_micro.plot()<jupyter_output><empty_output><jupyter_text>Calcular Rendimientos<jupyter_code>ret_micro = calc_daily_ret(closes_micro)<jupyter_output><empty_output><jupyter_text>Datos de opciones<jupyter_code>micro = web.YahooOptions('MSFT')
micro_opt = micro.get_all_data().reset_index()
micro_opt.set_index('Expiry')<jupyter_output><empty_output><jupyter_text>Elegir una fecha para seleccionar las opciones de call y encontrar nuestro strike price La elección de la fecha es debido a que el cliente esta interesado en obtener rentabilidad cada año, para asegurar esto se firman opciones para asegurar que a inicios del 2022 se tenga pactado un precio especifico.<jupyter_code>fecha1 = '2022-01-21'
call_f1 = micro_opt.loc[(micro_opt.Expiry== fecha1) & (micro_opt.Type=='call')]
call_f1<jupyter_output><empty_output><jupyter_text>Sonrisa de volatilidad<jupyter_code>ax = call_f1.set_index('Strike').loc[:, 'IV'].plot(figsize=(8,6))
ax.axvline(call_f1.Underlying_Price.iloc[0], color='g');<jupyter_output><empty_output><jupyter_text>Al graficar las opciones call que vencen en la fecha deseada nos damos cuenta que el strike optimo según la sonrisa de volatilidad que se crea en la gráfica es de aproximadamente 255   Opción que deseamos valuar  Se elige una opción tipo call debido a que queremos comprar en la fecha determinada al precio de ejercicio determinado, dado que microsoft va a la laza se desea pactar un precio para cubrirnos en caso de que suba demasiado su precio. Se desea asegurar un precio de compra.<jupyter_code>K = 255
opt_deseada = micro_opt.loc[(micro_opt.Type=='call') & (micro_opt.Strike==K) & (micro_opt.Expiry=='2022-01-21')]
opt_deseada
opt_valuar = opt_deseada.loc[list(opt_deseada.index)[0]]
# información de la opción
opt_valuar['JSON']<jupyter_output><empty_output><jupyter_text>Simulación de precios Modelo Normal de rendimientos<jupyter_code>mu = ret_micro.mean()
sigma = ret_micro.std()
r = 0.0006/360
mu, sigma, r
from datetime import date

# Datos de la opción y del día de actual
today = pd.Timestamp(date.today())
expiry = opt_valuar.Expiry

# Fechas desde el día de hoy hasta la fecha de cierre del contrato (considerando unicamente los días hábiles)
dates = pd.date_range(start=today, end=expiry, freq='B')

# Cantidad de escenarios a simular para el método de montecarlo
ndays = len(dates)
nscen = 10000

K = opt_valuar.Strike
S0 = closes_micro.iloc[-1]
sim_ret = pd.DataFrame(sigma*np.random.randn(ndays,nscen)+r,index=dates)
sim_closes = S0*np.exp(sim_ret.cumsum())<jupyter_output><empty_output><jupyter_text>Valuación de la opción basandonos en la función de pago correspondiente EUROPEA<jupyter_code>strike = K
call=pd.DataFrame({'Prima':np.exp(-r*ndays)*np.fmax(sim_closes - strike, 0).mean(axis=1)}, index=dates)
call.plot();
# INTERVALOS DE CONFIANZA
confianza = 0.95
sigma_est = sim_closes.iloc[-1].sem()
mean_est = call.iloc[-1].Prima
# i1 = st.t.interval(confianza,nscen-1, loc=mean_est, scale=sigma_est)
i2 = st.norm.interval(confianza, loc=mean_est, scale=sigma_est)
call.iloc[-1], print(i2)<jupyter_output>(26.56669301327338, 29.11238296014053)<jupyter_text>Histograma de rendimietos<jupyter_code># Centro mis datos en mi tasa libre de riesgo
freq, values = np.histogram(ret_micro-mu+r, bins=10000)
# freq = freq.astype('float32')
prob = freq/np.sum(freq)

# Datos de la opción y del día de actual
today = pd.Timestamp(date.today())
expiry = opt_valuar.Expiry

# Fechas desde el día de hoy hasta la fecha de cierre del contrato (considerando unicamente los días hábiles)
dates = pd.date_range(start=today, end=expiry, freq='B')

# Cantidad de escenarios a simular para el método de montecarlo
ndays = len(dates)
nscen = 10000

K = opt_valuar.Strike
S0 = closes_micro.iloc[-1]

ret = np.random.choice(values[1:], (ndays,nscen), p=prob)
sim_ret_hist = pd.DataFrame(ret, index=dates)
sim_closes_hist = S0*np.exp(sim_ret_hist.cumsum())
strike = pd.DataFrame(K*np.ones([ndays,nscen]),index=dates)
call_hist=pd.DataFrame({'Prima':np.exp(-r*ndays)*np.fmax(sim_closes_hist-strike,np.zeros([ndays,nscen])).T.mean()},index=dates)
call_hist.plot();
confianza = 0.95
sigma_est = sim_closes_hist.iloc[-1].sem()
mean_est = call_hist.iloc[-1].Prima
# i1 = st.t.interval(confianza,nscen-1, loc=mean_est, scale=sigma_est)
i2 = st.norm.interval(confianza, loc=mean_est, scale=sigma_est)
call_hist.iloc[-1], print(i2)
opt_valuar['JSON']['lastPrice']<jupyter_output><empty_output><jupyter_text>Valuación opcion down-and-out Modelos normal de rendimietos<jupyter_code>mu = ret_micro.mean()
sigma = ret_micro.std()
r = 0.0006/360
mu, sigma, r
# Datos de la opción y del día de actual
today = pd.Timestamp(date.today())
expiry = opt_valuar.Expiry

# Fechas desde el día de hoy hasta la fecha de cierre del contrato (considerando unicamente los días hábiles)
dates = pd.date_range(start = today, end = expiry, freq='B')

# Cantidad de escenarios a simular para el método de montecarlo
ndays = len(dates)
nscen = 10000

K = opt_valuar.Strike
S0 = closes_micro.iloc[-1]

sim_ret = pd.DataFrame(sigma*np.random.randn(ndays,nscen)+r,index=dates)
sim_closes = S0*np.exp(sim_ret.cumsum())
S0<jupyter_output><empty_output><jupyter_text>Se elige esta barrera porque de esta manera se le brinda un mayor control al cliente sobre las pérdidas potenciales en las que podría incurrir después. El precio de la barrera se fija en 225 (por debajo del strike price) dado que analizando el comportamineto de la acción en el mercado las probabilidades de que toque la barrera no son muy altas. Al usar una barrera abaratamos el precio de la prima de la opción<jupyter_code>pd.set_option('display.max_columns', 15)

# Precio barrera
B = 225

# Función de desactivación (knock-out) DOWN AND OUT
# Si en algún momento el precio toca la barrera la opción se desactiva
I = (sim_closes > B).cumprod(axis=0)  > 0
I<jupyter_output><empty_output><jupyter_text>Valuación call down and out<jupyter_code>K = opt_valuar.Strike
S0 = opt_valuar.Underlying_Price
K, S0
# Definir barrera
B = 225
# Crear función indicadora
I = (sim_closes > B).cumprod(axis=0) > 0
# Definir strike
strike = K
# Calcular la prima de una opción Europea
call = pd.DataFrame({'Prima Europea':np.exp(-r*ndays)*np.fmax(sim_closes - strike, 0)
                     .mean(axis=1)},index=dates)
# Calcular la prima de una opción barrera
calldo = pd.DataFrame({'Prima down-and-out':np.exp(-r*ndays)*(I * np.fmax(sim_closes - strike, 0))
                       .mean(axis=1)},index=dates)
# Graficar el resultado de las dos primas previamente valuadas
ax = calldo.plot();
call.plot(ax=ax);
call.iloc[-1], calldo.iloc[-1]<jupyter_output><empty_output><jupyter_text>Histograma<jupyter_code># Definir barrera
B = 225
# Crear función indicadora
I = (sim_closes > B).cumprod(axis=0) > 0
# Definir strike
strike = K
# Calcular la prima de una opción Europea
call_hist = pd.DataFrame({'Prima Europea':np.exp(-r*ndays)*np.fmax(sim_closes_hist - strike, 0)
                     .mean(axis=1)},index=dates)
# Calcular la prima de una opción barrera
call_hist_do = pd.DataFrame({'Prima down-and-out':np.exp(-r*ndays)*(I * np.fmax(sim_closes_hist - strike, 0))
                       .mean(axis=1)},index=dates)
# Graficar el resultado de las dos primas previamente valuadas
ax = call_hist_do.plot();
call_hist.plot(ax=ax);
call_hist.iloc[-1], call_hist_do.iloc[-1]<jupyter_output><empty_output><jupyter_text>Podemos observar que la prima de la opción se abarata al poner una barrera, si bien no es mucha diferencia de precios pero si es una diferencia significativa. Al comprador le beneficia usar una opción barrera, ya que las porbabilidades de que la opción se desactive no son altas y el precio de la prima de la opción es menor que el de una opción europea. Con el método del histograma la prima se abarata mucho más que si usamos rendimientos normales.   2. Opción barrera 'PUT'- Up-and-out  Elegir una fecha para seleccionar las opciones de y encontrar nuestro strike price La elección de la fecha es debido a que el cliente esta interesado en obtener rentabilidad cada año, para asegurar esto se firman opciones para asegurar que a inicios del 2022 se tenga pactado un precio de venta especifico.<jupyter_code>fecha1 = '2022-01-21'
put_f1 = micro_opt.loc[(micro_opt.Expiry== fecha1) & (micro_opt.Type=='put')]
put_f1<jupyter_output><empty_output><jupyter_text>Sonrisa de volatilidad<jupyter_code>ax = put_f1.set_index('Strike').loc[:, 'IV'].plot(figsize=(8,6))
ax.axvline(put_f1.Underlying_Price.iloc[0], color='g');<jupyter_output><empty_output><jupyter_text>Al graficar las opciones call que vencen en la fecha deseada nos damos cuenta que el strike optimo según la sonrisa de volatilidad que se crea en la gráfica es de aproximadamente 250 Opción que deseamos valuarSe elige una opción tipo put debido a que queremos vender en la fecha determinada al precio de ejercicio determinado, microsoft va a alza pero se desea pactar un precio para cubrirnos en caso de que baje demasiado su precio. Se desea asegurar un precio de venta.<jupyter_code>K = 250
opt_deseada = micro_opt.loc[(micro_opt.Type=='put') & (micro_opt.Strike==K) & (micro_opt.Expiry=='2022-01-21')]
opt_deseada
opt_valuar_p = opt_deseada.loc[list(opt_deseada.index)[0]]
# información de la opción
opt_valuar_p['JSON']<jupyter_output><empty_output><jupyter_text>Simulación de precios Modelo normal de rendimientos<jupyter_code>from datetime import date

# Datos de la opción y del día de actual
today = pd.Timestamp(date.today())
expiry = opt_valuar_p.Expiry

# Fechas desde el día de hoy hasta la fecha de cierre del contrato (considerando unicamente los días hábiles)
dates = pd.date_range(start=today, end=expiry, freq='B')

# Cantidad de escenarios a simular para el método de montecarlo
ndays = len(dates)
nscen = 10000

K = opt_valuar_p.Strike
S0 = closes_micro.iloc[-1]
sim_ret = pd.DataFrame(sigma*np.random.randn(ndays,nscen)+r,index=dates)
sim_closes = S0*np.exp(sim_ret.cumsum())<jupyter_output><empty_output><jupyter_text>Valuación de la opción basandonos en la función de pago correspondiente EUROPEA<jupyter_code>strike = K
put=pd.DataFrame({'Prima':np.exp(-r*ndays)*np.fmax(strike - sim_closes , 0).mean(axis=1)}, index=dates)
put.plot();
put.iloc[-1]
# INTERVALOS DE CONFIANZA
confianza = 0.95
sigma_est = sim_closes.iloc[-1].sem()
mean_est = put.iloc[-1].Prima
# i1 = st.t.interval(confianza,nscen-1, loc=mean_est, scale=sigma_est)
i2 = st.norm.interval(confianza, loc=mean_est, scale=sigma_est)
print(i2)<jupyter_output>(18.830593302908813, 21.364157809671436)<jupyter_text>Histograma de rendimientos<jupyter_code># Centro mis datos en mi tasa libre de riesgo
freq, values = np.histogram(ret_micro-mu+r, bins=10000)
# freq = freq.astype('float32')
prob = freq/np.sum(freq)

# Datos de la opción y del día de actual
today = pd.Timestamp(date.today())
expiry = opt_valuar_p.Expiry

# Fechas desde el día de hoy hasta la fecha de cierre del contrato (considerando unicamente los días hábiles)
dates = pd.date_range(start=today, end=expiry, freq='B')

# Cantidad de escenarios a simular para el método de montecarlo
ndays = len(dates)
nscen = 10000

K = opt_valuar_p.Strike
S0 = closes_micro.iloc[-1]

ret = np.random.choice(values[1:], (ndays,nscen), p=prob)
sim_ret_hist = pd.DataFrame(ret, index=dates)
sim_closes_hist = S0*np.exp(sim_ret_hist.cumsum())
strike = pd.DataFrame(K*np.ones([ndays,nscen]),index=dates)
put_hist=pd.DataFrame({'Prima':np.exp(-r*ndays)*np.fmax(strike - sim_closes_hist,np.zeros([ndays,nscen])).T.mean()},index=dates)
put_hist.plot();
put_hist.iloc[-1]
confianza = 0.95
sigma_est = sim_closes_hist.iloc[-1].sem()
mean_est = put_hist.iloc[-1].Prima
# i1 = st.t.interval(confianza,nscen-1, loc=mean_est, scale=sigma_est)
i2 = st.norm.interval(confianza, loc=mean_est, scale=sigma_est)
print(i2)
opt_valuar_p['JSON']['lastPrice']<jupyter_output><empty_output><jupyter_text>Valuación opcion up-and-out Modelos normal de rendimietos<jupyter_code>mu = ret_micro.mean()
sigma = ret_micro.std()
r = 0.0006/360
mu, sigma, r
# Datos de la opción y del día de actual
today = pd.Timestamp(date.today())
expiry = opt_valuar_p.Expiry

# Fechas desde el día de hoy hasta la fecha de cierre del contrato (considerando unicamente los días hábiles)
dates = pd.date_range(start = today, end = expiry, freq='B')

# Cantidad de escenarios a simular para el método de montecarlo
ndays = len(dates)
nscen = 10000

K = opt_valuar_p.Strike
S0 = closes_micro.iloc[-1]

sim_ret = pd.DataFrame(sigma*np.random.randn(ndays,nscen)+r,index=dates)
sim_closes = S0*np.exp(sim_ret.cumsum())
S0
opt_valuar_p.Underlying_Price<jupyter_output><empty_output><jupyter_text>El precio de la barrera se fija en 280 (arriba del strike price) dado que analizando el comportamineto de la acción en el mercado las probabilidades de que toque la barrera no son muy altas, ya que el precio si bien va a la alza no presenta subidas muy abruptas. Al usar una barrera abaratamos el precio de la prima de la opción.<jupyter_code>pd.set_option('display.max_columns', 15)

# Precio barrera
B = 280

# Función de desactivación (knock-out) UP AND OUT
# Si en algún momento el precio toca la barrera la opción se desactiva
I = (sim_closes < B).cumprod(axis=0)  > 0
I
K = opt_valuar_p.Strike
S0 = opt_valuar_p.Underlying_Price
K, S0
# Definir barrera
B = 280
# Crear función indicadora
I = (sim_closes < B).cumprod(axis=0) > 0
# Definir strike
strike = K
# Calcular la prima de una opción Europea
put = pd.DataFrame({'Prima Europea':np.exp(-r*ndays)*np.fmax(strike - sim_closes , 0)
                     .mean(axis=1)},index=dates)
# Calcular la prima de una opción barrera
put_uo = pd.DataFrame({'Prima up-and-out':np.exp(-r*ndays)*(I * np.fmax(strike - sim_closes, 0))
                       .mean(axis=1)},index=dates)
# Graficar el resultado de las dos primas previamente valuadas
ax = put_uo.plot();
put.plot(ax=ax);
put.iloc[-1], put_uo.iloc[-1]<jupyter_output><empty_output><jupyter_text>Histograma<jupyter_code># Definir barrera
B = 280
# Crear función indicadora
I = (sim_closes < B).cumprod(axis=0) > 0
# Definir strike
strike = K
# Calcular la prima de una opción Europea
put_hist = pd.DataFrame({'Prima Europea':np.exp(-r*ndays)*np.fmax(strike - sim_closes_hist , 0)
                     .mean(axis=1)},index=dates)
# Calcular la prima de una opción barrera
put_hist_uo = pd.DataFrame({'Prima up-and-out':np.exp(-r*ndays)*(I * np.fmax(strike - sim_closes_hist, 0))
                       .mean(axis=1)},index=dates)
# Graficar el resultado de las dos primas previamente valuadas
ax = put_hist_uo.plot();
put_hist.plot(ax=ax);
put_hist.iloc[-1], put_hist_uo.iloc[-1]<jupyter_output><empty_output><jupyter_text>Finalmente podemos analizar que la barrera si logra abaratar el precio de la prima de la opción de manera significativa. Se observa claramente que con el método del histograma la prima se abarata mucho más que si usamos rendimientos normales.   Solución Diego Pintor![image.png](attachment:image.png)<jupyter_code>#importar los paquetes que se van a usar
import pandas as pd
import pandas_datareader.data as web
import numpy as np
from sklearn.neighbors import KernelDensity
import datetime
from datetime import datetime, timedelta
import scipy.stats as st
import scipy as sp
import scipy.optimize as optimize
import scipy.cluster.hierarchy as hac
import matplotlib.pyplot as plt
import seaborn as sns
from datetime import date
%matplotlib inline
#algunas opciones para Python
pd.set_option('display.notebook_repr_html', True)
pd.set_option('display.max_columns', 6)
pd.set_option('display.max_rows', 10)
pd.set_option('display.width', 78)
pd.set_option('precision', 3)
# Función para descargar precios de cierre ajustados:
def get_adj_closes(tickers, start_date=None, end_date=None):
    # Fecha inicio por defecto (start_date='2010-01-01') y fecha fin por defecto (end_date=today)
    # Descargamos DataFrame con todos los datos
    closes = web.DataReader(name=tickers, data_source='yahoo', start=start_date, end=end_date)
    # Solo necesitamos los precios ajustados en el cierre
    closes = closes['Adj Close']
    # Se ordenan los índices de manera ascendente
    closes.sort_index(inplace=True)
    return closes

####### Calculation of log-returns
def calc_daily_ret(closes):
    return np.log(closes/closes.shift(1)).dropna()
closes = get_adj_closes(['AAPL'], '2017-01-01')
closes_appl = closes.loc[:,'AAPL']
closes_appl
ret_appl = calc_daily_ret(closes_appl)
mu = ret_appl.mean()
sigma = ret_appl.std()
r = 0.006/360
mu, sigma, r<jupyter_output><empty_output><jupyter_text>Opción Call Down-and-out  Seleccionando el strike a partir de la Volatility Smile<jupyter_code>call_do = appl_opt.loc[(appl_opt.Expiry== '2021-09-17') & (appl_opt.Type=='call')]
ax = call_do.set_index('Strike').loc[:, 'IV'].plot(figsize=(8,6))
ax.axvline(call_do.Underlying_Price.iloc[0], color='g');
call_do.Underlying_Price.iloc[0]<jupyter_output><empty_output><jupyter_text>Observamos que el Strike estará alrededor de 130.49<jupyter_code># Datos de la opción y del día de actual
today = pd.Timestamp(date.today())

pd.set_option('display.max_rows', 10)

appl = web.YahooOptions('AAPL')
appl_opt = appl.get_all_data().reset_index()
appl_opt.set_index('Expiry').sort_index()#.head(1000)

opt_deseada = appl_opt.loc[(appl_opt.Type=='call') & (appl_opt.Strike==130) & (appl_opt.Expiry=='2021-09-17')]
opt_deseada

opt_valuar = opt_deseada.loc[list(opt_deseada.index)[0]]
opt_valuar

expiry = opt_valuar.Expiry

# Fechas desde el día de hoy hasta la fecha de cierre del contrato (considerando unicamente los días hábiles)
dates = pd.date_range(start = today, end = expiry, freq='B')

# Cantidad de escenarios a simular para el método de montecarlo
ndays = len(dates)
nscen = 10000

S0 = closes_appl.iloc[-1]

sim_ret = pd.DataFrame(sigma*np.random.randn(ndays,nscen)+r,index=dates)
sim_closes = S0*np.exp(sim_ret.cumsum())
S0
K = opt_valuar.Strike
S0 = opt_valuar.Underlying_Price
K, S0
# Se utiliza la función desactivadora (knock out)
B = 120
I = (sim_closes > B).cumprod(axis=0)  > 0 #Función knock out
# La barrera se activa cuando baja mucho la opción
# Si el spot es de 130, la barrera tiene que estar por debajo del spot
S0
strike = K
# Calcular la prima de una opción Europea
call = pd.DataFrame({'Prima Europea':np.exp(-r*ndays)*np.fmax(sim_closes - strike, 0)
                     .mean(axis=1)},index=dates)
# Calcular la prima de una opción barrera
calldo = pd.DataFrame({'Prima down-and-out':np.exp(-r*ndays)*(I * np.fmax(sim_closes - strike, 0))
                       .mean(axis=1)},index=dates)
# Graficar el resultado de las dos primas previamente valuadas
ax = calldo.plot();
call.plot(ax=ax);
call.iloc[-1]
calldo.iloc[-1]<jupyter_output><empty_output><jupyter_text>Resultados Down-and-outSe puede observar que el precio de una opción Europea Estándar será de 11.76, mientras que el precio de una opción down-and-out con la Barrera en 120 dólares estará en 9.27  Opción Put Up-and-out  Seleccionando el strike a partir de la Volatility Smile<jupyter_code>put_uo = appl_opt.loc[(appl_opt.Expiry== '2021-09-17') & (appl_opt.Type=='put')]
ax = put_uo.set_index('Strike').loc[:, 'IV'].plot(figsize=(8,6))
ax.axvline(put_uo.Underlying_Price.iloc[0], color='g');
put_uo.Underlying_Price.iloc[0]<jupyter_output><empty_output><jupyter_text>Como podemos ver, de forma similar el strike estará alrededor de 130<jupyter_code>opt_deseada = appl_opt.loc[(appl_opt.Type=='put') & (appl_opt.Strike==130) & (appl_opt.Expiry=='2021-09-17')]
opt_deseada

opt_valuar = opt_deseada.loc[list(opt_deseada.index)[0]]
opt_valuar

expiry = opt_valuar.Expiry

# Fechas desde el día de hoy hasta la fecha de cierre del contrato (considerando unicamente los días hábiles)
dates = pd.date_range(start = today, end = expiry, freq='B')

# Cantidad de escenarios a simular para el método de montecarlo
ndays = len(dates)
nscen = 10000

S0 = closes_appl.iloc[-1]

sim_ret = pd.DataFrame(sigma*np.random.randn(ndays,nscen)+r,index=dates)
sim_closes = S0*np.exp(sim_ret.cumsum())
S0
K = opt_valuar.Strike
S0 = opt_valuar.Underlying_Price
K, S0
# Se utiliza la función desactivadora (knock out)
B = 140
I = (sim_closes < B).cumprod(axis=0)  > 0  #Función knock out
# La barrera se activa cuando baja mucho la opción
# Si el spot es de 130, la barrera tiene que estar por debajo del spot
S0
strike = K
# Calcular la prima de una opción Europea
put = pd.DataFrame({'Prima Europea':np.exp(-r*ndays)*np.fmax(strike - sim_closes, 0)
                     .mean(axis=1)},index=dates)
# Calcular la prima de una opción barrera
putuo = pd.DataFrame({'Prima up-and-out':np.exp(-r*ndays)*(I * np.fmax(strike - sim_closes, 0))
                       .mean(axis=1)},index=dates)
# Graficar el resultado de las dos primas previamente valuadas
ax = putuo.plot();
put.plot(ax=ax);
put.iloc[-1]
putuo.iloc[-1]<jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.11151401390725652, 'fraction_numerical': 0.02329252165010025, 'mean_word_length': 5.482853982300885, 'pattern_counts': {'":': 0, '<': 118, '<?xml version=': 0, '>': 127, 'https://': 1, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '28', 'dir': 'jupyter-structured-clean-dedup', 'id': '653185', 'license': 'MIT', 'n_tokens_mistral': 9333, 'n_tokens_neox': 8855, 'n_words': 2303, 'path': 'ProyectoConjunto_3_Tarea11_LEspinosa_DPintor.ipynb', 'repo_name': 'lyhaesp/ProyectoConjunto_LEspinosa_DPintor', 'size': '23490'}