반환 값이 아닌 부작용을 위해 호출하는 함수 (화면에 인쇄, GUI 업데이트, 파일로 인쇄 등)를 생각해보십시오.
def fun_with_side_effects(x):
...side effects...
return y
이제이 func를 호출하기 위해 목록 이해력을 사용하는 것이 Pythonic입니까 ?
[fun_with_side_effects(x) for x in y if (...conditions...)]
목록을 어디에도 저장하지 않습니다.
또는이 func를 다음과 같이 호출해야합니다.
for x in y:
if (...conditions...):
fun_with_side_effects(x)
어느 것이 더 낫고 그 이유는 무엇입니까?
답변
그렇게하는 것은 매우 반 파이 토닉이며 노련한 Pythonista는 당신에게 지옥을 줄 것입니다. 중간 목록은 생성 된 후 버려 지므로 잠재적으로 매우 크고 생성 비용이 많이들 수 있습니다.
답변
사람들이 말했듯이 필요하지 않은 큰 임시 목록을 만들 것이기 때문에 목록 이해력을 사용해서는 안됩니다 . 다음 두 가지 방법은 동일합니다.
consume(side_effects(x) for x in xs)
for x in xs:
side_effects(x)
man 페이지 consume
에서 정의 itertools
:
def consume(iterator, n=None):
"Advance the iterator n-steps ahead. If n is none, consume entirely."
# Use functions that consume iterators at C speed.
if n is None:
# feed the entire iterator into a zero-length deque
collections.deque(iterator, maxlen=0)
else:
# advance to the empty slice starting at position n
next(islice(iterator, n, n), None)
물론 후자는 더 명확하고 이해하기 쉽습니다.
답변
목록 이해는 목록을 만드는 데 사용됩니다. 그리고 실제로 목록을 작성하지 않는 한 목록 이해를 사용 해서는 안됩니다 .
그래서 두 번째 옵션을 얻었습니다. 목록을 반복 한 다음 조건이 적용될 때 함수를 호출합니다.
답변
두 번째가 더 좋습니다.
코드를 이해해야하는 사람을 생각해보십시오. 첫 번째로 쉽게 업장을 얻을 수 있습니다 🙂
filter ()를 사용하여 둘 사이의 중간에 갈 수 있습니다. 예를 고려하십시오.
y=[1,2,3,4,5,6]
def func(x):
print "call with %r"%x
for x in filter(lambda x: x>3, y):
func(x)
답변
목표에 따라 다릅니다.
목록의 각 개체에 대해 몇 가지 작업을 수행하려는 경우 두 번째 방법을 채택해야합니다.
다른 목록에서 목록을 생성하려는 경우 목록 이해를 사용할 수 있습니다.
명시적인 것이 암시적인 것보다 낫습니다. 단순한 것이 복잡한 것보다 낫습니다. (파이썬 젠)
답변
넌 할 수있어
for z in (fun_with_side_effects(x) for x in y if (...conditions...)): pass
하지만 그다지 예쁘지 않습니다.
답변
부작용에 대한 목록 이해력을 사용하는 것은 추악하고 비파이 토닉이며 비효율적이며 저는 그렇게하지 않을 것입니다. for
루프 for
는 부작용이 중요한 절차 적 스타일을 나타 내기 때문에 대신 루프를 사용합니다 .
그러나 부작용에 대한 목록 이해를 절대적으로 사용해야한다면 생성기 표현식을 대신 사용하여 비 효율성을 피해야합니다. 이 스타일을 절대적으로 고집한다면 다음 두 가지 중 하나를 수행하십시오.
any(fun_with_side_effects(x) and False for x in y if (...conditions...))
또는:
all(fun_with_side_effects(x) or True for x in y if (...conditions...))
이들은 생성기 표현식이며 버려지는 무작위 목록을 생성하지 않습니다. 나는 생각 all
나는 그들 모두가 혼란하고 사용할 수 없습니다한다고 생각하지만 형태가 약간 아마 더 분명하다.
나는 이것이 추악하다고 생각하고 실제로 코드에서 그것을하지 않을 것입니다. 하지만 이런 방식으로 루프를 구현해야한다고 주장한다면 그렇게 할 것입니다.
나는 목록 이해력과 그들의 ilk가 적어도 기능적 스타일과 약간 닮은 것을 사용하려는 시도를 나타내야한다고 생각하는 경향이 있습니다. 그 가정을 깨뜨리는 부작용이있는 것을 넣으면 사람들이 당신의 코드를 더주의 깊게 읽어야하는데, 그것은 나쁜 것이라고 생각합니다.