KeyError in Python Code

I've linked Refinitiv with Python and wanting to calculate a series of risk adjusted metrics (e.g. returns, std, beta, etc) for a bunch of shares. Relevant section of the codes after linking etc reads as follows:


def rapm(stocks, benchmark, start_date, end_date, RF, MAR):

data = pd.DataFrame()

bench = pd.DataFrame()

data = ek.get_timeseries(stocks, fields ='CLOSE',start_date='2017-01-01', end_date='2020-11-30')

bench = ek.get_timeseries('.FTSE', fields ='CLOSE',start_date='2017-01-01', end_date='2020-11-30')

table = BeautifulTable(maxwidth=120)

for i in stocks:

# Calculation of Daily Returns (Stocks and Benchmark)

data['daily_return_' + i] = data[i].pct_change()

bench['daily_return'] = bench.pct_change()

.......................

rapm(['AZN.L','GSK.L','HIK.L','SN.L'],['.FTSE'],'2017-01-01','2020-11-30', 2, 2)


When I run the code, I get the error message:

KeyError: 'daily_return_AZN.L'


Fairly new to using Python and Refinitiv.


Any ideas on how to fix this will be greatly appreciated.

Best Answer

  • Gurpreet
    Answer ✓

    @cafriyie, In your code:

    # Calculation of Daily Returns (Stocks and Benchmark)
    data['daily_return_' + i] = data[i].pct_change()
    bench['daily_return'] = bench.pct_change()
    # Calculation of Cumulative Return (Stocks and Benchmark)
    st_return_i = np.prod(data['daily_return_' + i] + 1 ) - 1
    bench_return = np.prod(bench['daily_return_' + i] + 1) - 1

    You are trying to access column daily_return_*** on dataframe bench, but you haven't defined it. In other words, bench['daily_return'] is a valid entity, whereas bench['daily_return_AZN.L'] is not.

    For general help with Pandas, it is best to ask question on the Python/Pandas forums on the stackoverflow.

Answers

  • Hi @cafriyie,

    There must be some other issue in the code; the snippet you have pasted works ok without error. You will have to attach the complete python code, for us to debug it.

    Here is the output I get:

    image

  • Hi @Gurpreet,

    Please find below full details of my codes as per your request above:


    """

    import pandas as pd

    import numpy as np

    import pandas_datareader as web

    import eikon as ek

    import configparser as cp

    from beautifultable import BeautifulTable

    from scipy import stats


    cfg = cp.ConfigParser()

    cfg.read('eikon.cfg.txt')

    ek.set_app_key(cfg['eikon']['app_id'])


    stocks = ['AZN.L','GSK.L','HIK.L','SN.L']


    def rapm(stocks, benchmark, start_date, end_date, RF, MAR):

    data = pd.DataFrame()

    bench = pd.DataFrame()

    data = ek.get_timeseries(stocks, fields ='CLOSE',start_date='2017-01-01', end_date='2020-11-30')

    bench = ek.get_timeseries('.FTSE', fields ='CLOSE',start_date='2017-01-01', end_date='2020-11-30')

    table = BeautifulTable(maxwidth=120)

    table.columns.headers = ['Stock','Return','Benchmark Return','Standard Deviation','Downside Deviation','Beta',

    'Tracking Error','Sharpe Ratio','Sortino Ratio','Treynor Ratio','Information Ratio']

    table.set_style(BeautifulTable.STYLE_RST)

    for i in data:

    # Calculation of Daily Returns (Stocks and Benchmark)

    data['daily_return_' + i] = data[i].pct_change()

    bench['daily_return'] = bench.pct_change()

    # Calculation of Cumulative Return (Stocks and Benchmark)

    st_return_i = np.prod(data['daily_return_'+i]+ 1 ) - 1

    bench_return = np.prod(bench['daily_return_'+i]+ 1) - 1

    # Calculation of Standard Deviation and Downside Deviation

    std_i = data['daily_return_' + i].std()*np.sqrt(252)

    data['DD_' + i] = data[data['daily_return_' + i]<0]['daily_return_' + i]

    dd_i = data['DD_' + i].std()*np.sqrt(252)

    # Calculation of Beta

    beta_i = stats.lineregress(data['daily_return_' + i].dropna(),bench['daily_return'].dropna())[0]

    # Calculation of Tracking Error

    te_i = (data['daily_return_' + i] - bench['daily_return']).std()*np.sqrt(252)

    # Calculation of Sharpe Ratio

    sharpe_i = (st_return_i - RF/100) / std_i

    # Calculation of Sortino Ratio

    sortino_i = (st_return_i - MAR/100) / dd_i

    # Calculation of Treynor Ratio

    treynor_i = (st_return_i - RF/100) / beta_i

    # Calculation of Information Ratio

    information_i = (st_return_i - bench_return)/ te_i

    column = (i,str(round(st_return_i*100,2))+'%',str(round(bench_return*100,2))+'%',str(round(std_i*100,2))+'%',

    str(round(dd_i*100,2))+'%',round(beta_i,2),str(round(te_i*100,2))+'%',round(sharpe_i,2),round(sortino_i,2),

    round(treynor_i,2),round(information_i,2))

    table.rows.append(column)

    print(table)


    rapm(['AZN.L','GSK.L','HIK.L','SN.L'],['.FTSE'],'2017-01-01','2020-11-30', 2, 2)

    """


    Thank you very much.


  • Hi @Gurpreet, Thank you very much for your response. I have uploaded the full set of codes in my post below. If you could have a look for me please? Thank you once again.

  • Thank you very much.