面向对象基本知识:

  • 面向对象是一种编程方式,此编程方式的实现是基于对 对象 的使用
  • 类 是一个模板,模板中包装了多个“函数”供使用(可以将多函数中公用的变量封装到对象中)
  • 对象,根据模板创建的实例(即:对象),实例用于调用被包装在类中的函数
  • 面向对象三大特性:封装、继承和多态

面向对象类成员

一、变量

变量包括:类变量和实例变量,他们在定义和使用中有所区别,而最本质的区别是内存中保存的位置不同,

类变量:属于类

实例变量:属于实例

  1. class Role(object):
  2. #类变量,在内存中仅保存一份
  3. ac = None
  4. def __init__(self,name,role,weapon,life_value):
  5. #实例变量,保存在各个实例中
  6. self.name = name
  7. self.role = role
  8. self.weapon = weapon
  9. self.life_value = life_value
  10.  
  11. def buy_gun(self,weapon):
  12. print("%s is buying [%s]" %(self.name,weapon))
  13. self.weapon = weapon
  14.  
  15. p1 = Role("p1",'police','b12',)
  16. t1 = Role("t1",'tufei','b11',)
  17. t2 = Role("t2",'tufei','b13',)
  18. t3 = Role("t3",'tufei','b14',)
  19.  
  20. #实例赋值,将创建新的变量给实例
  21. p1.ac = "China Brand"
  22. t1.ac = "US Brand"
  23. #类变量赋值,实例中没有创建该变量,继续使用类变量赋的值
  24. Role.ac = "JP Brand"
  25. print("p1:",p1.weapon,p1.ac)
  26. print("t1:",t1.weapon,t1.ac)
  27. print("t2:",t2.weapon,t2.ac)
  28. print("t3:",t3.weapon,t3.ac)

由上述代码可以看出【实例变量需要通过对象来访问】【类变量可以通过类访问】,在使用上可以看出类变量和实例变量的归属是不同的。其在内容的存储方式类似如下图:

由上图可知:

  • 类变量在内存中只保存一份
  • 实例变量在每个实例中都要保存一份

应用场景: 通过类创建实例时,如果每个对象都具有相同的变量,那么就使用类变量。

二、方法

方法包括:普通方法、静态方法和类方法,三种方法在内存中都归属于类,区别在于调用方式不同。

  • 普通方法:由对象调用;至少一个self参数;执行普通方法时,自动将调用该方法的对象赋值给self
  • 类方法:由调用; 至少一个cls参数;执行类方法时,自动将调用该方法的复制给cls
  • 静态方法:由调用;无默认参数;
  1. class Foo:
  2. def __init__(self, name):
  3. self.name = name
  4.  
  5. def ord_func(self):
  6. """ 定义普通方法,至少有一个self参数 """
  7. # print self.name
  8. print('普通方法')
  9.  
  10. @classmethod
  11. #类方法,不能访问实例变量
  12. def class_func(cls):
  13. """ 定义类方法,至少有一个cls参数 """
  14. print('类方法')
  15.  
  16. @staticmethod
  17. #静态方法,只是放在类下面,不能访问类和实例属性
  18. def static_func():
  19. """ 定义静态方法 ,无默认参数"""
  20. print('静态方法')

相同点:对于所有的方法而言,均属于类(非对象)中,所以,在内存中也只保存一份。

不同点:方法调用者不同、调用方法时自动传入的参数不同。

三、属性  

如果你已经了解Python类中的方法,那么属性就非常简单了,因为Python中的属性其实是普通方法的变种。

对于属性,有以下三个知识点:

  • 属性的基本使用
  • 属性的两种定义方式
  1. class foo(object):
  2. def __init__(self,name):
  3. self.name = name
  4. self.num = None
  5. #属性,将普通方法变成属性
  6. @property
  7. def total_num(self):
  8. return self.num
  9.  
  10. @total_num.setter
  11. def total_num(self,num):
  12. self.num = num
  13. print("total number is:",self.num)
  14.  
  15. @total_num.deleter
  16. def total_num(self):
  17. print("total number got deleted")
  18. del self.num

  19. #实例化
  20. d = Animal("who")
  21. #调用属性
    print(d.total_num)
  22. #属性赋值
    d.total_num =
  23. #删除属性
    del d.total_num
  24. #报错num已经被删除
    print(d.total_num)

由属性的定义和调用要注意一下几点:

  • 定义时,在普通方法的基础上添加 @property 装饰器;
  • 定义时,属性仅有一个self参数
  • 调用时,无需括号
               方法:obj.func()
               属性:obj.total_num

注意:属性存在意义是:访问属性时可以制造出和访问字段完全相同的假象

属性由方法变种而来,如果Python中没有属性,方法完全可以代替其功能。

四、类的私有化

类的所有成员都有两种形式:

  • 公有成员,在任何地方都能访问
  • 私有成员,只有在类的内部才能方法

定义不同:私有成员命名时,前两个字符是下划线。(特殊成员除外,例如:__init__、__call__、__dict__等)

  1. class Animal(object):
  2. def __init__(self, name):
  3. self.name = name #公有变量
  4. self.__num = None #私有变量

访问限制:只有在类的内部可以访问。。。

  1. class C(object):
  2. __name = "私有类变量"
  3. def func(self):
  4. print(C.__name)
  5.  
  6. class D(C):
  7. def show(self):
  8. print(C.__name) #AttributeError: type object 'C' has no attribute '_D__name'
  9. #print(D.__name) #AttributeError: type object 'D' has no attribute '_D__name'
  10.  
  11. C.__name #类访问,出错
  12. obj = C()
  13. obj.func() #类内部可以访问
  14. obj_son = D() #无法继承私有类属性
  15. obj_son.show() #派生类访问,出错
  1. class E(object):
  2. def __init__(self):
  3. self.__foo = "私有实例变量"
  4. def func(self):
  5. print(self.__foo) #类内部访问
  6. class F(E):
  7. def show(self):
  8. print(self.__foo) #派生类访问
  9.  
  10. obj2 = E()
  11. obj2.__foo #通过对象直接访问,出错
  12. print(obj2._E__foo) #访问私有实例变量
  13. obj2.func() #类内部访问
  14. obj2_son = F()
  15. obj2_son.show() #派生类中访问,出错
  1. 方法、属性的访问于上述方式相似,即:私有成员只能在类内部使用,无法被继承
    ps:非要访问私有属性的话,可以通过 对象.___属性名
  2. 五、类的特殊成员
  1. class foo(object):
  2. """
  3. __doc__显示类的描述信息
  4. """
  5. def __init__(self):
  6. """
  7. 注:构造方法的执行是由创建对象触发的,即:对象 = 类名() ;
  8. """
  9. self.name = None
  10. self.age = None
  11. self.sq = []
  12. def __call__(self):
  13. """
  14. __call__ 方法的执行是由对象后加括号触发的,即:对象() 或者 类()()
  15. """
  16. print("__call__")
  17. def __str__(self):
  18. """
  19. 如果一个类中定义了__str__方法,那么在打印 对象 时,默认输出该方法的返回值。
  20. :return:
  21. """
  22. return "啥"
  23. def __iter__(self):
  24. """
  25. 用于迭代器,之所以列表、字典、元组可以进行for循环,是因为类型内部定义了 __iter__
  26. """
  27. return iter(self.sq)
  28. def __del__(self):
  29. pass
  30. #def __new__(self):
  31. """
  32. __new__方法接受的参数虽然也是和__init__一样,但__init__是在类实例创建之后调用,而 __new__方法正是创建这个类实例的方法。
  33. 一般不用使用这个方法,否则你将无法实例化对象
  34. """
  35. #pass

  36. #实例化对象
  37. f = foo() #自动执行__init__方法
  38. f() #:对象() 或者 类()()调用__call__
  39. foo()() #调用call方法
  40. print(f.__doc__) #显示类的描述信息
  41. print(f.__dict__) #类或对象中的所有成员
  42. print(f) #方法输出__str__方法定义的返回值
  43. for i in f:print(i) #类型内部定义了 __iter__,可以迭代
  44.  
  45. #test.py
    import foo
    obj = foo()
    print(obj.__module__) # 表示当前操作的对象在那个模块
    print(obj.__class__) # 表示当前操作的对象在那个类
    print(isinstance(obj,foo))
  1.  

 __module__ 和  __class__ 

  __module__ 表示当前操作的对象在那个模块

  __class__     表示当前操作的对象的类是什么

  1. class C:
  2.  
  3. def __init__(self):
  4. self.name = 'wupeiqi'
  1. from lib.aa import C
  2.  
  3. obj = C()
  4. print obj.__module__ # 输出 lib.aa,即:输出模块
  5. print obj.__class__ # 输出 lib.aa.C,即:输出类

__dict__

  类或对象中的所有成员

上文中我们知道:类的普通字段属于对象;类中的静态字段和方法等属于类,即:

  1. class Province:
  2.  
  3. country = 'China'
  4.  
  5. def __init__(self, name, count):
  6. self.name = name
  7. self.count = count
  8.  
  9. def func(self, *args, **kwargs):
  10. print 'func'
  11.  
  12. # 获取类的成员,即:静态字段、方法、
  13. print Province.__dict__
  14. # 输出:{'country': 'China', '__module__': '__main__', 'func': <function func at 0x10be30f50>, '__init__': <function __init__ at 0x10be30ed8>, '__doc__': None}
  15.  
  16. obj1 = Province('HeBei',)
  17. print obj1.__dict__
  18. # 获取 对象obj1 的成员
  19. # 输出:{'count': , 'name': 'HeBei'}
  20.  
  21. obj2 = Province('HeNan', )
  22. print obj2.__dict__
  23. # 获取 对象obj1 的成员
  24. # 输出:{'count': , 'name': 'HeNan'}

__dict__

__iter__ 

用于迭代器,之所以列表、字典、元组可以进行for循环,是因为类型内部定义了 __iter__

  1. class Foo(object):
  2. pass
  3.  
  4. obj = Foo()
  5.  
  6. for i in obj:
  7. print i
  8.  
  9. # 报错:TypeError: 'Foo' object is not iterable

第一步

  1. #!/usr/bin/env python
  2. # -*- coding:utf- -*-
  3.  
  4. class Foo(object):
  5.  
  6. def __iter__(self):
  7. pass
  8.  
  9. obj = Foo()
  10.  
  11. for i in obj:
  12. print i
  13.  
  14. # 报错:TypeError: iter() returned non-iterator of type 'NoneType'

第二步

  1. #!/usr/bin/env python
  2. # -*- coding:utf- -*-
  3.  
  4. class Foo(object):
  5.  
  6. def __init__(self, sq):
  7. self.sq = sq
  8.  
  9. def __iter__(self):
  10. return iter(self.sq)
  11.  
  12. obj = Foo([,,,])
  13.  
  14. for i in obj:
  15. print i

第三步

  1. 以上步骤可以看出,for循环迭代的其实是  iter([11,22,33,44]) ,所以执行流程可以变更为
    #!/usr/bin/env python
  2. # -*- coding:utf- -*-
  3.  
  4. obj = iter([,,,])
  5.  
  6. for i in obj:
  7. print i

六、反射
python中的反射功能是由以下四个内置函数提供:hasattr、getattr、setattr、delattr,这四个函数分别用于对对象内部执行:检查是否含有某成员、获取成员、设置成员、删除成员。

  1. class Foo(object):
  2.  
  3. def __init__(self):
  4. self.name = 'wupeiqi'
  5.  
  6. def func(self):
  7. return 'func'
  8.  
  9. obj = Foo()
  10.  
  11. # #### 检查是否含有成员 ####
  12. hasattr(obj, 'name')
  13. hasattr(obj, 'func')
  14.  
  15. # #### 获取成员 ####
  16. getattr(obj, 'name')
  17. getattr(obj, 'func')
  18.  
  19. # #### 设置成员 ####
  20. setattr(obj, 'age', )
  21. setattr(obj, 'show', lambda num: num + )
  22.  
  23. # #### 删除成员 ####
  24. delattr(obj, 'name')
  25. delattr(obj, 'func')
  1. 反射实例
  1. import sys
  2. class Webserver(object):
  3. def __init__(self,host,port):
  4. self.host = host
  5. self.port = port
  6. def start(self):
  7. print("Server is starting...")
  8. def stop(self):
  9. print("Server is stopping...")
  10. def restart(self):
  11. self.stop()
  12. self.start()
  13.  
  14. #def test_run(name):
  15. # print("test running...",name)
  16.  
  17. def test_run(self,name): #定义函数,setter添加该函数至实例方法
  18. print("test running...",name,self.host)
  19.  
  20. if __name__ == "__main__":
  21. server = Webserver("1.1.1.1",)
  22. server2 = Webserver("2.2.2.2",)
  23. #第三种实现 反射
  24. if hasattr(server,sys.argv[]): #判断sys.argv[]是否在对象server中
  25. func = getattr(server,sys.argv[]) #获取server.method内存地址
  26. func() #执行server.method()
  27. setattr(server,"run",test_run) #在该实例 server 中,添加方法 run 方法名,test_run 函数,无法为方法自动传入self
  28. #server.run("koka") #执行添加不带self参数的test_run,无法调用实例变量
  29. server.run(server,"koka") #执行添加self参数的test_run,调用的时候需要手动添加实例

  30. setattr(server,"root","koka") #该在实例中添加变量,同上
  31. print(server.root)      #调用实例变量
  32. #print(server2.root) #其他实例无法调用
  33. delattr(Webserver,'start') #删除类中的start方法
  34. print(server.restart())
  35. """
  36. 判断用户输入是否存在实例
  37. #第一种实现 一个一个输出匹配
  38. if sys.argv[] == "start":
  39.     执行server.start()
  40. #第二种实现 定义字典查找
  41. cmd_dic ={
  42. "start":server.start,
  43. "stop":server.stop
  44. }
  45. if sys.argv[] in cmd_dic:
  46. cmd_dic[sys.argv[]]()
  47.  
  48. """

结论:反射是通过字符串的形式操作对象相关的成员。一切事物都是对象!!!

更多内容请参考:http://www.cnblogs.com/wupeiqi/articles/5017742.html

七、异常处理

在编程过程中为了增加友好性,在程序出现bug时一般不会将错误信息显示给用户,而是现实一个提示的页面,通俗来说就是不让用户看见大黄页!!!

  1. try:
  2. pass
  3. except Exception,ex:
  4. pass
  1. 常用的内建异常类
  1. Exception 所有异常类的基类
  2. AttributeError 特性引用或赋值失败时引发
  3. IOError 试图打开不存在文件(报或其他情况)时引发
  4. IndexError 在使用序列中不存在的索引时引发
  5. KeyError 在使用映射中不存在的键是引发
  6. NameError 在找不到名字(变量)时引发
  7. SyntaxError 在代码为错误形式时引发
  8. TypeError 在内建操作或者函数应用于错误类型的对象时引发
  9. ValueError 在内建操作或者函数应用于正确类型的对象,但是该对象使用不合适的值时引发
  10. ZeroDivisionError 在除法或者模除操作的第二个参数为0时引发
try..except

万能异常 在python的异常中,有一个万能异常:Exception,他可以捕获任意异常,即:

  1. try:
  2.   s = input('Enter something --> ')
  3. except EOFError:
  4.   print('\nWhy did you do an EOF on me?')
  5.   sys.exit() # exit the program
  6. except Exception: # 对于特殊处理或提醒的异常需要先定义,最后定义Exception来确保程序正常运行
  7.   print('\nSome error/exception occurred.')
  8.   # here, we are not exiting the program
手动触发异常
Raise IndexError 
 
如果捕捉到异常,但是有想重新引发它(也就是说要传递异常参数),那么可以调用不带参数的异常(还能在捕捉到异常的时候显示的提供具体异常)
 
多个异常语句
  1. s1 = 'hello'
  2. try:
  3. int(s1)
  4. except KeyError as e:
  5. print('键错误')
  6. except IndexError as e:
  7. print('索引错误')
  8. except Exception as e:
  9. print('错误')
try..finally
  1. try:
  2.   f = open('poem.txt')
  3.   while True: # our usual file-reading idiom
  4.     line = f.readline()
  5.     if len(line) == :
  6.       break
  7.     time.sleep()
  8.     print(line)
  9. finally:
  10.   f.close()
  11.   print('Cleaning up...closed the file')
  12.  
  13. class MyException(Exception):
  14.   pass
  15. try:
  16.   print("normal code here")
  17. except MyException:
  18.   print("MyException encoutered")
  19. else:
  20.   print "No exception”
自定义异常
  1. class MyException(Exception):
  2. pass
  3. try:
  4. #some code here
  5. raise MyException
  6. except MyException:
  7. print("MyException encoutered")

python学习笔记六 面向对象相关下(基础篇)的更多相关文章

  1. Python学习笔记整理总结【语言基础篇】

    一.变量赋值及命名规则① 声明一个变量及赋值 #!/usr/bin/env python # -*- coding:utf-8 -*- # _author_soloLi name1="sol ...

  2. python学习笔记五 模块上(基础篇)

    模块学习 模块,用一砣代码实现了某个功能的代码集合. 类似于函数式编程和面向过程编程,函数式编程则完成一个功能,其他代码用来调用即可,提供了代码的重用性和代码间的耦合.而对于一个复杂的功能来,可能需要 ...

  3. python学习笔记三 文件操作(基础篇)

    文件操作 打开文件 open(name[,mode[,buffering]])   open函数使用一个文件名作为强制参数,然后返回一个文件对象.[python 3.5 把file()删除掉]   w ...

  4. Python学习笔记六

    Python课堂笔记六 常用模块已经可以在单位实际项目中使用,可以实现运维自动化.无需手工备份文件,数据库,拷贝,压缩. 常用模块 time模块 time.time time.localtime ti ...

  5. Python学习笔记(一):基础知识

    一.什么是python? python是一种面向对象.解释型的计算机语言,它的特点是语法简洁.优雅.简单易学 二.编译型语言和解释型语言 编译型语言就是把程序编译成计算机语言然后执行,(一次编译到处运 ...

  6. python学习笔记——多进程间通信——Linux信号基础

    1 信号的基本描述 Signal信号(其全程为软中断信号)是Linux系统编程中非常重要的概念,信号是异步进程中通信的一种方式. 作用是通知进程发生了异步事件.进程之间可以调用系统来传递信号, 本身内 ...

  7. python学习笔记六 初识面向对象上(基础篇)

    python面向对象   面向对象编程(Object-Oriented Programming )介绍   对于编程语言的初学者来讲,OOP不是一个很容易理解的编程方式,虽然大家都知道OOP的三大特性 ...

  8. python学习笔记(10):面向对象

    一.类和实例 1.类(Class): 用来描述具有相同的属性和方法的对象的集合.它定义了该集合中每个对象所共有的属性和方法.对象是类的实例. 2.对象:通过类定义的数据结构实例.对象包括两个数据成员( ...

  9. python学习笔记(7): 面向对象

    class Foo: #类中的函数 def bar(self): #功能阐述 print('Bar') pass def hello(self,name): print('i am %s' %name ...

随机推荐

  1. Sql Server按树形结构排序查询表记录

    http://blog.csdn.net/dxnn520/article/details/8089149 ----------------------------------------------- ...

  2. 了解C++默认编写并调用哪些函数

    概念:编译器可以暗自为class创建default构造函数.copy构造函数.copy assignmengt构造函数,以及析构函数. 比如你写下:struct Node { }; 这就好像你写下这样 ...

  3. 使用putty组件向服务器上传或下载文件

    基于SSH的连接 上传文件: pscp -P 28661(portNum) -pw password sourceFilePath user@serverIP:destinationFilePath ...

  4. MATLAB中提供的线型属性

    MATLAB中提供的线型属性有: 线型 说明 标记符 说明 颜色 说明 - 实线(默认) + 加号符 r 红色 -- 双划线 o 空心圆 g 绿色 : 虚线 * 星号 b 蓝色 :. 点划线 . 实心 ...

  5. Careercup | Chapter 8

    8.2 Imagine you have a call center with three levels of employees: respondent, manager, and director ...

  6. Empire C:Basic 1

    一.首先,从一个C程序开始: ///Name:Hello World ///Author:JA ///Date:2015-2-4 #include <stdio.h> //包含标准库的信息 ...

  7. Codeigniter 3.0 相关文档 part one

    分页配置项 http://stackoverflow.com/questions/18418900/codeigniter-pagination-config-without-repeating-wi ...

  8. iOS 3D touch 使用技巧

    第一个 在桌面中3d Touch 打开菜单 由于本人纯属代码党,本次实现方法也只使用代码实现 到达到这个效果并不难,只需要在appdelegate中实现以下代码即可 ,当然也有缺点,就是这个app没运 ...

  9. LightOj 1236 - Pairs Forming LCM (分解素因子,LCM )

    题目链接:http://lightoj.com/volume_showproblem.php?problem=1236 题意:给你一个数n,求有多少对(i,  j)满足 LCM(i, j) = n, ...

  10. 部署移动BI必须要考虑的五大因素

    随着大屏智能手机和平板电脑的普及,商业智能分析应用程序也需要移动化.由于用户并不会长时间在办公桌前工作.在新的设备以及新的用户的共同促进下,移动BI即将成为主流. 但是,所有人都应该清楚这样一个事实: ...