首页 > 代码库 > Python OOP(2)-static method,class method and instance method

Python OOP(2)-static method,class method and instance method

 

静态方法(Static Method)

一种简单函数,符合以下要求:

1.嵌套在类中。

2.没有self参数。

特点

1.类调用、实例调用,静态方法都不会接受自动的self参数。

2.会记录所有实例的信息,而不是为实例提供行为。

 简单说staticmethod 无法访问类属性、实例属性,相当于一个相对独立的方法,跟类其实没什么关系,换个角度来讲,其实就是放在一个类的作用域里的函数而已。

 

#!python2#-*- coding:utf-8 -*-class A:    v1="class argu"        def __init__(self):        self.v1="instance argu"            def fun1():        print "Static fun"            fun1=staticmethod(fun1)    a=A()#实例调用a.v1instance argu#类调用A.v1class argua.fun1()            A.fun1()

 

另一种写法是在python2.4以后用装饰器decorator

#!python2#-*- coding:utf-8 -*-class A:    v1="class argu"        def __init__(self):        self.v1="instance argu"         @staticmethod           def fun1():        print "Static fun"            a=A()#实例调用a.v1instance argu#类调用A.v1class argua.fun1()            A.fun1()

 

类方法(Class Method)

一种函数,符合以下特征

1.类调用、或实例调用,传递的参数是一个类对象。

注意classmethod 可以访问类属性,无法访问实例属性。上述的变量val1,在类里是类变量,在实例中又是实例变量,所以容易混淆

适用于:

 

程序需要处理与类而不是与实例相关的数据。也就是说这种数据信息通常存储在类自身上,不需要任何实例也可以处理。

 

例如:

 

1.记录有一个类创建的实例的数目。

 

2.维护当前内存中一个类的所有实例的列表。

 

以上情况也可以同以下方式解决:

 

在类定义之外生成一个的简单函数

 

 

#记录实例创建数目def amountinstance():    print "Amount of instances is : %d" %(c1.numInstance)        class c1:    numInstance=0    def __init__(self):        c1.numInstance+=1        a=c1()b=c1()c=c1()amountinstance()3

 

因为类名称对简单函数而言,是可读取的全局变量,所以看到上例可以正常工作。

此外,函数名变成了全局变量,故仅适用于这个单一模块。

这样处理的缺点如下:

1.给文件的作用域添加了一个额外的名称,该名称仅能处理单个的类,不能应付多个类需要处理的情况。

2.该函数与类的直接关联很小,函数的定义可能在数百行代码之外的位置。

3.该函数位于类的命名空间之外,子类不能通过重新定义来代替或扩展它。

 

 

 

 

 

class MyClass:    val1 = Value 1    def __init__(self):        self.val2 = Value 2    def staticmd():        print 静态方法,无法访问val1和val2    smd = staticmethod(staticmd)    def classmd(cls):        print 类方法,类: + str(cls) + ,val1: + cls.val1 + ,无法访问val2的值    cmd = classmethod(classmd)                mc = MyClass()mc.cmd()类方法,类:__main__.MyClass,val1:Value 1,无法访问val2的值MyClass.cmd()类方法,类:__main__.MyClass,val1:Value 1,无法访问val2的值

 

另一种写法是在python2.4以后用装饰器decorator

class MyClass:    val1 = Value 1    def __init__(self):        self.val2 = Value 2            @staticmethod            def staticmd():        print 静态方法,无法访问val1和val2        @classmethod        def classmd(cls):        print 类方法,类: + str(cls) + ,val1: + cls.val1 + ,无法访问val2的值                mc = MyClass()mc.classmd()类方法,类:__main__.MyClass,val1:Value 1,无法访问val2的值MyClass.classmd()类方法,类:__main__.MyClass,val1:Value 1,无法访问val2的值#实例的val1与类的val1是不一样的,类方法可以访问的是类的val1mc.val1 = Value changedmc.classmd()类方法,类:__main__.MyClass,val1:Value 1,无法访问val2的值MyClass.classmd()类方法,类:__main__.MyClass,val1:Value 1,无法访问val2的值MyClass.val1=Value changedmc.classmd()类方法,类:__main__.MyClass,val1:Value changed,无法访问val2的值MyClass.classmd()类方法,类:__main__.MyClass,val1:Value changed,无法访问val2的值

 

最后汇总instance method, static method 和class method 的实现和调用

 

#!python2#-*- coding:utf-8 -*-class Methods():            def im(self,v2):        self.v2=v2        print "Call instance method: %d " % v2            @staticmethod        def sm(v2):        print "Call static method: %d " % v2            @classmethod        def cm(cls,v2):        print "Call class method: %d " % v2        obj=Methods()    #instance method call #实例方法调用一定要将类实例化,方可通过实例调用obj.im(1)Call instance method: 1 Methods.im(obj,1)Call instance method: 1 #static method call#静态方法调用时不需要实例参数obj.sm(2)Call static method: 2 Methods.sm(2)Call static method: 2 #class method call# 类方法调用时,Python会把类(不是实例)传入类方法第一个(最左侧)参数cls(默认)obj.cm(3)Call class method: 3 Methods.cm(3)Call class method: 3 

 

Python OOP(2)-static method,class method and instance method