파이썬 : 특정 조건으로 목록 (시퀀스)에서 항목 수 가져 오기


84

엄청난 수의 항목이있는 목록이 있다고 가정합니다.

l = [ 1, 4, 6, 30, 2, ... ]

항목이 특정 조건을 충족해야하는 목록에서 항목 수를 가져오고 싶습니다. 내 첫 생각은 :

count = len([i for i in l if my_condition(l)])

그러나 my_condition () 필터링 된 목록에도 많은 항목이있는 경우 필터링 된 결과에 대한 새 목록을 만드는 것은 메모리 낭비 일 뿐이라고 생각합니다. 효율성을 위해 IMHO는 위의 호출이 다음보다 나을 수 없습니다.

count = 0
for i in l:
    if my_condition(l):
        count += 1

임시 목록을 생성하지 않고 특정 조건을 충족하는 항목 수를 얻는 기능적 스타일의 방법이 있습니까?

미리 감사드립니다.


3
생성기와 목록 사이의 선택은 실행 시간과 메모리 소비 사이의 선택입니다. 코드를 프로파일 링하면 결과가 얼마나 자주 직관적이지 않은지 놀랄 것입니다. 조기 최적화는 모든 악의 근원입니다.
Paulo Scardine 2013 년

답변:


102

생성기 표현식을 사용할 수 있습니다 .

>>> l = [1, 3, 7, 2, 6, 8, 10]
>>> sum(1 for i in l if i % 4 == 3)
2

또는

>>> sum(i % 4 == 3 for i in l)
2

그 사실을 사용합니다 int(True) == 1.

또는 itertools.imap(python 2) 또는 간단히 map(python 3) 사용할 수 있습니다 .

>>> def my_condition(x):
...     return x % 4 == 3
... 
>>> sum(map(my_condition, l))
2

1
@mgilson : 나는 그것이 계산을 수행하지 않는다고 생각합니다. start기본값은 0이므로 첫 번째 추가는 True + 0, 아니오입니다.
DSM

4
예. 내가 좀 더 명확하게해야 할 것 같은데 ... 뭐가 중요하지 않아요 int(True). int("1") == 1하지만 그렇다고해서 할 수 있다는 의미는 아닙니다 "1" + 0. 중요한 것은 파이썬이 integer + True또는 integer + False.
mgilson 2013 년

2
@mgilson : 흠, 좋아, 당신은 나를 설득했습니다.
DSM

4
요점은 이것이 bool의 하위 클래스 int이므로 bool과 int를 쉽게 추가 할 수 있습니다 ( True값이 1이고 False값이 0 임).
mgilson 2013 년

글쎄, 그것이 내가 언급함으로써 얻은 것입니다 int(True) == 1. 그러나 당신의 요점은 int("1") == 1그것을 그렇게 줄여서 사실이 아닌 것을 암시 할 수 있다는 것을 증명합니다.
DSM

21

당신은 원하는 발전기 이해 보다는 여기에 목록을.

예를 들면

l = [1, 4, 6, 7, 30, 2]

def my_condition(x):
    return x > 5 and x < 20

print sum(1 for x in l if my_condition(x))
# -> 2
print sum(1 for x in range(1000000) if my_condition(x))
# -> 14

또는 사용하십시오 itertools.imap(명시 적 목록 및 생성기 표현식이 다소 파이썬 적이라고 생각하지만).

sum예제에서는 명확하지 않지만 생성기 이해를 멋지게 구성 할 수 있습니다. 예를 들면

inputs = xrange(1000000)      # In Python 3 and above, use range instead of xrange
odds = (x for x in inputs if x % 2)  # Pick odd numbers
sq_inc = (x**2 + 1 for x in odds)    # Square and add one
print sum(x/2 for x in sq_inc)       # Actually evaluate each one
# -> 83333333333500000

이 기술의 멋진 점은 최종 결과가 평가 될 때까지 메모리에 평가 및 저장을 강요하지 않고도 코드에서 개념적으로 별도의 단계를 지정할 수 있다는 것입니다.


10

reduce함수형 프로그래밍을 선호하는 경우이를 사용하여 수행 할 수도 있습니다.

reduce(lambda count, i: count + my_condition(i), l, 0)

이렇게하면 한 번만 통과하고 중간 목록이 생성되지 않습니다.


7

다음과 같이 할 수 있습니다.

l = [1,2,3,4,5,..]
count = sum(1 for i in l if my_condition(i))

조건을 충족하는 각 요소에 대해 1을 더합니다.


당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.