0

I need to apply different functions for a database python depending on a slice of this dataframe. Each function creates several columns.

Here is my attempt (very simplified version of course) :

df=pd.DataFrame({'Type':['O','O','A'],'A':[7,9,8],'B':[8,6,5]})

def f1(df):
    df['test']='A-OK'
    df['test2']='A-OK2'
    return df
def f2(df):
    df['test']='O-OK'
    df['test2']='O-OK2'
    return df

def function_test(df):
    df_a=df[df.Type =='A']
    df_o=df[df.Type =='O']
    #Applying functions
    df_a=f1(df_a)
    df_o=f2(df_o)

    #retrieving results
    df[df.Type =='A']=df_a
    df[df.Type =='O']=df_o

    return df
function_test(df)

The dataframes df_o and df_a (temporary) contains the good information, but I cannot copy the results in the original df after that.

Edit : Typos corrected

Rhesous
  • 984
  • 6
  • 12
  • with your code, just add `df['test'] = None` and `df['test2'] = None` at the beginning of you function `function_test(df)` and it should work, but it is not a clean way to do it. btw you do `df_o=f1(df_o)` but it should be `df_o=f2(df_o)` – Ben.T May 28 '18 at 15:43
  • do you want to append '-OK' & `-OK2` to whatever is in `Type` for that row? – Haleemur Ali May 28 '18 at 15:44
  • Thanks for your answers, actually the functions do complex things, this was just a really quick example – Rhesous May 28 '18 at 16:15

2 Answers2

1

Your problem is in assigning to the slice in lines:

df[df.Type =='A']=df_a
df[df.Type =='O']=df_o

After changing the typo in line:

df_o=f2(df_o) # instead of f1

Just return:

pandas.concat([df_a, df_o]).sort_index()

For output:

   A  B Type  test  test2
0  7  8    O  O-OK   O-OK
1  9  6    O  O-OK   O-OK
2  8  5    A  A-OK  A-OK2

But consider more optimally:

df['test'] = df['Type'].apply(lambda x: 'A-OK' if x == 'A' else 'O-OK')
df['test2'] = df['Type'].apply(lambda x: 'A-OK2' if x == 'A' else 'O-OK')

and so on.

twolffpiggott
  • 1,063
  • 8
  • 13
  • 1
    Thanks for the answer, I think the concat options should be fine ! Actually I can't just apply and return one column because in the real life case I'm facing I need to apply a lot of functions that create a lot of columns, – Rhesous May 28 '18 at 15:49
  • Ah, yes. You're right. Applies with multiple outputs can get messy fast. [This answer](https://stackoverflow.com/questions/16236684/apply-pandas-function-to-column-to-create-multiple-new-columns) gives it a go, though. – twolffpiggott May 28 '18 at 15:53
0
df.assign(test=df.Type+'-OK', test2=df.Type+'-OK2') 

will do it in 1 line

#outputs

   A  B Type  test test2
0  7  8    O  O-OK  O-OK
1  9  6    O  O-OK  O-OK
2  8  5    A  A-OK  A-OK
Haleemur Ali
  • 26,718
  • 5
  • 61
  • 85
  • Thanks for the answer, actually I wanted to use really long fonctions, I just used OK and OK2 to make a simple and fast example – Rhesous May 28 '18 at 15:47