13、 Python 中重载
函数重载主要是为了解决两个问题。
1 可变参数类型。 2 可变参数个数。
另外,一个基本的设计原则是,仅仅当两个函数除了参数类型和参数个数不同以外,其功能是完全相同的,此时才使用函数重载,如果两个函数的功能其实不同,那么不应当使用重载,而应当使用一个名字不同的函数。
好吧,那么对于情况1,函数功能相同,但是参数类型不同,python 如何处理?答案是根本不需要处理,因为python可以接受任何类型的参数,如果函数的功能相同,那么不同的参数类型在python中很可能是相同的代码,没有必要做成两个不同函数。
那么对于情况2,函数功能相同,但参数个数不同,python如何处理?大家知道,答案就是缺省参数。对那些缺少的参数设定为缺省参数即可解决问题。因为你假设函数功能相同,那么那些缺少的参数终归是需要用的。
好了,鉴于情况1跟情况2都有了解决方案,python自然就不需要函数重载了。
14、新式类和旧式类
Python中类分两种:旧式类和新式类:新式类都从object继承,经典类不需要。
新式类的MRO(method resolution order 基类搜索顺序)算法采用C3算法广度优先搜索,而旧式类的MRO算法是采用深度优先搜索新式类相同父类只执行一次构造函数,经典类重复执行多次。
其中:
截止到python2.1,只存在旧式类。旧式类中,类名和type是无关的:如果x 是一个旧式类,那么x.__class__定义了x的类名,但是type(x)总是返回<type
'instance'>。这反映了所有的旧式类的实例是通过一个单一的叫做instance 的内建类型来实现的,这是它和类不同的地方。新式类是在python2.2为了统一类和实例引入的。一个新式类只能由用户自定义。如果x是一个新式类的实例,那么type(x)和x.__class__是一样的结果(尽管这不能得到保证,因为新式类的实例的__class__方法是允许被用户覆盖的)。 Python 2.x中默认都是经典类,只有显式继承了object才是新式类
Python 3.x中默认都是新式类,经典类被移除,不必显式的继承object
15、 __new__和__init__的区别
这个__new__确实很少见到,先做了解吧.
__new__是一个静态方法,而__init__是一个实例方法. __new__方法会返回一个创建的实例,而__init__什么都不返回. 只有在__new__返回一个cls的实例时后面的__init__才能被调用. 当创建一个新实例时调用__new__,初始化一个实例时用__init__. ps: __metaclass__是创建类时起作用.所以我们可以分别使用 __metaclass__,__new__和__init__来分别在类创建,实例创建和实例初始化的时候做一些小手脚.
16、单例模式
这个绝对常考啊.绝对要记住1~2个方法,当时面试官是让手写的.
1 使用__new__方法
class Singleton(object): def __new__(cls, *args, **kw): if not hasattr(cls, '_instance'): orig = super(Singleton, cls) cls._instance = orig.__new__(cls, *args,
**kw)
return cls._instance
class MyClass(Singleton): a = 1 2 共享属性
创建实例时把所有实例的__dict__指向同一个字典,这样它们具有相同的属性和方法. class Borg(object): _state = {} def __new__(cls, *args, **kw): ob = super(Borg, cls).__new__(cls, *args, **kw) ob.__dict__ = cls._state return ob class MyClass2(Borg):
a = 1
3 装饰器版本
def singleton(cls, *args, **kw):
instances = {} def getinstance():
if cls not in instances:
instances[cls] = cls(*args, **kw) return instances[cls]
return getinstance
@singleton class MyClass:
...
4 import方法
作为python的模块是天然的单例模式
# mysingleton.py class My_Singleton(object): def foo(self): pass
my_singleton = My_Singleton()
# to use
from mysingleton import my_singleton
my_singleton.foo()
17、Python 中的作用域
Python 中,一个变量的作用域总是由在代码中被赋值的地方所决定的。当 Python 遇到一个变量的话他会按照这样的顺序进行搜索:本地作用域(Local)→当前作用域被嵌入的本地作用域(Enclosing locals)
→全局/模块作用域(Global)→内置作用域(Built-in)
18、闭包
闭包(closure)是函数式编程的重要的语法结构。闭包也是一种组织代码的结构,它同样提高了代码的可重复使用性。
当一个内嵌函数引用其外部作作用域的变量,我们就会得到一个闭包. 总结一下, 创建一个闭包必须满足以下几点:
必须有一个内嵌函数内嵌函数必须引用外部函数中的变量外部函数的返回值必须是内嵌函数感觉闭包还是有难度的,几句话是说不明白的,还是查查相关资料.
重点是函数运行后并不会被撤销,就像16题的instance字典一样,当函数运行完后,instance并不被销毁,而是继续留在内存空间里.这个功能类似类里的类变量,只不过迁移到了函数上.
闭包就像个空心球一样,你知道外面和里面,但你不知道中间是什么样.
19、lambda 函数
其实就是一个匿名函数,为什么叫lambda?因为和后面的函数式编程有关.