2017-04-07 1 views
1

一部のコードでバグが発生しました。2つのリストの間に "and"を使用すると、(エラーではなく)2番目のリストが表示されるのはなぜですか?

[x for x in range(3, 6) and range(0, 10)] 
print x 

[0, 1, 2, 3, 4, 5, 6, 7, 8, 9] 

someList and someOtherListが何をするか疑問に思う、私は実験

(この文を書くの正しい方法は、問題の一部ではありません):(間違った)ラインは類似していました。今まで渡された最後のパラメータに結果を設定しているようだ:

x = range(0,3) # [0, 1, 2] 
y = range(3, 10) # [3, 4, 5, 6, 7, 8, 9] 
z = range(4, 8) # [4, 5, 6, 7] 

print x and y  # [3, 4, 5, 6, 7, 8, 9] 
print y and x  # [0, 1, 2] 
print z and y and x # [0, 1, 2] 

私は、これは便利です何かを書くことができるという意図しない結果であることを前提としていますが、私はどのように見て本当にないんだけどここでは "and"演算子のセマンティクスが適用されています。

経験上、Pythonは演算子をサポートしていないもの(つまり、TypeErrorを吐き出しているもの)に演算子を適用しないため、となるべきではないというエラーがあります。 -ed。私が間違いを起こさないという事実は、私が行方不明になっていることを私に伝えることです。

私には何が欠けていますか? list and listはなぜ許可された操作ですか?そして、この動作で何か「有用な」ものがありますか?

+1

質問はブール値についてですが、答えは関係なく、種類の適用 –

+0

おかげ@TimCastelijns – KidneyChris

+0

私はリンクの質問は、問題がちょうどブールリスト(それは任意のリストだ)ではないことは言うことができると思いますが、私は本当にないんだことここにたくさん追加します。重複して閉じるのは楽しいです。 – KidneyChris

答えて

2

andオペレータは、最初のオペランドの真実をチェックします。真理度がFalseの場合、最初の引数が返されます。それ以外の場合は2番目の引数が返されます。

両方range(..) sが要素が含まれているのであれば、最後オペランドが返されます。だからあなたの式は:、

[x for x in range(3, 6) if x in range(0, 10)]

range(..)しかしでリストを構築し、それを作る:

[x for x in range(0, 10)] 

あなたはしかし、フィルタリングするifを使用することができます。

[x for x in range(3, 6) and range(0, 10)] 

に相当しますひどく効率的ではない。我々はxintであることを知っているので、我々は境界は次のようにチェックしますかすることができ、この場合にはもちろん

[x for x in range(3, 6) if 0 <= x < 10]

range(3,6)内のすべての要素がrange(0,10)の範囲内にあるので、チェックは無用です。

+0

同様に(そして一般的にもっと便利です)リスト上で 'or'演算子を使って空でない最初のリストを返します。 – Phylogenesis

+0

@Phylogenesis:はい、確かに。 'or'は' True'真実性を持つ最初の要素を返します。 –

関連する問題