DSM's answer, который выбирает строки с использованием булевой маски, хорошо работает, даже если DataFrame имеет не уникальный индекс. Мой метод, который выбирает строки с использованием значений индекса, немного медленнее, когда индекс уникален, а значительно медленнее, когда индекс содержит повторяющиеся значения.
@roland: Пожалуйста, подумайте о принятии ответа DSM.
Вы можете использовать groupby-filter
:
In [16]: df.loc[df.groupby('User')['X'].filter(lambda x: x.sum() == 0).index]
Out[16]:
User X
0 1 0
1 1 0
5 3 0
6 3 0
Сама по себе GroupBy фильтр просто возвращает это:
In [29]: df.groupby('User')['X'].filter(lambda x: x.sum() == 0)
Out[29]:
0 0
1 0
5 0
6 0
Name: X, dtype: int64
но вы можете использовать свой индекс,
In [30]: df.groupby('User')['X'].filter(lambda x: x.sum() == 0).index
Out[30]: Int64Index([0, 1, 5, 6], dtype='int64')
, чтобы выбрать нужные строки, используя df.loc
.
Вот тест я использовал:
In [49]: df2 = pd.concat([df]*10000) # df2 has a non-unique index
Я Ctrl - C «d это, потому что она занимает слишком много времени, чтобы закончить:
In [50]: %timeit df2.loc[df2.groupby('User')['X'].filter(lambda x: x.sum() == 0).index]
Когда Я осознал свою ошибку, я создал DataFrame с уникальным индексом:
In [51]: df3 = df2.reset_index() # this gives df3 a unique index
In [52]: %timeit df3.loc[df3.groupby('User')['X'].filter(lambda x: x.sum() == 0).index]
100 loops, best of 3: 13 ms per loop
In [53]: %timeit df3.loc[df3.groupby("User")["X"].transform(sum) == 0]
100 loops, best of 3: 11.4 ms per loop
Это показывает метод в DSM хорошо выполняет даже с не уникальным индексом:
In [54]: %timeit df2.loc[df2.groupby("User")["X"].transform(sum) == 0]
100 loops, best of 3: 11.2 ms per loop
Знаем ли мы, что все 'X'> = 0, или вам нужно беспокоиться о' -1, + 1'? – DSM
все значения X> = 0 – roland