podzbiór ramki danych Pythona

Przechodzę z R na Python. Właśnie zacząłem używać pand. Mam kod R, który ładnie się komponuje:

k1 <- subset(data, Product = p.id & Month < mn & Year == yr, select = c(Time, Product))
Teraz chcę robić podobne rzeczy w Pythonie. to jest to co mam do tej pory:
import pandas as pd
data = pd.read_csv("../data/monthly_prod_sales.csv")


#first, index the dataset by Product. And, get all that matches a given 'p.id' and time.
 data.set_index('Product')
 k = data.ix[[p.id, 'Time']]

# then, index this subset with Time and do more subsetting..
Zaczynam czuć, że robię to źle. być może istnieje eleganckie rozwiązanie. Czy ktoś może pomóc? Muszę wyodrębnić miesiąc i rok z znacznika czasu, który mam i zrobić podzbiór. Być może istnieje jednolinijkowy, który spełni wszystkie to:
k1 <- subset(data, Product = p.id & Time >= start_time & Time < end_time, select = c(Time, Product))
Dzięki.
Author: user1717931, 2013-10-08

3 answers

Zakładam, że Time i Product są kolumnami w DataFrame, df jest instancją DataFrame, a pozostałe zmienne są wartościami skalarnymi:

Na razie musisz odwołać się do instancji DataFrame:

k1 = df.loc[(df.Product == p_id) & (df.Time >= start_time) & (df.Time < end_time), ['Time', 'Product']]

Nawiasy są również konieczne, ze względu na pierwszeństwo operatora & w stosunku do operatorów porównania. Operator & jest w rzeczywistości przeciążonym operatorem bitowym, który ma taki sam priorytet jak operatory arytmetyczne, które z kolei mają wyższy priorytet niż operatorów porównawczych.

In pandas 0.13 a new experimental DataFrame.query() metoda będzie dostępna. Jest bardzo podobny do podzbioru modulo argumentu select:

Z query() zrobiłbyś to tak:

df[['Time', 'Product']].query('Product == p_id and Month < mn and Year == yr')

Oto prosty przykład:

In [9]: df = DataFrame({'gender': np.random.choice(['m', 'f'], size=10), 'price': poisson(100, size=10)})

In [10]: df
Out[10]:
  gender  price
0      m     89
1      f    123
2      f    100
3      m    104
4      m     98
5      m    103
6      f    100
7      f    109
8      f     95
9      m     87

In [11]: df.query('gender == "m" and price < 100')
Out[11]:
  gender  price
0      m     89
4      m     98
9      m     87

Ostateczne zapytanie, które Cię interesuje, będzie nawet w stanie skorzystać z przykutych porównań, takich jak:

k1 = df[['Time', 'Product']].query('Product == p_id and start_time <= Time < end_time')
 77
Author: Phillip Cloud,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-07-05 17:40:09

Tylko dla kogoś, kto szuka rozwiązania bardziej podobnego do R:

df[(df.Product == p_id) & (df.Time> start_time) & (df.Time < end_time)][['Time','Product']]

Nie ma potrzeby data.loc lub query, ale myślę, że jest trochę długi.

 18
Author: sernle,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-05-12 10:21:19

Odkryłem, że możesz użyć dowolnego warunku podzbioru dla danej kolumny, owijając ją w []. Na przykład masz df z kolumnami ['Product',' Time',' Year','Color']

I powiedzmy, że chcesz dołączyć produkty wyprodukowane przed 2014 rokiem. Możesz napisać,

df[df['Year'] < 2014]

Aby zwrócić wszystkie wiersze, w których ma to miejsce. Możesz dodać różne warunki.

df[df['Year'] < 2014][df['Color' == 'Red']

Następnie po prostu wybierz kolumny, które chcesz, jak opisano powyżej. Na przykład kolor produktu i klucz df powyżej,

df[df['Year'] < 2014][df['Color' == 'Red'][['Product','Color']]
 9
Author: gpicard,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-04-20 19:53:40