Python学习之==>面向对象编程

一、面向对象与面向过程

  面向对象与面向过程是两种不同的编程范式,范式指的是按照什么方式去编程、去实现一个功能。不同的编程范式本质上代表对各种不同类型的任务采取不同的解决问题的思路。

1、面向过程编程

  角色是执行者,把一个项目按照一定的顺序,从头到尾一步步执行下去。这种思想好理解,但只要前面一个步骤变了,后面的步骤也要跟着变,维护起来比较麻烦。

2、面向对象编程

  角色是指挥者,把一个项目分成一个个小的部分,每个部分负责一方面的功能,整个项目由这些部分组合而成一个整体。类似一个机关,分为各个职能部门,只要符合一定的前提就行。面向对象的思想适合多人分工合作。

  面向对象是包含面向过程思路的,比如定义类中的方法,每个小方法、小功能还是面向过程的的思想。

  面向对象与面向过程的主要区别就是:面向对象可以使程序更加容易更改和扩展。

二、面向对象的特性

1、类

  Class,相当于一个种类、一个模型。一个类就是对一类拥有相同属性的对象的抽象、蓝图、原形。在类中定义了这些对象都具备的属性、共同的方法。

2、对象(实例)

  Object,根据模型造出来的具体的东西。一个对象就是一个类实例化后实例。一个类必须经过实例化后才能在程序中调用,一个类可以实例化多个对象,每个对象也可以有不同的属性。(对象就是实例,两者是一个意思)

3、实例化

  初始化一个类,创造一个对象。把一个类变成一个具体的对象的过程,叫做实例化。

4、属性

  属性就是类里面的一个变量,有类属性(类变量)和实例属性(实例变量)两种。类属性是在定义的时候就有的,实例属性是在实例化的时候才产生的变量。举个例子来说明类属性于实例属性:

  类属性(类变量):公共的变量,每个实例都可以用。直接通过“类名.XXX”来进行调用和修改,不需要实例化

  实例属性(实例变量):必须先进行实例化,然后通过“实例名.XXX”来进行调用和修改。

  下面简单定义一个类来说明以上概念,类的定义使用class关键字,类名的首字母大写。

 1 class Person():  # 经典类,新式类为:class Person(object):
 2     hand = 2     # 类属性
 3     def __init__(self,name):  # 构造函数,类在实例化的时候自动执行的函数
 4         # self代表的是实例化之后的对象
 5         self.name = name  # 实例属性
 6         self.nose = 1     # 实例属性
 7         print(‘开始创造机器人。。。‘)
 8     def driver(self):  # 实例方法
 9         print(‘%s开车中。。‘%self.name)
10         self.eat()     # 调用类里面的方法
11     def fly(self):     # 实例方法
12         print(‘%s,飞吧。。‘%self.name)  # 获取类里面的变量
13     def eat(self):     # 实例方法
14         print(‘%s吃吧,管饱‘%self.name)
15
16 # 类在用的时候,首先需要实例化
17 zlj = Person(‘张流量‘)  # 实例化:类名+括号
18 print(zlj.name)         # 调用实例属性
19 print(zlj.nose)         # 调用实例属性
20 print(zlj.hand)         # 调用类属性
21 zlj.hand = 5            # 不会改变类变量,只影响实例里面的变量
22 print(zlj.hand)         # 5
23 zlj.sex = ‘男‘          # 为实例增加实例属性
24 print(zlj.sex)
25 zlj.driver()            # 调用类方法
26 zlj.fly()               # 调用类方法
27 dcg = Person(‘董春光‘)  # 实例化dcg
28 print(dcg.hand)         # 2
29 Person.hand = 10        # 修改类变量
30 print(dcg.hand)         # 10
31 print(zlj.hand)         # 5,修改类变量发生在修改实例变量之后,所以实例变量的值不再发生改变

 5、方法

    方法就是类的功能,是定义在类里面的函数

  (1)类方法(cls):@classmethod

      a、不用实例化就可以直接调用

      b、它可以通过cls使用类变量

      c、它不能调用实例变量和实例方法

      d、不想实例化的时候,可以把方法定义成类方法

  (2)实例方法:self

      实例化后才能使用的方法

  (3)属性方法(self):@property

      看起来很像属性的一个方法,将没有入参的函数变为一个变为一个属性方法(类似于变量),结果是函数的返回值

  (4)静态方法():@staticmethod

      静态方法就是一个普通的函数,只不过写在类里面而已。它用不了类属性(变量)、类方法、实例属性(变量)、实例方法

 1 class Baby(object):
 2     nationality = ‘China‘   # 类变量,公共变量,每个实例都可以用
 3     def __init__(self):     # 构造函数,类在实例化的时候自动执行的函数
 4         self.name = ‘牛牛‘  # 实例变量,必须实例化才能调用
 5     def my(self):           # 实例方法,必须实例化才能调用
 6         self.sex = ‘男‘  # 实例变量,必须实例化才能调用
 7     def cry(self):          # 实例方法,必须实例化才能调用
 8         print(‘呜呜呜‘)
 9     @property               # 属性方法,直接返回函数执行结果
10     def AAA(self):
11         return 98
12     @classmethod            # 类方法,不用实例化就可以直接调用
13     def xm(cls):            # cls代表的就是Baby类
14         print(cls.nationality)
15         # cls.name          # 报错,不能调用类中其他的实例变量
16         # cls.my()          # 报错,不能调用勒种其他的实例方法
17         print(‘我是类方法‘)
18     @staticmethod           # 静态方法
19     def xh():
20         print(‘这个是静态方法,它和没写在类里面的函数一样‘)
21
22 # 类方法:不想实例化的时候可以定义成类方法
23 # 1、不用实例化就可以直接调用
24 # 2、它可以通过cls使用类变量
25 # 3、它不能调用这个类里面的其他实例方法和实例变量
26 Baby.xm()  # 不用实例化直接用类名调用类方法
27
28 # 实例方法
29 Zll = Baby()
30 Zll.my()
31 print(Zll.name)
32 Zll.xm()   # 实例化后通过对象调用类方法
33
34 # 属性方法
35 Dcg = Baby()
36 print(Dcg.AAA)  # 调用属性方法不用加括号
37
38 # 静态方法:
39 # 1、就是一个普通函数,只不过是写在类里面而已
40 # 2、它用不了类变量、类方法、实例变量、实例方法
41 Hr = Baby()
42 Hr.xh()

6、继承

  一个类可以派生出子类,在父类里面定义的属性和方法自动被子类继承,继承是为了代码重用。并且,子类可以重写父类的方法。Python3中经典类和新式类的多继承都是广度优先。但在Python2中,经典类和新式类的多继承是有区别的:经典类的多继承是深度优先,新式类的多继承是广度优先。

 1 class Father(object):  # 父类
 2     def __init__(self):
 3         self.money = 1000000
 4         self.house = ‘5环20套‘
 5     def sing(self):
 6         print(‘唱歌‘)
 7     def dance(self):
 8         print(‘跳广场舞‘)
 9     def mf(self):
10         print(‘找朋友‘)
11 class Son(Father):    # 继承类:将父类名写在括号里
12     def dance(self):
13         self.house = ‘2环1套‘
14         print(‘跳霹雳舞‘)
15
16 # 通过继承类调用父类中的方法和变量
17 m = Son()       # 实例化
18 print(m.money)  # 调用父类中的实例变量
19 m.sing()        # 调用父类中的实例方法
20 m.dance()       # 子类和父类中都存在的方法则用子类中的方法
21 print(m.house)  # 子类和父类中都存在的变量则用子类中的变量

重写父类的方法:

  (1)父类方法没用,需要重写

  (2)父类方法不够完善,想给这个方法在原有的基础上添加一些功能

 1 class Zll():
 2     pass
 3
 4 class Dcg():
 5     def smile(self):
 6         print(‘喔喔喔‘)
 7
 8 class Lw():
 9     def smile(self):
10         print(‘啊啊啊‘)
11
12 class Xz(Zll,Dcg,Lw):           # 子类可以继承多个父类
13     def smile(self):            # 重写父类的方法
14         Lw().smile()            # 调用父类,指定哪个父类
15         super(Xz,self).smile()  # 自动找到父类,先找到哪个类用哪个类
16         print(‘呵呵呵‘)
17
18 A = Xz()
19 A.smile()

经典类与新式类的区别:

  在Python3中经典类和新式类没有区别,在Python2中区别如下:

  (1)多继承的时候:

      经典类:深度优先

      新式类:广度优先

      Python3里面都是广度优先

  (2)Python2里面经典类不能用super,新式类可以用

 1 # class A():      # 经典类
 2 class A(object):  # 新式类
 3     def x(self):
 4         print(‘A‘)
 5 class B(A):
 6     pass
 7 class C(A):
 8     def x(self):
 9         print(‘C‘)
10 class D(B,C):
11     pass
12
13 S = D()
14 S.x()
15 # 运行结果:
16     # Python2经典类:A(先从B里面找,B里面没有再去A里面找,A里面没有再去C里面找,B→A→C)
17     # Python2新式类:C(先从B里面找,B里面没有再去C里面找,C里面没有再去A里面找,B→C→A)
18     # Python3:C(和Python2中新式类一样)

7、封装

  把一些功能的实现细节隐藏,但类中对数据的赋值、内部调用对外部用户却是透明的,使类变成一个胶囊或容器,里面包含着类的数据和方法(比如说创造一个人,把身体内部的心肝脾肺肾都封装起来了,其他人只能直接找这个人而看不到里面有上面东西)。

8、多态

  对不同类的对象发出相同的消息将会有不同的行为。比如,你的老板让所有员工在九点钟开始工作, 他只要在九点钟的时候说:“开始工作”即可,而不需要对销售人员说:“开始销售工作”,对技术人员说:“开始技术工作”, 因为“员工”是一个抽象的事物, 只要是员工就可以开始工作,他知道这一点就行了。至于每个员工,当然会各司其职,做各自的工作。

  多态就是抽象化的一种体现,把一系列具体事物的共同点抽象出来, 再通过这个抽象的事物, 与不同的具体事物进行对话。一种接口,多种实现。

 1 class Animal(object):  # 父类
 2     def __init__(self, name):
 3         self.name = name
 4 class Dog(Animal):     # 狗类,有叫的方法
 5     def cry(self):
 6         print(‘狗 [%s] 汪汪汪‘ % self.name)
 7 class Cat(Animal):     # 猫类,有叫的方法
 8     def cry(self):
 9         print(‘猫 [%s] 喵喵喵‘ % self.name)
10 def cry(obj):          # 定义一个函数,去调用传进来的实例的cry方法
11     obj.cry()
12
13 d1 = Dog(‘大黄‘)  # 实例化狗
14 d2 = Dog(‘小黄‘)  # 实例化狗
15 c1 = Cat(‘小白‘)  # 实例化猫
16 c2 = Cat(‘小黑‘)  # 实例化猫
17 cry(d1)           # 把对象d1传进来
18 cry(d2)           # 把对象d2传进来
19 objs = [d1, d2, c1, c2]  # 把上面实例化的对象都放到一个list里面
20 for obj in objs:         # 循环统一调用
21     cry(obj)

三、本类对象

  类中的self代表的是本类对象,也就是实例化后的对象。因为函数里面的变量都是局部变量,出了函数就不能使用,用self绑定之后,在类中任何地方都能随便使用(self.XXX)。

 1 class Baby:
 2     def __init__(self,name):
 3         #name = name      # 局部变量,出了函数就失效
 4         self.name = name  # 在类中self.name可以随便用了
 5         print(‘self的内存地址‘, id(self))
 6     def cry(self):
 7         print(‘%s在哭‘%self.name)  # self.name在类中其他方法可以使用
 8 Zll = Baby(‘张流量‘)         # 实例化时将Amy的地址给self
 9 print(‘实例的内存地址‘,id(Zll))    # 与实例化时self的内存地址一致
10 Zll.cry()
11 # 通过运行发现self的内存地址和实例的内存地址是一样的,说明self代表的就是实例化后的对象Zll

四、构造函数与析构函数

1、构造函数

  类在实例化时自动执行的函数,但类中不是必须包含构造函数的。

  实例化时只有构造函数会自动执行,其他函数不会被执行。

1 class Baby(object):
2     def __init__(self):     # 构造函数,类在实例化的时候自动执行的函数
3         self.name = ‘牛牛‘  # 实例变量,必须实例化才能调用
4     def my(self):           # 实例方法,必须实例化才能调用
5         self.sex = ‘男‘     # 实例变量,必须实例化才能调用
6
7 Zll = Baby()
8 print(Zll.name)  # 实例化时构造函数自动执行
9 print(Zll.sex)   # my方法未被执行,所以会报错--‘Baby‘ object has no attribute ‘sex‘

解决Zll.sex报错有两种方式:

(1)在构造函数中调用一次my函数,如下:

 1 class Baby(object):
 2     def __init__(self):     # 构造函数,类在实例化的时候自动执行的函数
 3         self.name = ‘牛牛‘  # 实例变量,必须实例化才能调用
 4         self.my()           # 在构造函数中调用一次my方法,实例化时会自动执行
 5     def my(self):           # 实例方法,必须实例化才能调用
 6         self.sex = ‘男‘     # 实例变量,必须实例化才能调用
 7
 8 Zll = Baby()
 9 print(Zll.name)  # 实例化时构造函数自动执行
10 print(Zll.sex)   # 实例化时自动调用了一次my函数

(2)实例化后,先调用一次my函数,再使用my函数下的实例变量,如下:

 1 class Baby(object):
 2     def __init__(self):     # 构造函数,类在实例化的时候自动执行的函数
 3         self.name = ‘牛牛‘  # 实例变量,必须实例化才能调用
 4     def my(self):           # 实例方法,必须实例化才能调用
 5         self.sex = ‘男‘     # 实例变量,必须实例化才能调用
 6
 7 Zll = Baby()
 8 print(Zll.name)  # 实例化时构造函数自动执行
 9 Zll.my()         # 调用一次my方法
10 print(Zll.sex)   

2、析构函数

  实例被销毁的时候执行,但不是必须的。

  一般可用于测试用例执行完毕后的关闭连接、关闭数据库、删除测试数据等操作。

例子:操作Mysql数据库

 1 import pymysql
 2 class MyDb(object):
 3     def __init__(self,host,user,db,passwd,
 4                  port=3306,charset=‘utf8‘):  # 构造函数
 5         try:
 6             self.conn = pymysql.connect(
 7                 host=host,user=user,passwd=passwd,port=port,db=db,charset=charset,
 8                 autocommit=True  # 自动提交
 9             )
10         except Exception as e:
11             print(‘数据库连接失败!:%s‘%e)
12         else:
13             self.cur = self.conn.cursor(cursor=pymysql.cursors.DictCursor)
14
15     def __del__(self):  # 析构函数,实例被销毁的时候执行
16         self.cur.close()
17         self.conn.close()
18         print(‘数据库连接关闭‘)
19
20     def ex_sql(self,sql):
21         try:
22             self.cur.execute(sql)
23         except Exception as e:
24             print(‘sql语句有问题:%s‘%sql)
25         else:
26             self.res = self.cur.fetchall()
27             return self.res
28
29 my = MyDb(‘118.24.3.40‘,‘jxz‘,‘jxz‘,‘123456‘)
30 my.ex_sql(‘select * from stu;‘)
31 print(my.res)  # 可以用实例属性取值
32 print(my.ex_sql(‘select * from stu;‘))  # 也可以用实例方法的返回值
33 print(‘我是最后一行代码‘)   # 执行完最后这行代码后再执行析构函数

五、私有变量&私有方法

  出了类以后就不能再使用的变量和方法,被称为私有变量、私有方法。

   有些重要的信息不想被调用,可以加两个下划线"__",将变量或者方法变为私有。

 1 class Redis(object):
 2     def __init__(self):
 3         self.__host = ‘127.0.0.1‘  # 私有变量
 4         self.port = 6379
 5     def __close(self):             # 私有方法
 6         print(‘私有方法‘)
 7     def open(self):
 8         print(‘实例方法‘)
 9         self.__close()             # 类内部可以调用私有方法
10
11 m = Redis()
12 print(m.__host) # 报错,没有__host这个属性,私有变量出类后不能再使用
13 print(m.port)   # 打印出:6379
14 m.open()        # 打印出:实例方法,私有方法
15 m.__close()     # 报错,没有这个方法,,私有方法出类后不能再使用

例子:操作Redis数据库

 1 # 封装redis操作类
 2 import redis
 3 class My(object):
 4     def __init__(self):
 5         self.__host = ‘127.0.0.1‘  # 私有变量
 6         self.__port = 6379         # 私有变量
 7         self.__passwd = ‘‘         # 私有变量
 8         self.__db = 1              # 私有变量
 9         try:
10             self.r = redis.Redis(host=self.__host,port=self.__port,password=self.__passwd,db=self.__db)
11         except Exception as res:
12             print(‘redis连接失败..【%s】‘%res)
13             # 这时并不会去连redis
14             # 所以捕捉不到数据库连接失败的异常,这里写的捕捉异常没有意义,可以不写
15     def __close(self):             # 私有方法
16         print(‘close‘)
17
18     def str_get(self,name):                  # str类型get
19         res = self.r.get(name)
20         if res:
21             return res.decode()
22         return None
23
24     def str_set(self,name,value,time=None):  # str类型set
25         self.r.set(name,value,time)
26
27     def str_delete(self,name):               # str类型的删除key
28         # res = self.r.get(name)
29         res = self.r.exists(name)  # 判断redis数据库是否存在name这个key
30         if res:
31             self.r.delete(name)
32             print(‘删除成功‘)
33         else:
34             print(‘%s不存在‘%name)
35
36     def hash_get(self,name,key):             # hash类型获取单个key
37         res = self.r.hget(name,key)
38         if res:
39             return res.decode()
40         return None
41
42     def hash_set(self,name,key,value):       # hash类型set
43         self.r.hset(name,key,value)
44
45     def hash_getall(self,name):              # hash类型获取key里面的所有数据
46         dic = {}
47         res = self.r.hgetall(name)
48         if res:
49             for key,value in res.items():
50                 dic[key.decode()] = value.decode()
51             return dic
52         return None
53
54     def hash_del(self,name,key):             # 删除某个hash里面小key
55         res = self.r.hget(name,key)
56         if res:
57             self.r.hdel(name,key)
58             print(‘删除成功‘)
59         else:
60             print(‘%s不存在‘%name)
61
62     def clean_redis(self):                   # 清理redis
63         # self.r.flushdb()  # 清空redis数据库
64         res = self.r.keys()
65         for key in res:
66             self.r.delete(key)
67         print(‘清空redis数据库成功‘)
68
69 m = My()
70 m.str_set(‘Kity‘,‘famale‘)
71 print(m.str_get(‘Kity‘))
72 m.str_delete(‘Kity‘)
73 m.hash_set(‘toy‘,‘car‘,‘red‘)
74 m.hash_set(‘toy‘,‘ball‘,‘blue‘)
75 print(m.hash_get(‘toy‘,‘car‘))
76 print(m.hash_get(‘toy‘,‘car‘))
77 m.hash_del(‘toy‘,‘car‘)
78 m.clean_redis()

原文地址:https://www.cnblogs.com/L-Test/p/9242824.html

时间: 2024-10-07 19:59:00

Python学习之==>面向对象编程的相关文章

Python学习笔记——面向对象编程

接下来学习面向对象编程,基础的就不记录了,只记录一些Python特有的或者高级的特性. http://www.liaoxuefeng.com/wiki/0014316089557264a6b348958f449949df42a6d3a2e542c000/0014318645694388f1f10473d7f416e9291616be8367ab5000 1. 类的定义 定义类使用class关键字,后面紧跟类名(首字母大写),接着是从哪个类继承下来的(所有类最终会继承object). 通过类名加参

从0开始的Python学习014面向对象编程

 简介 到目前为止,我们的编程都是根据数据的函数和语句块来设计的,面向过程的编程.还有一种我们将数据和功能结合起来使用对象的形式,使用它里面的数据和方法这种方法叫做面向对象的编程. 类和对象是面向对象编程的两个重要方面.对于类和对象的关系,举个例子就像学生和小明同学的关系一样.学生(类)是一个拥有共同属性的群体,小明同学(对象)是其中一个有自己特性的个体. 对于一个对象或类的变量被称为域,函数被称为类或对象的方法. 域有两种类型--属于每个对象或属于类本身,分别成为实例变量和类变量. 类使用cl

python学习日记-面向对象编程(一)

python的类(class)和实例(instance) 假设一种鞋子(shoe)有尺码(size)和颜色(color)两种属性,以此为例. 类可以起到模板的作用,因此,可以在创建实例的时候,把一些我们认为必须绑定的属性强制填写进去.通过定义一个特殊的__init__方法,在创建实例的时候,就把size,color属性绑到shoe上去,例如: 1 class Shoe(object): 2 3 def __int__(self, size, color): 4 self.size = size

python学习day11 面向对象编程 类和实例

class Student(object): #class后面紧接着是类名,即Student,类名通常是大写开头的单词,紧接着是(object),表示该类是从哪个类继承下来的.通常,如果没有合适的继承类,就使用object类,这是所有类最终都会继承的类. def __init__(self,name,score): #通过定义一个特殊的__init__方法,在创建实例的时候,就把类的name,score等属性绑上去,__init__方法的第一个参数永远是self,表示创建的实例本身,因此,在__

Day6 - Python基础6 面向对象编程

Python之路,Day6 - 面向对象学习 本节内容: 面向对象编程介绍 为什么要用面向对象进行开发? 面向对象的特性:封装.继承.多态 类.方法. 引子 你现在是一家游戏公司的开发人员,现在需要你开发一款叫做<人狗大战>的游戏,你就思考呀,人狗作战,那至少需要2个角色,一个是人, 一个是狗,且人和狗都有不同的技能,比如人拿棍打狗, 狗可以咬人,怎么描述这种不同的角色和他们的功能呢? 你搜罗了自己掌握的所有技能,写出了下面的代码来描述这两个角色 1 2 3 4 5 6 7 8 9 10 11

Python学习记录-socket编程

Python学习记录-socket编程 学习 python socket Python学习记录-socket编程 1. OSI七层模型详解 2. Python socket 3. socket()函数 4. TCP socket通信流程 5. Python Internet 模块 1. OSI七层模型详解 以上图见:http://blog.csdn.net/yaopeng_2005/article/details/7064869 其它详情可参考:socket网络基础 2. Python sock

Python:笔记(3)——面向对象编程

Python:笔记(3)--面向对象编程 类型与对象 术语 程序中存储的所有数据都是对象.每个对象都有一个身份.一个类别和一个值. 如:a=42,就是用值42创建了一个整数对象. 大多数对象都拥有大量特点的属性和方法. 属性就是与对象相关的值. 方法就是被调用时将在对象上执行某些操作的函数. 使用 . 运算符可以访问属性和方法. Python中对象的一些说明 检查对象类型最佳的方式是利用内置函数 isinstance(object,type) 所有对象都有引用计数,当一个对象的引用计数归零时,他

python学习之面向对象高级特性

类属性与实例属性类属性就是类对象所拥有的属性,它被所有类对象的实例对象所共有,在内存中只存在一个副本.在前面的例子中我们接触到的就是实例属性(对象属性),它不被所有类对象的实例对象所共有,在内存中的副本个数取决于对象个数. 05_类属性鱼实例属性.py import random class Turtle(object): # power是类属性. power = 100 def __init__(self): # x,y:实例属性. self.x = random.randint(0, 10)

Python基础6-1 面向对象编程

概述 面向过程:根据业务逻辑从上到下写垒代码 函数式:将某功能代码封装到函数中,日后便无需重复编写,仅调用函数即可 面向对象:对函数进行分类和封装,让开发"更快更好更强..." 面向过程编程最易被初学者接受,其往往用一长段代码来实现指定功能,开发过程中最常见的操作就是粘贴复制,即:将之前实现的代码块复制到现需功能处. while True:     if cpu利用率 > 90%:         #发送邮件提醒         连接邮箱服务器         发送邮件