1. 鸭子类型:
当你看到一只鸟走来像鸭子,游泳起来像鸭子,叫起来也像鸭子,他么他就可以叫做鸭子。任何可迭代的对象。一样的方法,可以用可迭代的话,就可以迭代的组合打印。__getitem__可以塞到任何的类中,跟鸭子类型一样,指定相同的方法名。魔法函数正是充分运用了鸭子类型,能够被本身调用。
class Cat(object): def say(self): print("i am a cat") class Dog(object): def say(self): print("i am a dog") def __getitem__(self, item): return "bobby" class Duck(object): def say(self): print("i am a duck") animal_lst = [Cat,Dog,Duck] for animal in animal_lst: animal().say() class Company: def __init__(self,employee_list): self.employee = employee_list def __getitem__(self, item): return self.employee[item] a = ["bobby1","bobby2"] b = ["bobby2","bobby"] name_tuple = ("bobby3","bobby4") name_set = set() name_set.add("bobby5") name_set.add("bobby6") # a.extend(b) # a.extend(name_tuple) company = Company(["a",[b],"c"]) a.extend(company) print(a)
2. 抽象基类(abc模块):
abstract base class
可以当做接口。Py的抽象基类也不能实例化的。
变量在Py当中就是一个符号。可以指向任何对象。
Py信奉的是鸭子类型。把鸭子类型放在第一位。
# 我们去检查某个类是否具有某种方法。(应用场景一) class Company(object): def __init__(self,employee_list): self.employee = employee_list def __len__(self): return len(self.employee) com = Company(['bobby1','bobby2']) print(hasattr(com,"__len__")) # 我们在某些情况之下希望判定某个对象的类型 from collections.abc import Sized isinstance(com,Sized) # 我们需要强制某个子类必须去实现某些方法 # 实现了web框架,继承cache(redis,cache,memerycache) # 需要设计一个抽象基类,执行子类必须实现某些方法 # 如何去模拟一个抽象基类 import abc # metaclass=abc.ABCMeta class CacheBase(metaclass=abc.ABCMeta): @abc.abstractmethod def get(self, key): pass @abc.abstractmethod def set(self, key, value): pass class RediCache(CacheBase): def set(self, key, value): pass def get(self, key): pass redis_cache = RediCache() redis_cache.set("key","value")
记住:抽象的是基类:必须metaclass = abc.ABCMeta
记住:抽象基类后有abc.abstractmethod抽象方法,和,abcabstractpropery抽象属性。
记住:抽象基类的主要作用是“定义”接口。
记住:用的是import abc这个抽象基类,而不是from collections.abc import abc
记住:使用__subclasshook__后只要具体类定义了与抽象类相同的方法就认为是他的子类
import abc class A(object): __metaclass__ = abc.ABCMeta @abc.abstractmethod def say(self): return 'say yeah' @classmethod def __subclasshook__(cls, C): if cls is A: if any("say" in B.__dict__ for B in C.__mro__): return True return NotTmplementd class B(object): def say(self): return 'hello' print issubclass(B, A) # True print isinstance(B(), A) # True print B.__dict__ # {'say': <function say at 0x7f...>, ...} print A.__subclasshook__(B) # True
__mro__ 表示多继承的顺序。