Étant donné une trame de données qui ressemble à ceci:
A B
2005-09-06 5 -2
2005-09-07 -1 3
2005-09-08 4 5
2005-09-09 -8 2
2005-09-10 -2 -5
2005-09-11 -7 9
2005-09-12 2 8
2005-09-13 6 -5
2005-09-14 6 -5
Existe-t-il un moyen Pythonic pour créer une matrice 2x2 comme ceci:
1 0
1 a b
0 c d
Où:
a = nombre d'observations où les éléments correspondants des colonnes A et B sont tous deux positifs.
b = nombre d'observations où les éléments correspondants de la colonne A sont positifs et négatifs dans la colonne B.
c = nombre d'observations où les éléments correspondants de la colonne A sont négatifs et positifs dans la colonne B.
d = nombre d'observations où les éléments correspondants des colonnes A et B sont tous deux négatifs.
Pour cet exemple, la sortie serait:
1 0
1 2 3
0 3 1
Merci
Appelons votre dataframe data
. Essayer
a = data['A']>0
b = data['B']>0
data.groupby([a,b]).count()
Probablement plus simple d'utiliser simplement la fonction pandas crosstab
. Emprunt à Dyno Fu ci-dessus:
import pandas as pd
from StringIO import StringIO
table = """dt A B
2005-09-06 5 -2
2005-09-07 -1 3
2005-09-08 4 5
2005-09-09 -8 2
2005-09-10 -2 -5
2005-09-11 -7 9
2005-09-12 2 8
2005-09-13 6 -5
2005-09-14 6 -5
"""
sio = StringIO(table)
df = pd.read_table(sio, sep=r"\s+", parse_dates=['dt'])
df.set_index("dt", inplace=True)
pd.crosstab(df.A > 0, df.B > 0)
Production:
B False True
A
False 1 3
True 3 2
[2 rows x 2 columns]
Le tableau est également utilisable si vous voulez faire un test exact de Fisher avec scipy.stats
etc:
from scipy.stats import fisher_exact
tab = pd.crosstab(df.A > 0, df.B > 0)
fisher_exact(tab)
Voici une page vraiment utile sur la fonction de tableau croisé pandas:
http://chrisalbon.com/python/pandas_crosstabs.html
Je pense donc que pour ce que vous aimeriez faire, vous devriez utiliser
import pandas as pd
pd.crosstab(data['A']>0, data['B']>0)
J'espère que cela pourra aider!
import pandas as pd
from StringIO import StringIO
table = """dt A B
2005-09-06 5 -2
2005-09-07 -1 3
2005-09-08 4 5
2005-09-09 -8 2
2005-09-10 -2 -5
2005-09-11 -7 9
2005-09-12 2 8
2005-09-13 6 -5
2005-09-14 6 -5
"""
sio = StringIO(table)
df = pd.read_table(sio, sep=r"\s+", parse_dates=['dt'])
df.set_index("dt", inplace=True)
a = df['A'] > 0
b = df['B'] > 0
df1 = df.groupby([a,b]).count()
print df1["A"].unstack()
production:
B False True
A
False 1 3
True 3 2
c'est juste la réponse de lnanenok et l'utilisation de unstack()
pour le rendre plus lisible. le crédit devrait aller à lanenok.