私はちょうどばかげた小さなヘルパー関数を発明しました:
def has_one(seq, predicate=bool):
"""Return whether there is exactly one item in `seq` that matches
`predicate`, with a minimum of evaluation (short-circuit).
"""
iterator = (item for item in seq if predicate(item))
try:
iterator.next()
except StopIteration: # No items match predicate.
return False
try:
iterator.next()
except StopIteration: # Exactly one item matches predicate.
return True
return False # More than one item matches the predicate.
私が思いついた最も読みやすい/慣用的なインラインのものは次のとおりだったからです。
[predicate(item) for item in seq].count(True) == 1
... seq が小さいことはわかっているので、私の場合は問題ありませんが、奇妙に感じます。このヘルパーを壊す必要がないようにする、ここで忘れているイディオムはありますか?
明確化
振り返ってみると、これはちょっとくだらない質問でしたが、いくつかの優れた回答が得られました! 私はどちらかを探していました:
- 明白で読みやすいインライン イディオムまたは stdlib 関数。この場合、熱心な評価が受け入れられます。
- より明白で読みやすいヘルパー関数 -- 他の関数全体を分割しているため、最小限の評価のみが許容されるようです。
@Stephan202はヘルパー関数の非常にクールなイディオムを思いつき、 @ Martin v. Löwisは、述語が bool を返すという仮定の下で、より単純なインライン イディオムを思いつきました。助けてくれてありがとう@みんな!