專欄地址:每週一個 Python 模塊html
operator 模塊是 Python 中內置的操做符函數接口,它定義了算術,比較和與標準對象 API 相對應的其餘操做的內置函數。python
operator 模塊是用 C 實現的,因此執行速度比 Python 代碼快。git
from operator import *
a = -1
b = 5
print('a =', a)
print('b =', b)
print()
print('not_(a) :', not_(a)) # False
print('truth(a) :', truth(a)) # True
print('is_(a, b) :', is_(a, b)) # False
print('is_not(a, b):', is_not(a, b)) # True
複製代碼
not_()
包括尾隨下劃線,由於not
是 Python 的關鍵字。 truth()
做爲判斷表達式用在if
語句中,或者將一個表達式轉換成bool
。 is_()
和is
關鍵字的用法同樣,is_not()
用法相同,只不過返回相反的答案。github
from operator import *
a = 1
b = 5.0
print('a =', a)
print('b =', b)
for func in (lt, le, eq, ne, ge, gt):
print('{}(a, b): {}'.format(func.__name__, func(a, b)))
# a = 1
# b = 5.0
# lt(a, b): True
# le(a, b): True
# eq(a, b): False
# ne(a, b): True
# ge(a, b): False
# gt(a, b): False
複製代碼
功能是等同於使用表達式語法<
, <=
,==
,>=
,和>
。app
from operator import *
a = -1
b = 5.0
c = 2
d = 6
print('\nPositive/Negative:')
print('abs(a):', abs(a)) # abs(a): 1
print('neg(a):', neg(a)) # neg(a): 1
print('neg(b):', neg(b)) # neg(b): -5.0
print('pos(a):', pos(a)) # pos(a): -1
print('pos(b):', pos(b)) # pos(b): 5.0
print('\nArithmetic:')
print('add(a, b) :', add(a, b)) # add(a, b) : 4.0
print('floordiv(a, b):', floordiv(a, b)) # floordiv(a, b): -1.0
print('floordiv(d, c):', floordiv(d, c)) # floordiv(d, c): 3
print('mod(a, b) :', mod(a, b)) # mod(a, b) : 4.0
print('mul(a, b) :', mul(a, b)) # mul(a, b) : -5.0
print('pow(c, d) :', pow(c, d)) # pow(c, d) : 64
print('sub(b, a) :', sub(b, a)) # sub(b, a) : 6.0
print('truediv(a, b) :', truediv(a, b)) # truediv(a, b) : -0.2
print('truediv(d, c) :', truediv(d, c)) # truediv(d, c) : 3.0
print('\nBitwise:')
print('and_(c, d) :', and_(c, d)) # and_(c, d) : 2
print('invert(c) :', invert(c)) # invert(c) : -3
print('lshift(c, d):', lshift(c, d)) # lshift(c, d): 128
print('or_(c, d) :', or_(c, d)) # or_(c, d) : 6
print('rshift(d, c):', rshift(d, c)) # rshift(d, c): 1
print('xor(c, d) :', xor(c, d)) # xor(c, d) : 4
複製代碼
使用序列的運算符能夠分爲四組:構建序列,搜索項目,訪問內容以及從序列中刪除項目。less
from operator import *
a = [1, 2, 3]
b = ['a', 'b', 'c']
print('\nConstructive:')
print(' concat(a, b):', concat(a, b)) # concat(a, b): [1, 2, 3, 'a', 'b', 'c']
print('\nSearching:')
print(' contains(a, 1) :', contains(a, 1)) # contains(a, 1) : True
print(' contains(b, "d"):', contains(b, "d")) # contains(b, "d"): False
print(' countOf(a, 1) :', countOf(a, 1)) # countOf(a, 1) : 1
print(' countOf(b, "d") :', countOf(b, "d")) # countOf(b, "d") : 0
print(' indexOf(a, 5) :', indexOf(a, 1)) # indexOf(a, 5) : 0
print('\nAccess Items:')
print(getitem(b, 1)) # b
print(getitem(b, slice(1, 3))) # ['b', 'c']
print(setitem(b, 1, "d") # None
print(b) # ['a', 'd', 'c']
print(setitem(a, slice(1, 3), [4, 5])) # None
print(a) # [1, 4, 5]
print('\nDestructive:')
print(delitem(b, 1)) # None
print(b) # ['a', 'c']
print(delitem(a, slice(1, 3)) # None
print(a) # [1]
複製代碼
其中一些操做(例如setitem()
和delitem()
)修改了序列而且不返回值。函數
除了標準運算符以外,許多類型的對象還支持經過特殊運算符進行「原地」修改 ,+=
一樣具備就地修改的功能:測試
from operator import *
a = -1
b = 5.0
c = [1, 2, 3]
d = ['a', 'b', 'c']
a = iadd(a, b)
print('a = iadd(a, b) =>', a) # a = iadd(a, b) => 4.0
c = iconcat(c, d)
print('c = iconcat(c, d) =>', c) # c = iconcat(c, d) => [1, 2, 3, 'a', 'b', 'c']
複製代碼
operator 模塊最特別的特性之一就是獲取方法的概念,獲取方法是運行時構造的一些可回調對象,用來獲取對象的屬性或序列的內容,獲取方法在處理迭代器或生成器序列的時候特別有用,它們引入的開銷會大大下降 lambda 或 Python 函數的開銷。spa
from operator import *
class MyObj:
"""example class for attrgetter"""
def __init__(self, arg):
super().__init__()
self.arg = arg
def __repr__(self):
return 'MyObj({})'.format(self.arg)
l = [MyObj(i) for i in range(5)]
print(l) # [MyObj(0), MyObj(1), MyObj(2), MyObj(3), MyObj(4)]
# Extract the 'arg' value from each object
g = attrgetter('arg')
vals = [g(i) for i in l]
print('arg values:', vals) # arg values: [0, 1, 2, 3, 4]
# Sort using arg
l.reverse()
print(l) # [MyObj(4), MyObj(3), MyObj(2), MyObj(1), MyObj(0)]
print(sorted(l, key=g)) # [MyObj(0), MyObj(1), MyObj(2), MyObj(3), MyObj(4)]
複製代碼
operator
模塊中的函數經過標準 Python 接口進行操做,所以它能夠使用用戶定義的類以及內置類型。.net
from operator import *
class MyObj:
"""Example for operator overloading"""
def __init__(self, val):
super(MyObj, self).__init__()
self.val = val
def __str__(self):
return 'MyObj({})'.format(self.val)
def __lt__(self, other):
"""compare for less-than"""
print('Testing {} < {}'.format(self, other))
return self.val < other.val
def __add__(self, other):
"""add values"""
print('Adding {} + {}'.format(self, other))
return MyObj(self.val + other.val)
a = MyObj(1)
b = MyObj(2)
print('Comparison:')
print(lt(a, b))
# Comparison:
# Testing MyObj(1) < MyObj(2)
# True
print('\nArithmetic:')
print(add(a, b))
# Arithmetic:
# Adding MyObj(1) + MyObj(2)
# MyObj(3)
複製代碼
operator 模塊還包含一些函數用來測試映射、數字和序列類型的 API 兼容性。
from operator import *
class NoType(object):
pass
class MultiType(object):
def __len__(self):
return 0
def __getitem__(self, name):
return "mapping"
def __int__(self):
return 0
o = NoType()
t = MultiType()
for func in [isMappingType, isNumberType, isSequenceType]:
print "%s(o):" % func.__name__, func(o)
print "%s(t):" % func.__name__, func(t)
# isMappingType(o): False
# isMappingType(t): True
# isNumberType(o): False
# isNumberType(t): True
# isSequenceType(o): False
# isSequenceType(t): True
複製代碼
使用 methodcaller 能夠獲取對象的方法。
from operator import methodcaller
class Student(object):
def __init__(self, name):
self.name = name
def getName(self):
return self.name
stu = Student("Jim")
func = methodcaller('getName')
print func(stu) # 輸出Jim
複製代碼
還能夠給方法傳遞參數:
f = methodcaller('name', 'foo', bar=1)
f(b) # return b.name('foo', bar=1)
複製代碼
methodcaller方法等價於下面這個函數:
def methodcaller(name, *args, **kwargs):
def caller(obj):
return getattr(obj, name)(*args, **kwargs)
return caller
複製代碼
相關文檔: