2012-07-11 121 views
16

這是一個可能愚蠢的問題,但看着the mapping of operators to functions我注意到,沒有功能來表示not in運營商。起初我以爲這可能是因爲解釋器重新排序爲not x in y,但有一個is not的功能,它看起來應該與not in完全一樣。我錯過了什麼,或者那個操作員真的不存在?python運營商,沒有運營商的「不在」

這裏是一個非常愚蠢的例子,你可能希望這樣的:

def compare_iter(a,b,func): 
    return [func(aa,bb) for aa,bb in zip(a,b)] 

my_compare=compare_iter(xx,yy,lambda x,y:x not in y) #lambda -- yuck 
my_compare=map(operator.not_,compare_iter(xx,yy,operator.contains) #extra map? grr... 
#it would be nice to do: my_compare=compare_iter(xx,yy,operator.not_contains) 

當然,我可以寫我自己的這個功能,但是你的效率,而運營商模塊付出的代價可能會出推動這個代碼的python,因此執行速度更快。

+0

確實,不能'a不是b'只是被重新排序爲'不是a是b'? – JAB 2012-07-11 14:51:51

+0

有沒有檢查'不在'可能比檢查'in'更快的情況? – 2012-07-11 14:53:29

+1

@PaulManta令人懷疑,因爲'不在'根據定義是一個徹底的搜索。 – 2012-07-11 14:56:19

回答

14

另一個功能在這裏沒有必要。 not inin倒數,所以你有以下映射:

obj in seq => contains(seq, obj) 

obj not in seq => not contains(seq, obj) 

你是對的,這是不是與is/is not一致的,因爲身份測試應該是對稱的。這可能是一個設計神器。

+1

考慮到這一點,在我看來,另一個操作符*應該是必要的。 'x> y'並不一定(暗示)python中的not(x <= y)'。爲什麼要測試遏制有什麼不同? – mgilson 2012-07-12 21:00:21

3

您可能會發現下面的函數和拆卸,爲了解運營商是有幫助的:

>>> def test(): 
     if 0 in(): pass 
     if 0 not in(): pass 
     if 0 is(): pass 
     if 0 is not(): pass 
     return None 

>>> dis.dis(test) 
    2   0 LOAD_CONST    1 (0) 
       3 LOAD_CONST    2 (()) 
       6 COMPARE_OP    6 (in) 
       9 POP_JUMP_IF_FALSE  15 
      12 JUMP_FORWARD    0 (to 15) 

    3  >> 15 LOAD_CONST    1 (0) 
      18 LOAD_CONST    3 (()) 
      21 COMPARE_OP    7 (not in) 
      24 POP_JUMP_IF_FALSE  30 
      27 JUMP_FORWARD    0 (to 30) 

    4  >> 30 LOAD_CONST    1 (0) 
      33 LOAD_CONST    4 (()) 
      36 COMPARE_OP    8 (is) 
      39 POP_JUMP_IF_FALSE  45 
      42 JUMP_FORWARD    0 (to 45) 

    5  >> 45 LOAD_CONST    1 (0) 
      48 LOAD_CONST    5 (()) 
      51 COMPARE_OP    9 (is not) 
      54 POP_JUMP_IF_FALSE  60 
      57 JUMP_FORWARD    0 (to 60) 

    6  >> 60 LOAD_CONST    0 (None) 
      63 RETURN_VALUE   
>>> 

正如你所看到的,有在各個運營商的差異;和他們的代碼(按順序)是6,7,8和9.

+2

是的,但是如果你在()中不是0,它會將它轉換爲0而不是在()中 - 這讓我更加想到,運算符模塊中應該有一個對應的運算符爲「不在」顯然是解釋者的獨特(甚至是首選)操作員... – mgilson 2012-07-11 15:47:47

+2

@mgilson:剛注意到我自己。我認爲這將是另一種方式,但現在我發現自己同意你的觀點。有趣的是,儘管討論了它的實用性,但我似乎無法在官方的Python郵件列表中找到關於在操作符中加入'not in'的討論。 – JAB 2012-07-11 15:58:08

+1

@JAB,你可以發佈一些關於實用性的討論鏈接嗎? (這個問題對我來說主要是學術問題,我很想看看其他人對實際使用案例的看法)有沒有辦法要求添加它? – mgilson 2012-07-11 16:00:22