Python 面向對象 補充 方法相關

私有化方法

class Person(object):
    __age = 18

    def __run(self):
        print('pao')

內置特殊方法

生命週期方法
其他內置方法:信息格式化操作,調用操作,索引操作,切片操作,迭代器,描述器

生命週期方法

信息格式化操作

__str__

面向用戶使用

class Person(object):
    def __init__(self, n, a):
        self.name = n
        self.age = a
    
    def __str__(self):
        return 'name: %s, age: %s'%(self.name, self.age)
        
p1 = Person('sz', 18)
print(p1)

p2 = Person('zhangsan', 19)
print(p2)

s = str(p1)
print(s, type(s))

name: sz, age: 18
name: zhangsan, age: 19
name: sz, age: 18 <class ‘str’>

__repr__

面向開發者使用

class Person(object):
    def __init__(self, n, a):
        self.name = n
        self.age = a
    
    def __str__(self):
        return 'name: %s, age: %s'%(self.name, self.age)
        
    def __repr__(self):
        return 'reprxxx'


p1 = Person('sz', 18)
print(p1)

p2 = Person('zhangsan', 19)
print(p2)

s = str(p1)
print(s, type(s))

print(repr(p1))

name: sz, age: 18
name: zhangsan, age: 19
name: sz, age: 18 <class ‘str’>
reprxxx

調用操作

__call__

作用:使對象具備當作函數來調用的能力
使用:

class Person(object):
    def __call__(self, *args, **kwargs):
        print('xxx', args, kwargs)

p = Person()
p(123, 456, name='zs')

xxx (123, 456) {‘name’: ‘zs’}

實例:

# 創建很多畫筆,畫筆的類型(鋼筆,鉛筆),畫筆的顏色(紅,黃)
class PenFactory(object):
    def __init__(self, p_type):
        self.p_type = p_type
    
    def __call__(self, p_color):
        print('創建了一個%s的畫筆,它是%s顏色' % (self.p_type, p_color))
        
gangbiF = PenFactory('鋼筆')
gangbiF('紅色')

qianbiF = PenFactory('鉛筆')
qianbiF('黃色')

創建了一個鋼筆的畫筆,它是紅色顏色
創建了一個鉛筆的畫筆,它是黃色顏色

索引操作

可以對一個實例對象進行索引操作

class Person:
    def __init__(self):
        self.cache = {}

    def __setitem__(self, key, value):
        print('setitem', key, value)
        self.cache[key] = value
    
    def __getitem__(self, item):
        print('getitem', item)
        return self.cache[item]
    
    def __delitem__(self, key):
        print('delitem', key)
        del self.cache[key]

p = Person()
p['name'] = 'sz'

print(p['name'])

del p['name']

print(p.cache)

setitem name sz
getitem name
sz
delitem name
{}

切片操作

class Person:
    def __init__(self):
        self.items = [1,2,3,4,5,6,7,8 ]

    def __setitem__(self, key, value):
        # print('setitem', key, value)
        # print(key.start)
        # print(key.stop)
        # print(key.step)
        # print(value)
        if isinstance(key, slice):
            self.items[key] = value

    def __getitem__(self, item):
        print('getitem', item)
    #     return self.cache[item]
    
    def __delitem__(self, key):
        print('delitem', key)
    #     del self.cache[key]

p = Person()
p[0:4:2] = ['a', 'b']
print(p.items)

[‘a’, 2, ‘b’, 4, 5, 6, 7, 8]

比較操作

class Person:
    def __init__(self, age, height):
        self.age = age
        self.height = height

    # ==
    def __eq__(self, other):
        print(other)
        return self.age == other.age
    
    # !=
    def __ne__(self, other):
        print('xxx')

    # >
    def __gt__(self, other):
        pass


    # >=
    def __ge__(self, other):
        pass

    # <
    def __lt__(self, other):
        pass

    # <=
    def __le__(self, other):
        pass

p1 = Person(18, 190)
p2 = Person(18, 180)

print(p1 == p2)
print(p1 != p2)

比較操作-註釋事項

如果對於反向操作的比較符,只定義了其中的一個方法,但使用的是另外一種比較運算。那麼,解釋器會採用調換參數的方式進行調用該方法。但不支持疊加操作。

class Person:
    def __init__(self, age, height):
        self.age = age
        self.height = height

    # <
    def __lt__(self, other):
        print('lt')
        print(self.age)
        print(other.age)
        return self.age < other.age

p1 = Person(18, 190)
p2 = Person(19, 180)

print(p1 < p2)
print(p1 > p2) 

lt
18
19
True
lt
19
18
False

import functools

@functools.total_ordering
class Person:
    def __init__(self, age, height):
        self.age = age
        self.height = height

    # <
    def __lt__(self, other):
        print('lt')
        return False

    def __eq__(self, other):
        print('eq')



p1 = Person(18, 190)
p2 = Person(19, 180)


print(p1 <= p2)
print(Person.__dict__)

lt
eq
None
{‘module’: ‘main’, ‘init’: <function Person.init at 0x03960E40>, ‘lt’: <function Person.lt at 0x03960E88>, ‘eq’: <function Person.eq at 0x03960ED0>, ‘dict’: <attribute ‘dict’ of ‘Person’ objects>, ‘weakref’: <attribute ‘weakref’ of ‘Person’ objects>, ‘doc’: None, ‘hash’: None, ‘gt’: <function _gt_from_lt at 0x02D66C90>, ‘le’: <function _le_from_lt at 0x02D66CD8>, ‘ge’: <function _ge_from_lt at 0x02D66D20>}

比較操作-上下文布爾值

class Person:
    def __init__(self):
        self.age = 10

    def __bool__(self):
        return False

p = Person()

if p:
    print('xx')

遍歷操作

class Person:
    def __init__(self):
        self.result = 1

    def __getitem__(self, item):
        self.result += 1
        if self.result >= 6:
            raise StopIteration('停止遍歷')

        return self.result

p = Person()

for i in p:
    print(i)

2
3
4
5

__next__

class Person:
    def __init__(self):
        self.result = 1

    # def __getitem__(self, item):
    #     print('getitem')
    #     self.result += 1
    #     if self.result >= 6:
    #         raise StopIteration('停止遍歷')
    #     return self.result

    def __iter__(self):
        print('iter')
        return self
    
    def __next__(self):
        self.result += 1
        if self.result >= 6:
            raise StopIteration('停止遍歷')
        return self.result




p = Person()

for i in p:
    print(i)

iter
2
3
4
5

class Person:
    def __init__(self):
        self.result = 1

    # def __getitem__(self, item):
    #     print('getitem')
    #     self.result += 1
    #     if self.result >= 6:
    #         raise StopIteration('停止遍歷')
    #     return self.result

    def __iter__(self):
        print('iter')
        return self
    
    def __next__(self):
        self.result += 1
        if self.result >= 6:
            raise StopIteration('停止遍歷')
        return self.result




p = Person()

print(next(p))
print(next(p))
print(next(p))
print(next(p))
print(next(p))

2
3
4
5

StopIteration: 停止遍歷

迭代器的複用

class Person:
    def __init__(self):
        self.age = 1

    def __iter__(self):
        print('iter')
        self.age = 1
        return self
    
    def __next__(self):
        self.age += 1
        if self.age >= 6:
            raise StopIteration('停止遍歷')
        return self.age


p = Person()
for i in p:
    print(i)

for i in p:
    print(i)

import collections
print(isinstance(p, collections.Iterator))

iter
2
3
4
5
iter
2
3
4
5
d:\python\test\test2.py:25: DeprecationWarning: Using or importing the ABCs from ‘collections’ instead of from ‘collections.abc’ is deprecated, and in 3.8 it will stop working
print(isinstance(p, collections.Iterator))
True

可迭代的判定依據

class Person:
    def __init__(self):
        self.age = 1

    def __iter__(self):
        print('iter')
        self.age = 1
        return self
    
    def __next__(self):
        self.age += 1
        if self.age >= 6:
            raise StopIteration('停止遍歷')
        return self.age


p = Person()
for i in p:
    print(i)

import collections
print(isinstance(p, collections.Iterator))
print(isinstance(p, collections.Iterable))

iter
2
3
4
5
d:\python\test\test2.py:22: DeprecationWarning: Using or importing the ABCs from ‘collections’ instead of from ‘collections.abc’ is deprecated, and in 3.8 it will stop working
print(isinstance(p, collections.Iterator))
True
d:\python\test\test2.py:23: DeprecationWarning: Using or importing the ABCs from ‘collections’ instead of from ‘collections.abc’ is deprecated, and in 3.8 it will stop working
print(isinstance(p, collections.Iterable))
True

iter函數的使用

class Person:
    def __init__(self):
        self.age = 1

    def __iter__(self):
        print('iter')
        self.age = 1
        return self
    
    def __next__(self):
        self.age += 1
        if self.age >= 6:
            raise StopIteration('停止遍歷')
        return self.age
    
    def __call__(self, *args, **kwargs):
        self.age += 1
        if self.age >= 6:
            raise StopIteration('停止遍歷')
        return self.age



p = Person()

# pt = iter(p.__next__, 4)
pt = iter(p, 4)

print(pt)
print(pt is p)


for i in pt:
    print(i)

<callable_iterator object at 0x0450AB30>
False
2
3

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章