zoukankan      html  css  js  c++  java
  • python的对象和类

    1:在Python中所有的都是对象,class 是一个对象,class的实例也是一个对象。在java或者c++中,class 是不用来存放数据的,只有class的实例才存放
        数据

    1 class class1(object):
    2     pass
    1 if __name__=='__main__':
    2     test = class1()
    3     print class1
    4     print test

      class1是一个对象,print 出来的结果:<class '__main__.class1'>
     那么 test也是一个对象,test.__class__也是一个对象
     


    2:在python中所有的对象允许动态的添加属性或者方法,当类添加属性之后,类的实例同样能够访问该对象
        如果修改了类的__class__的属性或者方法,那么该类对性的实例同样也具有该类的方法或者属性

     1 class class1(object):
     2     pass
     3 
     4 if __name__=='__main__':
     5     test = class1()
     6     #print class1
     7     #print test
     8    
     9 test.__class__.newAttr=10
    10     test1 = class1()
    11     print test1.newAttr

       
        当我们通过test.__class__修改了class1类的属性之后,给class1添加了个新的属性newAttr=10
        则重新test = class1()新的实例后,新的实例拥有newAttr这个属性,
        对于添加新的方法同样如此
       


      3:每个实例都有__dict__来存放动态的属性,查看一下代码:

     1 class class1(object):
     2     pass
     3 
     4 if __name__=='__main__':
     5     test = class1()
     6     #print class1
     7     #print test
     8        
     9     test.__class__.newAttr=10
    10     test1 = class1()
    11     print test.__dict__
    12     print test.__class__.__dict__
    13     print test1.__dict__
    14     print test1.__class__.__dict__
    15     test1.newAttr2=20
    16     print test.__dict__
    17     print test.__class__.__dict__
    18     print test1.__dict__
    19     print test1.__class__.__dict__


    4:继承:当继承后,python不会像java,c++那样在子类的实例中包含父类的实例,子类的实例是个全新的对象,与父类一点关系都没有
            不会包含有父类的任何东西,继承只是在子类的__base__指向了父类在查找函数,属性的过程中会查找父类
            仅此而已,而这个父类也是class对象

    5:类里的变量不是以self,开头定义的都是类变量,相当于java,c++里的static,所有实例共享他们

    6:python为每一个对象定义了一些属性和方法
            __doc__
            __module__
            __class__
            __bases__
            __dict__


    7:python的继承
    基类 __init__ / __del__ 需显示调用
    继承方法的调用和基类声明顺序有关
    在成员名称前添加 "__" 使其成为私有成员。
    除了静态(类型)字段,我们还可以定义静态方法。

    1 class Class1:
    2     @staticmethod
    3     def test():
    4     print "static method"
    5    
    6 Class1.test()
    7 static method

               
    从设计的角度,或许更希望用属性(property)来代替字段(field)。

     1 class Class1:
     2     def __init__(self):
     3         self.__i = 1234
     4     def getI(self): return self.__i
     5     def setI(self, value): self.__i = value
     6     def delI(self): del self.__i
     7     I = property(getI, setI, delI, "Property I")
     8                  
     9 a = Class1()
    10 a.I
    11 1234
    12 a.I = 123456
    13 a.I
    14 123456
    15                 

    如果只是 readonly property,还可以用另外一种方式。
     

     1 class Class1:
     2     def __init__(self):
     3         self.__i = 1234 
     4     @property
     5     def I(self):
     6         return self.__i
     7                  
     8 a = Class1()
     9 a.I
    10 1234
    11                 

                   
    用 __getitem__ 和 __setitem__ 可以实现 C# 索引器的功能。

    class Class1:
        def __init__(self):
            self.__x = ["a", "b", "c"]
        def __getitem__(self, key):
            return self.__x[key]
        def __setitem__(self, key, value):
            self.__x[key] = value
                                
    a = Class1()
    a[1]
    'b'
    a[1] = "xxxx"
    a[1]
    'xxxx'


    8:python的多重继承
    由于python的继承主要是将几个对象建立关系,因此多重继承最重要的就是怎样在多个父类中寻找某个attribute
    python寻找attribute的顺序:  

    1. If attrname is a Python-provided attribute for objectname, return it.

    2. Check objectname.__class__.__dict__ for attrname. If it exists and is a data-descriptor, return the descriptor result. Search all bases of objectname.__class__ for the same case.

    3. Check objectname.__dict__ for attrname, and return if found. Unless objectname is a type object, in which case search its bases too. If it is a type object and a descriptor is found in the object or its bases, return the descriptor result.

    4. Check objectname.__class__.__dict__ for attrname. If it exists and is a non-data descriptor, return the descriptor result. If it exists, and is not a descriptor, just return it. If it exists and is a data descriptor, we shouldn't be here because we would have returned at point 2. Search all bases of objectname.__class__ for same case.

    5. Raise AttributeError



    9:python重载
    我们还可以通过重载 __getattr__ 和 __setattr__ 来拦截对成员的访问,需要注意的是 __getattr__ 只有在访问不存在的成员时才会被调用。

     1 class Class1:
     2     def __getattr__(self, name):
     3         print "__getattr__"
     4         return None
     5     def __setattr__(self, name, value):
     6         print "__setattr__"
     7         self.__dict__[name] = value
     8        
     9 
    10            
    11 >>> a = Class1()
    12 >>> a.x
    13 __getattr__
    14 >>> a.x = 123
    15 __setattr__
    16 >>> a.x
    17 123
    18         

    如果类型继承自 object,我们可以使用 __getattribute__ 来拦截所有(包括不存在的成员)的获取操作。
    注意在 __getattribute__ 中不要使用 "return self.__dict__[name]" 来返回结果,因为在访问 "self.__dict__" 时同样会被 __getattribute__ 拦截,从而造成无限递归形成死循环。

     1 class Class1(object):
     2     def __getattribute__(self, name):
     3          print "__getattribute__"
     4          return object.__getattribute__(self, name)
     5        
     6 >>> a = Class1()
     7 >>> a.x
     8 __getattribute__
     9        
    10 Traceback (most recent call last):
    11 File "<pyshell#3>", line 1, in <module>
    12 a.x
    13 File "<pyshell#1>", line 4, in __getattribute__
    14 return object.__getattribute__(self, name)
    15 AttributeError: 'Class1' object has no attribute 'x'
    16 >>> a.x = 123
    17 >>> a.x
    18 __getattribute__
    19 123
  • 相关阅读:
    【SQL】oralce中使用group by和case when按照条件求和
    【SQL】ORACLE在sqlplus中使用spool方式生成建表语句
    【SQL】将特定的元素按照自己所需的位置排序
    【LeetCode刷题】SQL-Second Highest Salary 及扩展以及Oracle中的用法
    【LeetCode刷题】SQL-Combine Two Tables
    CSDN无故封我账号,转战博客园。
    Visual Studio 代码管理器svn插件下载
    Geoserver的跨域问题
    Jmeter+Ant+jenkins实现api自动化测试的持续集成
    python编程中的并发------多线程threading模块
  • 原文地址:https://www.cnblogs.com/huazi/p/2491869.html
Copyright © 2011-2022 走看看