Feb-09-2021, 02:25 PM
I want to add moving averages of prices and volume of various periods of the DJIA index. The code below works:
Thank you.
Sample Data:
import pandas as pd mydata = pd.read_csv('djia.csv', index_col = 'Date') what_dict = {'price': ['price', 'Close'], 'vol': ['vol', 'Volume']} def add_avg(df = mydata, df_new, what): """Adds moving averages of various rolling periods""" """Params: df : original dataframe.""" """ df_new: new dataframe""" """what: specifies either average price or volume""" x = what_dict.get(what) df_new[f'avg_{x[0]}_5'] = df[x[1]].rolling(5).mean().shift(1) #weekly avg df_new[f'avg_{x[0]}_30'] = df[x[1]].rolling(21).mean().shift(1) #monthly avg df_new[f'avg_{x[0]}_365'] = df[x[1]].rolling(252).mean().shift(1) def add_std(df = mydata, df_new, what): """Same as above, but adds std deviation instead""" x = what_dict.get(what) df_new[f'std_{x[0]}_5'] = df[x[1]].rolling(5).std().shift(1) df_new[f'std_{x[0]}_30'] = df[x[1]].rolling(21).std().shift(1) df_new[f'std_{x[0]}_365'] = df[x[1]].rolling(252).std().shift(1) data = pd.DataFrame() list = ['price', 'vol'] for i in list: add_col(data_raw, data, i) add_std(data_raw, data, i) print(data.columns)Gives:
Output:Index(['avg_price_5', 'avg_price_30', 'avg_price_365', 'std_price_5',
'std_price_30', 'std_price_365', 'avg_vol_5', 'avg_vol_30',
'avg_vol_365', 'std_vol_5', 'std_vol_30', 'std_vol_365', 'return_1',
'return_5', 'return_30', 'return_365', 'moving_avg_5', 'moving_avg_30',
'moving_avg_365'],
dtype='object')
As you can see there is too much repetition. I want to combine the two functions into one. Specifically, I want to add an argument to the function to specify whether mean() or std() is called. Something like:def add_col(df = mydata, df_new, what, func): """func argument will specify whether mean() or std() to be called""" func_dict = {'avg': 'mean', 'std': 'std'} #can't use mean() and std() as value here - throws an error saying they are #not defined y = func_dict.get(func) df_new[f'avg_{x[0]}_5'] = df[x[1]].rolling(5).y().shift(1) #Throws Attribute Error - Rolling Object has no attribute 'y' df_new[f'avg_{x[0]}_30'] = df[x[1]].rolling(21).y().shift(1) df_new[f'avg_{x[0]}_365'] = df[x[1]].rolling(252).y().shift(1)Would appreciate some pointers here.
Thank you.
Sample Data:
Output:Date Open High Low Close Adj Close Volume
1/12/2005 10806.03027 10934.90039 10806.03027 10912.57031 10912.57031 2569800
2/12/2005 10912.00977 10921.37012 10861.66016 10877.50977 10877.50977 2149000
5/12/2005 10876.9502 10876.9502 10810.66992 10835.00977 10835.00977 2373400
6/12/2005 10835.41016 10936.2002 10835.41016 10856.86035 10856.86035 2646300
7/12/2005 10856.86035 10868.05957 10764.00977 10810.91016 10810.91016 2434900
8/12/2005 10808.42969 10847.25 10729.66992 10755.12012 10755.12012 2532900
9/12/2005 10751.75977 10805.9502 10729.91016 10778.58008 10778.58008 2389300