首先,和定义函数的 def 一样, class 是定义类的关键字。
紧接着的是类名,这个可以自定义,同样的,不能和python的内置关键字冲突。建议首字母大写,例如Myclass
然后是一个括号,里面的参数是用于继承的,一般继承于 object,表示一个新式类。另外,你可能见过没有括号的写法,这是经典类的写法。
class NewClass(object):
pass
class OldClass:
pass
New = NewClass() # 创建一个新式类的实例
Old = OldClass() # 创建一个经典类的实例
构造器方法
般可以理解类中的函数就是方法,而方法分为:实例方法,只有实例化后才能调用的,其第一个参数一般为 self,代表实例本身;类方法,其第一个参数为 cls,代表类本身;还有静态方法,就是个普通函数,没有要求参数。
1. __init__(self [,arg1,....]):
当类被调用进行实例化的时候,python会自动调用类里面的构造函数(如果有的话),在构造函数中,可以进行各种初始化的操作,最常见的就是上面的进行实例的属性的创建。
python 在示例化的时候,会检查其实行了 __init__ 方法了没有,如果没有则不对实例进行任何操作,然后返回对象。如果实行了这个方法,则自动调用这个方法,并自动将 self 传进行,也就是说我们在实例化进行传参的时候,将不用理会 self,直接传给后面的参数。
讲到属性,就必须要提一下什么是属性。属性其实更像一个变量,大多数对象都可以有属性(不包括python的内置类型),例如函数。
def Test(): pass Test.a = 123 print Test.a
因为函数也是一个对象。
属性在类中,就是一个变量,但是,函数名也是一个变量名。所以,所谓的属性就是:属于一个对象的数据或者函数元素。
例如:
class NewClass(object): a = 123 print NewClass.a
当然,因为 python 的特性,我们可以在运作中为某个对象添加属性,而不用一开始就在类中写定。
注意,这个方法应该返回 None,也就是说我们一般不用 return 任何对象,让它默认返回就行了。
2. __new__(cls [,arg1,....]):
这也是一个构造器方法,它是一个类方法,一般在对 python 的不可变数据类型进行继承扩展的时候用的比较多。
某处拿来的代码示例:
class RoundFloat(float): def __new__(cls, val): return super(RoundFloat, cls).__new__(cls, round(val, 2)) a = RoundFloat(3.14159) print a
关于类的继承以后再讲。
这个方法不同之处在于它必须返回一个合法的实例。这里的 cls 也是自动传递的。
解构器方法
__del__(self [,arg1,....])
这个方法将会在对象所以的引用被清除后才执行,例如:
class Test(object): def __del__(self): print '我被干掉了,兄弟们为我报仇!' a = Test() # 创建了一个对象 b = a # b又引用了a c = b # c又引用了b,现在 a 所指向的对象有3次引用,相当有三条命 del a # 干掉一条命 del b # 又干掉 del c # 听说你有3条命?全部干掉!
注意,这里只输出了一次,也就是说到了最后才删除完毕。这里要注意一下几点:
1.调用 del 并不意味着完成删除某个对象,只是减少引用。
2.如果你有一个循环引用或其它的原因,让一个实例的引用逗留不去,该对象的__del__()可能永远不会被执行。
3.__del__()未捕获的异常会被忽略掉(因为一些在__del__()用到的变量或许已经被删除了)。 不要在__del__()中干与实例没任何关系的事情。
4.一般情况下并不用实现这个方法,因为这样有一定的风险。
5.如果你定义了__del__,并且实例是某个循环的一部分,垃圾回收器将不会终止这个循环— —你需要自已显式调用 del。
6.如果继承了父类,且父类中也有解构器,要记得调用。否则可能会有某些在父类中的清理方法没有调用到,出现以下无法预料的错误。
属性就是属于一个对象的数据或者函数,我们可以通过句点(.)来访问属性,
同时 python 还支持在运作中添加和修改属性。
类中的方法,其实就是类中的函数,可以分为:实例方法,类方法,静态方法。方法和字段一样,也是属于类的属性,所以也具有运行中修改的特效, 但一般不推荐这样做。
我在类的基本语法中,介绍了构造器方法:__init__ 、__new__;解构器方法:__del__;
注意,这里虽然是以两个下划线(__)开头,但同时以两个下划线(__)结尾,这里表明其是一个‘魔法方法’,关于类中的魔法方法,将起一篇进行说明。
但是,如果单纯只以两个下划线开始,则依然是私有化的意思,看代码示例:
class Test(object): def __scolia__(self): # 一个类似魔术方法,并不是私有化 return 'scolia' def __good(self): # 私有方法 return 'good' a = Test() print a.__scolia__() # 魔法方法可以在直接访问 print a.__good() # 私有方法不能直接访问
同样的,和字段私有化一样,我们也可能同特殊手段进行强制访问:
print a._Test__good() # 强制访问
当然,私有方法也可以在类的内部访问,和私有字段一样。
所以说,属性的私有化都是对访问入口进行混淆,同样的,也不建议强制访问私有属性。
也许这里的‘魔法方法’看起来并不‘魔法’,详情将以后解释。