Häufigkeitstabelle für eine einzelne Variable


97

Eine letzte Frage für Pandas-Neulinge an diesem Tag: Wie erstelle ich eine Tabelle für eine einzelne Serie?

Beispielsweise:

my_series = pandas.Series([1,2,2,3,3,3])
pandas.magical_frequency_function( my_series )

>> {
     1 : 1,
     2 : 2, 
     3 : 3
   }

Viel googeln hat mich zu Series.describe () und pandas.crosstabs geführt, aber keines von beiden macht genau das, was ich brauche: eine Variable, die nach Kategorien zählt. Oh, und es wäre schön, wenn es für verschiedene Datentypen funktionieren würde: Zeichenfolgen, Ints usw.

Antworten:


153

Vielleicht .value_counts()?

>>> import pandas
>>> my_series = pandas.Series([1,2,2,3,3,3, "fred", 1.8, 1.8])
>>> my_series
0       1
1       2
2       2
3       3
4       3
5       3
6    fred
7     1.8
8     1.8
>>> counts = my_series.value_counts()
>>> counts
3       3
2       2
1.8     2
fred    1
1       1
>>> len(counts)
5
>>> sum(counts)
9
>>> counts["fred"]
1
>>> dict(counts)
{1.8: 2, 2: 2, 3: 3, 1: 1, 'fred': 1}

5
.value_counts().sort_index(1), um zu verhindern, dass die erste Spalte möglicherweise leicht außer Betrieb
gerät

9
Gibt es ein Äquivalent für DataFrame anstelle von Serien? Ich habe versucht, .value_counts () auf einem df AttributeError: 'DataFrame' object has no attribute 'value_counts'
auszuführen

1
Gibt es eine einfache Möglichkeit, diese Zählungen in Proportionen umzuwandeln?
Dsaxton

7
@dsaxton Sie können .value_counts (normalize = True) verwenden, um die Ergebnisse in Proportionen umzuwandeln
Max Power

2
Um dies stattdessen für einen Datenrahmen zu verwenden, konvertieren Sie ihn in die entsprechende 1-D-Numpy-Array-Darstellung wie -, pd.value_counts(df.values.ravel())die eine Reihe zurückgibt, deren indexund valuesAttribute die eindeutigen Elemente bzw. deren Anzahl enthalten.
Nickil Maveli

11

Sie können das Listenverständnis in einem Datenrahmen verwenden, um die Häufigkeit der Spalten als solche zu zählen

[my_series[c].value_counts() for c in list(my_series.select_dtypes(include=['O']).columns)]

Nervenzusammenbruch:

my_series.select_dtypes(include=['O']) 

Wählt nur die kategorialen Daten aus

list(my_series.select_dtypes(include=['O']).columns) 

Verwandelt die Spalten von oben in eine Liste

[my_series[c].value_counts() for c in list(my_series.select_dtypes(include=['O']).columns)] 

Durchläuft die obige Liste und wendet value_counts () auf jede der Spalten an


5

Die Antwort von @DSM ist einfach und unkompliziert, aber ich dachte, ich würde dieser Frage meine eigene Eingabe hinzufügen. Wenn Sie sich den Code für pandas.value_counts ansehen , werden Sie feststellen , dass viel los ist.

Wenn Sie die Häufigkeit vieler Serien berechnen müssen, kann dies eine Weile dauern. Eine schnellere Implementierung wäre die Verwendung von numpy.unique mitreturn_counts = True

Hier ist ein Beispiel:

import pandas as pd
import numpy as np

my_series = pd.Series([1,2,2,3,3,3])

print(my_series.value_counts())
3    3
2    2
1    1
dtype: int64

Beachten Sie hier, dass es sich bei dem zurückgegebenen Artikel um eine Pandas.Series handelt

Im Vergleich dazu wird numpy.uniqueein Tupel mit zwei Elementen zurückgegeben, den eindeutigen Werten und den Zählwerten.

vals, counts = np.unique(my_series, return_counts=True)
print(vals, counts)
[1 2 3] [1 2 3]

Sie können diese dann zu einem Wörterbuch kombinieren:

results = dict(zip(vals, counts))
print(results)
{1: 1, 2: 2, 3: 3}

Und dann in eine pandas.Series

print(pd.Series(results))
1    1
2    2
3    3
dtype: int64

0

Für die Häufigkeitsverteilung einer Variablen mit übermäßigen Werten können Sie die Werte in Klassen reduzieren.

Hier habe ich übermäßige Werte für employrateVariablen, und es gibt keine Bedeutung für die Häufigkeitsverteilung mit direktenvalues_count(normalize=True)

                country  employrate alcconsumption
0           Afghanistan   55.700001            .03
1               Albania   11.000000           7.29
2               Algeria   11.000000            .69
3               Andorra         nan          10.17
4                Angola   75.699997           5.57
..                  ...         ...            ...
208             Vietnam   71.000000           3.91
209  West Bank and Gaza   32.000000               
210         Yemen, Rep.   39.000000             .2
211              Zambia   61.000000           3.56
212            Zimbabwe   66.800003           4.96

[213 rows x 3 columns]

Häufigkeitsverteilung values_count(normalize=True)ohne Klassifizierung, die Länge des Ergebnisses beträgt hier 139 (scheint als Häufigkeitsverteilung bedeutungslos zu sein):

print(gm["employrate"].value_counts(sort=False,normalize=True))

50.500000   0.005618
61.500000   0.016854
46.000000   0.011236
64.500000   0.005618
63.500000   0.005618

58.599998   0.005618
63.799999   0.011236
63.200001   0.005618
65.599998   0.005618
68.300003   0.005618
Name: employrate, Length: 139, dtype: float64

Bei der Klassifizierung setzen wir alle Werte mit einem bestimmten Bereich, dh.

0-10 als 1,
11-20 als 2  
21-30 als 3 und so weiter.
gm["employrate"]=gm["employrate"].str.strip().dropna()  
gm["employrate"]=pd.to_numeric(gm["employrate"])
gm['employrate'] = np.where(
   (gm['employrate'] <=10) & (gm['employrate'] > 0) , 1, gm['employrate']
   )
gm['employrate'] = np.where(
   (gm['employrate'] <=20) & (gm['employrate'] > 10) , 1, gm['employrate']
   )
gm['employrate'] = np.where(
   (gm['employrate'] <=30) & (gm['employrate'] > 20) , 2, gm['employrate']
   )
gm['employrate'] = np.where(
   (gm['employrate'] <=40) & (gm['employrate'] > 30) , 3, gm['employrate']
   )
gm['employrate'] = np.where(
   (gm['employrate'] <=50) & (gm['employrate'] > 40) , 4, gm['employrate']
   )
gm['employrate'] = np.where(
   (gm['employrate'] <=60) & (gm['employrate'] > 50) , 5, gm['employrate']
   )
gm['employrate'] = np.where(
   (gm['employrate'] <=70) & (gm['employrate'] > 60) , 6, gm['employrate']
   )
gm['employrate'] = np.where(
   (gm['employrate'] <=80) & (gm['employrate'] > 70) , 7, gm['employrate']
   )
gm['employrate'] = np.where(
   (gm['employrate'] <=90) & (gm['employrate'] > 80) , 8, gm['employrate']
   )
gm['employrate'] = np.where(
   (gm['employrate'] <=100) & (gm['employrate'] > 90) , 9, gm['employrate']
   )
print(gm["employrate"].value_counts(sort=False,normalize=True))

Nach der Klassifizierung haben wir eine klare Häufigkeitsverteilung. hier können wir leicht sehen, dass 37.64%von Ländern Beschäftigungsquote zwischen 51-60% und 11.79%von Ländern Beschäftigungsquote zwischen haben71-80%

5.000000   0.376404
7.000000   0.117978
4.000000   0.179775
6.000000   0.264045
8.000000   0.033708
3.000000   0.028090
Name: employrate, dtype: float64
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.