2017-05-11 2 views
1

Pour un seul niveau colonne indexée je faire ce qui suitComment utiliser la chaîne de méthode Pandas .assign() sur une colonne MultiIndex?

arrays = [['one', 'two', ]] 
tuples = list(zip(*arrays)) 
index = pd.MultiIndex.from_tuples(tuples, names=['first', 'second']) 
df = pd.DataFrame(pd.np.random.randn(3, 2), index=['A', 'B', 'C'], columns=index) 
print(df) 


first one two 
A 0.919921 -1.407321 
B 1.100169 -0.927249 
C -0.520308 0.619783 

print(df.assign(one=lambda x: x.one * 100)) 

first one   two 
A  144.950877 0.633516 
B  -0.593133 -0.630641 
C  -5.661949 -0.738884 

Maintenant, quand j'ai une colonne multiindice je peux accéder à la colonne désirée à l'aide .loc mais je ne peux pas assigner à quoi que ce soit comme il arrive avec l'erreur SyntaxError: keyword can't be an expression .

Voici un exemple,

arrays = [['bar', 'bar'], 
      ['one', 'two']] 

tuples = list(zip(*arrays)) 
index = pd.MultiIndex.from_tuples(tuples, names=['first', 'second']) 
df = pd.DataFrame(pd.np.random.randn(3, 2), index=['A', 'B', 'C'], columns=index) 

print(df) 

first bar 
second one   two 
A  1.119243 0.819455 
B  -0.473354 -1.340502 
C  0.150403 -0.211392 

Cependant,

df.assign(('bar', 'one')=lambda x: x.loc[:, ('bar', 'one')] * 10) 

SyntaxError: keyword can't be an expression 

Je peux faire

df.assign(barOne=lambda x: x.loc[:, ('bar', 'one')] * 10) 


first bar      barOne 
second one   two 
A  0.433909 0.949701 4.339091 
B  0.011486 -1.395144 0.114858 
C  -0.289821 2.106951 -2.89821 

mais ce n'est pas souhaitable. Je voudrais garder ma chaîne de méthodes bien, mais gardez également la colonne MultiIndexed.

+0

josh - J'ai posté une réponse ci-dessous qui ne pas utiliser la méthode 'Assign()' du tout. Mais je ne suis pas sûr si vous essayez de mieux comprendre cette méthode, ou de trouver une solution à un problème particulier. Si vous pouviez publier le résultat souhaité, ce serait utile. – pshep123

+0

La question était d'utiliser la fonction 'assign()' spécifiquement. La raison derrière cela est que j'utilisais le chaînage de méthodes. Ça allait bien jusqu'à ce que je veuille assigner au multiIndex. – josh

Répondre

1

Si je lis correctement, ne serait-il pas être aussi simple que:

df Original:

first  bar 
second  one  two 
A  0.386729 1.014010 
B  0.236824 0.439019 
C  0.530020 -0.268751 

code:

df[('bar','one')] *= 10 

Mise à jour df (modifier la colonne):

first   bar 
second  one  two 
A  3.8672946 1.014010 
B  2.3682376 0.439019 
C  5.3002040 -0.268751 

Ou, df mis à jour (créer une nouvelle colonne):

df[('bar','new')] = df[('bar','one')] * 10 

first  bar 
second  one  two  new 
A  0.386729 1.014010 3.867295 
B  0.236824 0.439019 2.368238 
C  0.530020 -0.268751 5.300204 
+0

Ceci est correct dans le sens où il fait ce que je veux, mais pas comment je veux le faire. Comme je l'ai mentionné plus haut, je voulais utiliser la méthode assign() pour pouvoir faire quelque chose dans une longue chaîne de méthodes. Merci quand même. – josh

+0

Quelle est votre sortie désirée et quelles sont les prochaines étapes de votre chaîne? Cela pourrait aider. – pshep123