python _魔法方法

基本的魔法方法
init(self[, …])

·构造器,当一个实例被创建的时候调用的初始化方法
new(cls[, …])

·new 是在一个对象实例化的时候所调用的第一个方法,在调用 init 初始化前,先调用__new__。
·new 至少要有一个参数cls,代表要实例化的类,此参数在实例化时由 Python 解释器自动提供,后面的参数直接传递给__init__。
·new`对当前类进行了实例化,并将实例返回,传给__init__的self。但是,执行了__new__,并不一定会进入__init__,只有__new__返回了,当前类cls的实例,当前类的__init__才会进入。
·若__new__没有正确返回当前类cls的实例,那__init__是不会被调用的,即使是父类的实例也不行,将没有__init__被调用。
·可利用__new__实现单例模式

class Earth:
    pass


a = Earth()
print(id(a))  # 260728291456
b = Earth()
print(id(b))  # 260728291624

class Earth:
    __instance = None  # 定义一个类属性做判断

    def __new__(cls):
        if cls.__instance is None:
            cls.__instance = object.__new__(cls)
            return cls.__instance
        else:
            return cls.__instance


a = Earth()
print(id(a))  # 512320401648
b = Earth()
print(id(b))  # 512320401648

在这里插入图片描述
·__new__方法主要是当你继承一些不可变的 class 时(比如int, str, tuple), 提供给你一个自定义这些类的实例化过程的途径。
del(self)

析构器,当一个对象将要被系统回收之时调用的方法。
在这里插入图片描述
str__和__repr
str(self)
当你打印一个对象时
当你使用 %s格式化的时候、
str强制转换类型的时候
会触发__str__
repr
有__str__时执行__str__,没有实现__str__的时候,执行__repr__
__repr(obj)内置函数对应的结果是__repr__的返回值
使用%r时,触发__repr

算术运算符
在这里插入图片描述
反算术运算符
反运算魔方方法,与算术运算符保持一一对应,不同之处就是反运算的魔法方法多了一个“r”。当文件左操作不支持相应的操作时被调用。
radd(self, other)定义加法的行为:+
rsub(self, other)定义减法的行为:-
rmul(self, other)定义乘法的行为:*
rtruediv(self, other)定义真除法的行为:/
rfloordiv(self, other)定义整数除法的行为://
rmod(self, other) 定义取模算法的行为:%
rdivmod(self, other)定义当被 divmod() 调用时的行为
rpow(self, other[, module])定义当被 power() 调用或 ** 运算时的行为
rlshift(self, other)定义按位左移位的行为:<<
rrshift(self, other)定义按位右移位的行为:>>
rand(self, other)定义按位与操作的行为:&
rxor(self, other)定义按位异或操作的行为:^
ror(self, other)定义按位或操作的行为:|
增量赋值运算符
iadd(self, other)定义赋值加法的行为:+=
isub(self, other)定义赋值减法的行为:-=
imul(self, other)定义赋值乘法的行为:*=
itruediv(self, other)定义赋值真除法的行为:/=
ifloordiv(self, other)定义赋值整数除法的行为://=
imod(self, other)定义赋值取模算法的行为:%=
ipow(self, other[, modulo])定义赋值幂运算的行为:**=
ilshift(self, other)定义赋值按位左移位的行为:<<=
irshift(self, other)定义赋值按位右移位的行为:>>=
iand(self, other)定义赋值按位与操作的行为:&=
ixor(self, other)定义赋值按位异或操作的行为:^=
ior(self, other)定义赋值按位或操作的行为:|=
一元运算符
neg(self)定义正号的行为:+x
pos(self)定义负号的行为:-x
abs(self)定义当被abs()调用时的行为
invert(self)定义按位求反的行为:~x
属性访问
在这里插入图片描述
描述符

class MyDecriptor:
    def __get__(self, instance, owner):
        print('__get__', self, instance, owner)

    def __set__(self, instance, value):
        print('__set__', self, instance, value)

    def __delete__(self, instance):
        print('__delete__', self, instance)


class Test:
    x = MyDecriptor()


t = Test()
t.x
# __get__ <__main__.MyDecriptor object at 0x000000CEAAEB6B00> <__main__.Test object at 0x000000CEABDC0898> <class '__main__.Test'>

t.x = 'x-man'
# __set__ <__main__.MyDecriptor object at 0x00000023687C6B00> <__main__.Test object at 0x00000023696B0940> x-man

del t.x
# __delete__ <__main__.MyDecriptor object at 0x000000EC9B160A90> <__main__.Test object at 0x000000EC9B160B38>

定制序列
如果说你希望定制的容器是不可变的话,你只需要定义__len__()和__getitem()方法。
如果你希望定制的容器是可变的话,除了__len
()和__getitem__()方法,你还需要定义__setitem__()和__delitem()__两个方法。
编写一个不可改变的自定义列表,要求记录列表中每个元素被访问的次数。

class CountList:
    def __init__(self, *args):
        self.values = [x for x in args]
        self.count = {}.fromkeys(range(len(self.values)), 0)

    def __len__(self):
        return len(self.values)

    def __getitem__(self, item):
        self.count[item] += 1
        return self.values[item]


c1 = CountList(1, 3, 5, 7, 9)
c2 = CountList(2, 4, 6, 8, 10)
print(c1[1])  # 3
print(c2[2])  # 6
print(c1[1] + c2[1])  # 7

print(c1.count)
# {0: 0, 1: 2, 2: 0, 3: 0, 4: 0}

print(c2.count)
# {0: 0, 1: 1, 2: 1, 3: 0, 4: 0}

编写一个可改变的自定义列表,要求记录列表中每个元素被访问的次数。

class CountList:
    def __init__(self, *args):
        self.values = [x for x in args]
        self.count = {}.fromkeys(range(len(self.values)), 0)

    def __len__(self):
        return len(self.values)

    def __getitem__(self, item):
        self.count[item] += 1
        return self.values[item]

    def __setitem__(self, key, value):
        self.values[key] = value

    def __delitem__(self, key):
        del self.values[key]
        for i in range(0, len(self.values)):
            if i >= key:
                self.count[i] = self.count[i + 1]
        self.count.pop(len(self.values))


c1 = CountList(1, 3, 5, 7, 9)
c2 = CountList(2, 4, 6, 8, 10)
print(c1[1])  # 3
print(c2[2])  # 6
c2[2] = 12
print(c1[1] + c2[2])  # 15
print(c1.count)
# {0: 0, 1: 2, 2: 0, 3: 0, 4: 0}
print(c2.count)
# {0: 0, 1: 0, 2: 2, 3: 0, 4: 0}
del c1[1]
print(c1.count)
# {0: 0, 1: 0, 2: 0, 3: 0}

迭代器
迭代器有两个基本的方法:iter() 和 next()。
·iter(object) 函数用来生成迭代器。
·next(iterator[, default]) 返回迭代器的下一个项目。
·iterator – 可迭代对象
·default – 可选,用于设置在没有下一个元素时返回该默认值,如果不设置,又没有下一个元素则会触发 StopIteration 异常。

links = {'B': '百度', 'A': '阿里', 'T': '腾讯'}
it = iter(links)
print(next(it))  # B
print(next(it))  # A
print(next(it))  # T
print(next(it))  # StopIteration


it = iter(links)
while True:
    try:
        each = next(it)
    except StopIteration:
        break
    print(each)

# B
# A
# T

生成器
在 Python 中,使用了 yield 的函数被称为生成器(generator)。
跟普通函数不同的是,生成器是一个返回迭代器的函数,只能用于迭代操作,更简单点理解生成器就是一个迭代器。
在调用生成器运行的过程中,每次遇到 yield 时函数会暂停并保存当前所有的运行信息,返回 yield 的值, 并在下一次执行 next() 方法时从当前位置继续运行。
调用一个生成器函数,返回的是一个迭代器对象
在这里插入图片描述
在这里插入图片描述
推导式
在这里插入图片描述
今天刚刚学完,时间有点紧了,先随便写写明天再来改进,嘻嘻!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值