Pandas DataFrame подсчитывает количество не всех элементов в двух столбцах [дубликат]

Мой ответ будет сосредоточен на КОГДА мы можем использовать while / for-else.

На первый взгляд кажется, что при использовании

while CONDITION:
    EXPRESSIONS
print 'ELSE'
print 'The next statement'

и

while CONDITION:
    EXPRESSIONS
else:
    print 'ELSE'
print 'The next statement'

Поскольку оператор print 'ELSE', как представляется, всегда выполняется в обоих случаях (оба, когда цикл while закончен или не запущен).

Тогда это отличается только тогда, когда оператор print 'ELSE' не будет выполнен. Когда внутри [code] while

In [17]: i = 0

In [18]: while i < 5:
    print i
    if i == 2:
        break
    i = i +1
else:
    print 'ELSE'
print 'The next statement'
   ....:
0
1
2
The next statement

имеется break, есть break, если он отличается от:

In [19]: i = 0

In [20]: while i < 5:
    print i
    if i == 2:
        break
    i = i +1
print 'ELSE'
print 'The next statement'
   ....:
0
1
2
ELSE
The next statement

return, поскольку он делает тот же эффект для двух вышеприведенных случаев.

exception raise также не вызывает различий, потому что когда он поднимается, где следующий код будет выполнен, в обработчике исключений (кроме блока), код в else или сразу после того, как предложение while не будет выполнено.

1
задан hernanavella 6 January 2016 в 00:00
поделиться

3 ответа

Вы можете вывести из вашего df и вызывать count передачу axis=1:

In [24]:
df['count'] = df[list('abcde')].count(axis=1)
df

Out[24]:
              Close  a   b   c   d   e      Time  count
2015-12-03  2051.25  5   4   3   1   1  05:00:00      5
2015-12-04  2088.25  5   4   3   1 NaN  06:00:00      4
2015-12-07  2081.50  5   4   3 NaN NaN  07:00:00      3
2015-12-08  2058.25  5   4 NaN NaN NaN  08:00:00      2
2015-12-09  2042.25  5 NaN NaN NaN NaN  09:00:00      1

TIMINGS

In [25]:
%timeit df[['a', 'b', 'c', 'd', 'e']].apply(lambda x: sum(x.notnull()), axis=1)
%timeit df.drop(['Close', 'Time'], axis=1).count(axis=1)
%timeit df[list('abcde')].count(axis=1)

100 loops, best of 3: 3.28 ms per loop
100 loops, best of 3: 2.76 ms per loop
100 loops, best of 3: 2.98 ms per loop

apply является самым медленным, который не является неожиданно, версия drop немного быстрее, но семантически я предпочитаю просто передавать список интересующих количеств и вызывать count для удобочитаемости

Хмм, я продолжаю получать различные тайминги сейчас:

In [27]:
%timeit df[['a', 'b', 'c', 'd', 'e']].apply(lambda x: sum(x.notnull()), axis=1)
%timeit df.drop(['Close', 'Time'], axis=1).count(axis=1)
%timeit df[list('abcde')].count(axis=1)
%timeit df[['a', 'b', 'c', 'd', 'e']].count(axis=1)

100 loops, best of 3: 3.33 ms per loop
100 loops, best of 3: 2.7 ms per loop
100 loops, best of 3: 2.7 ms per loop
100 loops, best of 3: 2.57 ms per loop
]

БОЛЬШЕ ВРЕМЕНИ

In [160]:
%timeit df[['a', 'b', 'c', 'd', 'e']].apply(lambda x: sum(x.notnull()), axis=1)
%timeit df.drop(['Close', 'Time'], axis=1).count(axis=1)
%timeit df[list('abcde')].count(axis=1)
%timeit df[['a', 'b', 'c', 'd', 'e']].count(axis=1)
%timeit df[list('abcde')].notnull().sum(axis=1) 

1000 loops, best of 3: 1.4 ms per loop
1000 loops, best of 3: 1.14 ms per loop
1000 loops, best of 3: 1.11 ms per loop
1000 loops, best of 3: 1.11 ms per loop
1000 loops, best of 3: 1.05 ms per loop

Кажется, что тестирование для notnull и суммирование (поскольку notnull приведет к созданию булевой маски) быстрее на этом наборе данных

Вкл. строка 50k df, последний метод немного быстрее:

In [172]:
%timeit df[['a', 'b', 'c', 'd', 'e']].apply(lambda x: sum(x.notnull()), axis=1)
%timeit df.drop(['Close', 'Time'], axis=1).count(axis=1)
%timeit df[list('abcde')].count(axis=1)
%timeit df[['a', 'b', 'c', 'd', 'e']].count(axis=1)
%timeit df[list('abcde')].notnull().sum(axis=1) 

1 loops, best of 3: 5.83 s per loop
100 loops, best of 3: 6.15 ms per loop
100 loops, best of 3: 6.49 ms per loop
100 loops, best of 3: 6.04 ms per loop
3
ответ дан EdChum 17 August 2018 в 19:36
поделиться
  • 1
    Еще один пример: df [list ('abcde')]. Notnull (). Sum (axis = 1), который был немного быстрее, чем любой из вышеперечисленных методов в моем тестировании. – n8yoder 6 January 2016 в 03:21
  • 2
    @ n8yoder Это немного быстрее, попробует более крупный набор данных – EdChum 6 January 2016 в 09:58
df['Count'] = df[['a', 'b', 'c', 'd', 'e']].apply(lambda x: sum(x.notnull()), axis=1)

In [1254]: df
Out[1254]: 
              Close  a   b   c   d   e      Time  Count
2015-12-03  2051.25  5   4   3   1   1  05:00:00      5
2015-12-04  2088.25  5   4   3   1 NaN  06:00:00      4
2015-12-07  2081.50  5   4   3 NaN NaN  07:00:00      3
2015-12-08  2058.25  5   4 NaN NaN NaN  08:00:00      2
2015-12-09  2042.25  5 NaN NaN NaN NaN  09:00:00      1
1
ответ дан Anton Protopopov 17 August 2018 в 19:36
поделиться

Включите список желаемых columns или просто отпустите два columns, которые вы не хотите исключать из count - вдоль axis=1 (см. docs) :

df['Count'] = df.drop(['Close', 'Time'], axis=1).count(axis=1)


     Close  a  b   c   d   e      Time  Count
0  2051.25  5  4   3   1   1  05:00:00      5
1  2088.25  5  4   3   1 NaN  06:00:00      4
2  2081.50  5  4   3 NaN NaN  07:00:00      3
3  2058.25  5  4   3 NaN NaN  08:00:00      3
4  2042.25  5  4 NaN NaN NaN  09:00:00      2
1
ответ дан Stefan 17 August 2018 в 19:36
поделиться
Другие вопросы по тегам:

Похожие вопросы: