2017-04-18 18 views
2

以下の "exampleDF"を考慮してください。パンダの2列を使用して関数を適用

name age sex 
a 21  male 
b 13 female 
c 56  female 
d 12  male 
e 45  nan 
f 10  female 

私は年齢が他childセックスにその等しいので、もし、年齢や性別を使用して新しい列を作成します。

私はこの

exampleDF['newColumn'] = exampleDF[['age','sex']].apply(lambda age,sex: 'child' if age < 15 else sex) 

を試してみましたが、私は私が間違っているの何で私を助けてください、エラーにmissing 1 required positional argument: 'sex'

を取得します。

答えて

0

これは、仕事をするだろう。そして、

import pandas as pd 
exampleDF=pd.DataFrame({'name':['a','b','c','d','e','f'],'age':[21,13,56,12,45,10],'sex':['male','female','female','male',None,'male']}) 
exampleDF['newColumn'] = exampleDF[['age','sex']].apply(lambda x: 'child' if x['age'] < 15 else x['sex'],axis=1) 

exampleDFがある:あなたのコードで

age name sex  newColumn 
0 21 a  male male 
1 13 b  female child 
2 56 c  female female 
3 12 d  male child 
4 45 e  None None 
5 10 f  male child 

あなたがlambda age,sex:を定義しようとしていますが、exampleDF[['age','sex']]ようにして1つのデータフレームであることを行うことができません2つの列(2つの別々の列ではありません)。上記の解決策はこの問題を解決します。また、軸を指定する必要もあります。

+0

これは非常にばかな質問かもしれませんが、いつ 'axis = 1 'を指定する必要がありますか?私は以前に軸を指定せずにラムダでapply関数を使用しました。 – Harj

+1

デフォルトではaxis = 0なので、行に関数を適用します(http://pandas.pydata.org/pandas-docs/stable/generated/pandas.DataFrame.apply.htmlを参照)。これは以前あなたが望んでいたものです。ただし、x ['age']とx ['sex']の2つのカラムに適用したいので、axis = 1を指定する必要があります。 –

+1

前のコメントを続けると、2つの例があります:最初の例はexampleDF ['newColumn'] = exampleDF [['age']]。apply(lambda x:x ** 2)です。ここでは、exampleDF [['age']]の各要素に四角形のアクションを適用するだけで、axis = 1を指定する必要はありません。しかし、次の例では、exampleDF ['newColumn'] = exampleDF [['age']]。apply(x ['age']> 15ならばlambda x:True、それ以外の場合はFalse、axis = 1)axis = 1は関数が列全体に直接適用されるためです。 –

3

私はより良いがmaskを使用していると思います - 他sex列からTrueboolean maskでGET値が新しい列にchild文字列を取得する場合:ソリューションの

print (exampleDF['age'] < 15) 
0 False 
1  True 
2 False 
3  True 
4 False 
5  True 
Name: age, dtype: bool 


exampleDF['newColumn'] = exampleDF['sex'].mask(exampleDF['age'] < 15, 'child') 
print (exampleDF) 
    name age  sex newColumn 
0 a 21 male  male 
1 b 13 female  child 
2 c 56 female female 
3 d 12 male  child 
4 e 45  NaN  NaN 
5 f 10 female  child 

主な利点は、それが高速である:

#small 6 rows df 
In [63]: %timeit exampleDF['sex'].mask(exampleDF['age'] < 15, 'child') 
1000 loops, best of 3: 517 µs per loop 

In [64]: %timeit exampleDF[['age','sex']].apply(lambda x: 'child' if x['age'] < 15 else x['sex'],axis=1) 
1000 loops, best of 3: 867 µs per loop 

#bigger 6k df 
exampleDF = pd.concat([exampleDF]*1000).reset_index(drop=True) 

In [66]: %timeit exampleDF['sex'].mask(exampleDF['age'] < 15, 'child') 
The slowest run took 5.41 times longer than the fastest. This could mean that an intermediate result is being cached. 
1000 loops, best of 3: 589 µs per loop 

In [67]: %timeit exampleDF[['age','sex']].apply(lambda x: 'child' if x['age'] < 15 else x['sex'],axis=1) 
10 loops, best of 3: 104 ms per loop 

#bigger 60k df - apply very slow 
exampleDF = pd.concat([exampleDF]*10000).reset_index(drop=True) 

In [69]: %timeit exampleDF['sex'].mask(exampleDF['age'] < 15, 'child') 
1000 loops, best of 3: 1.23 ms per loop 

In [70]: %timeit exampleDF[['age','sex']].apply(lambda x: 'child' if x['age'] < 15 else x['sex'],axis=1) 
1 loop, best of 3: 1.03 s per loop 
関連する問題