six day--面向对象

Posted yuyou123

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了six day--面向对象相关的知识,希望对你有一定的参考价值。

一、复习模块

1.计算时间差例子
2.随机数 代码 sample 随机取多个返回值
3.re 要求掌握常用的:与注册相关的,邮箱、手机号、省份证号
技术分享图片
 1 # collections模块
 2 # 有序字典 orderddict
 3 # 默认字典 defaultdict
 4 # 可命名元祖 namedtuple
 5 
 6 # 时间模块
 7 # 三种时间格式  时间戳时间 结构化时间 格式化时间
 8 # 计算时间差
 9     # 两个时间都转换成时间戳
10     # 时间戳之间相减 以秒为单位的小数差
11     # 将小数差转换成结构化时间 元组 1970 1.3
12     # 用当前结构化的时间差 减去 1970 1 1 00:0
13 
14 # random模块
15     # 发红包 发200的红包,发5个 —— 代码
16         # (0200) 取4个点
17     # 验证码
18         # 从数字中选一个 0-9
19         # 从a-z选一个
20         # 到底是字母还是数字也是随机的
21 
22 # os模块 —— 操作系统打交道
23     # 文件相关
24     # 文件夹相关的
25     # 和执行系统命令相关
26     # 和路径相关的
27 
28 # sys模块 —— 和解释器相关的
29     # sys.path
30     # sys.argv 执行py脚本的时候传入的参数
31 
32 # 正则模块
33     # 正则表达式
34         # 能够判断 邮箱 手机号
35     # re模块
36 
37 
38 # 三个模块+序列化  未讲
View Code

二、面向对象

1.引入--人狗大战

1.传具体的四个值,bug:未改变dog字典的值,写法麻烦
优化-传person、dog函数 --存在bug:出现人要狗、狗打人事件
优化2--把bite、attack放入dog、person的内部;函数内部去掉一个参数,形成闭包
注意:为何要引入Person函数--创建模板,要求必须具有这个属性,为何要放入内部---确定谁能调用
技术分享图片
 1 # 函数 基础数据类型 循环 文件处理 模块
 2 # 游戏公司
 3 # 人狗大战
 4 # 两个角色
 5 # 人
 6     # 昵称
 7     # 性别
 8     # 生命值
 9     # 战斗力
10     # 背包
11 # 狗
12     # 昵称
13     # 品种
14     # 生命值
15     # 战斗力
16 def Person(name,sex,hp,dps):   # 人模子
17     dic = {name:name,sex:sex,hp:hp,dps:dps,bag:[]}
18     def attack(dog):
19         dog[hp] -= dic[dps]
20         print(%s打了%s,%s掉了%s点血,剩余%s点血 % (dic[name], dog[name], dog[name], dic[dps], dog[hp]))
21     dic[attack] = attack   #注意位置
22     return dic
23 def Dog(name,kind,hp,dps):   # 狗模子
24     dic = {name:name,kind:kind,hp:hp,dps:dps}
25     def bite(person):
26         person[hp] -= dic[dps]
27         print(%s咬了%s,%s掉了%s点血,剩余%s点血 % (dic[name], person[name], person[name], dic[dps], person[hp]))
28     dic[bite] = bite
29     return dic
30 alex = Person(alex,不详,250,5)
31 ha2 = Dog(哈士奇,藏獒,15000,200)
32 # 人打狗
33 print(alex)
34 print(ha2)
35 print(alex[attack])      #<function Person.<locals>.attack at 0x00000000021C99D8> 调用函数返回内存地址。。。
36 alex[attack](ha2)  #执行函数
37 print(ha2)
38 
39 
40 # 面向对象的编程思想
41 # 人狗大战
42 # 创建一个人
43 # 创建一个狗
44 # 人打狗 —— 函数
45 # 狗咬人 —— 函数
46 
47 # 造模子 —— 面向对象
48 # 规范了一类角色的属性项目、属性的名字、技能、技能的名字
49 # 权限 有一些函数 只能是这个角色才能拥有 才能调用
面向对象初识

2.初识类的语法

类:具有相同属性和相同动作的一类事物  组成一个类          是抽象的
对象: 具体的某一个具有实际属性 和具体动作的一个实体 是具体的
类被创造出来 就是模子 是用来描述对象的
写法:
class 类名:
    静态属性=None
    def 动态属性(self):    #在类中的方法的一个默认的参数,但也只是一个形式参数,约定必须叫self
        pass

注:只要是写在类名中的名字 不管是变量还是函数名 都不能在类的外部直接调用
只能通过类名来使用它
类名的第一个功能---查看静态属性
类名.静态属性 可以增删改查
技术分享图片
1 # print(类名.静态属性)   # 查看
2 # 类名.静态属性 = 456    # 修改
3 # print(类名.静态属性)
4 # 类名.静态属性2 = abc# 增加
5 # print(类名.静态属性2)
6 # # del 类名.静态属性2 #删除
7 # # print(类名.静态属性2)
静态属性增删改查

类名.__dict__ 传值!!! 类中必要的默认值之外 还记录了程序员在类中定义的所有名字

类名可以查看某个方法,但是一般情况下,我们不直接使用类名来调用方法
类名.动态属性 ---只能查看,不能修改

类名的第二个功能---实例化(创造对象) 对象=类名()
一般 函数第一个字母小写,类名的第一个字母大写
class Person:pass
技术分享图片
 1 # alex = Person()
 2 # 对象 = 类名()
 3 # print(alex)  # object
 4 # print(Person)
 5 # alex name hp dps bag sex
 6 # print(alex.__dict__)
 7 # # alex.__dict__[name] = alex
 8 # # alex.__dict__[sex] = 不详
 9 # # alex.__dict__[hp] = 250
10 # # alex.__dict__[dps] = 5
11 # # alex.__dict__[bag] = []
12 # # print(alex.__dict__)
13 # alex.name = alex   # 给alex对象添加属性
14 # alex.hp = 250
15 # alex.dps = 5
16 # alex.sex = 不详
17 # alex.bag = []
18 # print(alex.__dict__)
传值
技术分享图片
 1 # class Person:
 2 #     def __init__(self,name,hp,dps,sex):
 3 #         self.name = name
 4 #         self.hp = hp
 5 #         self.dps = dps
 6 #         self.sex = sex
 7 #         self.bag = []
 8 #
 9 # alex = Person(alex,250,5,N/A)
10 # print(alex : ,alex)
11 # print(alex.__dict__)
12 # print(alex.name)
init
# 为什么会执行init中的内容?
# self到底是什么?
# 实例化的过程
# 类名()就是实例化
# 在实例化的过程中 发生了很多事情是外部看不到的
# 1.创建了一个对象
# 2.自动调用__init__方法
# 这个被创造的对象会被当做实际参数传到__init__方法中,并且传给第一个参数self
# 3.执行init方法中的内容
# 4.自动的把self作为返回值 返回给实例化的地方
def init之后,一般定义默认要传值的变量,可在外部调用啦
人狗例子kv的改成.的 
技术分享图片
 1 # class Person:
 2 #     def __init__(self,name,hp,dps,sex):
 3 #         self.name = name
 4 #         self.hp = hp
 5 #         self.dps = dps
 6 #         self.sex = sex
 7 #         self.bag = []
 8 #     def attack(self,dog):
 9 #         dog.hp -= self.dps
10 #         print(%s打了%s,%s掉了%s点血,剩余%s点血 % (self.name, dog.name, dog.name, self.dps, dog.hp))
11 #
12 # class Dog:
13 #     def __init__(self,name,kind,hp,dps):
14 #         self.name = name
15 #         self.hp = hp
16 #         self.dps = dps
17 #         self.kind = kind
18 #
19 #     def bite(self,person):
20 #         person.hp -= self.dps
21 #         print(%s打了%s,%s掉了%s点血,剩余%s点血 % (self.name, person.name, person.name, self.dps, person.hp))
22 #
23 # alex = Person(alex,250,5,N/A)
24 # ha2 = Dog(哈士奇,藏獒,15000,200)
25 # ha2.bite(alex)
26 
27 # 简化的方式
28 # alex.attack(ha2)   # Person.attack(alex)
29 # alex.attack(ha2)   # Person.attack(alex)
30 # print(alex.attack(ha2))   # Person.attack(alex)
31 # print(ha2.hp)
32 # print(alex : ,alex)
33 # print(alex.__dict__)
34 # print(alex.name)
人狗大战
小结# 对象名.方法名 相当于调用一个函数,默认把对象名作为第一个参数传入函数
# 剩余的其他参数根据我的需求可以随意传
技术分享图片
 1 # 已知半径 计算圆形的面积和周长 面向对象的思想完成
 2 # 类 圆
 3 # 属性 半径
 4 # 方法 计算面积 计算周长 计算直径
 5 # pi * r ** 2
 6 # 2*pi*r
 7 # from math import pi
 8 # class Circle:
 9 #     def __init__(self,r):
10 #         self.r = r
11 #     def area(self):
12 #         return pi * self.r ** 2
13 #     def perimeter(self):
14 #         return self.r *pi * 2
15 #     def r2(self):pass
16 # c1 = Circle(5)
17 
18 # print(面积是:,c1.area())
19 # print(周长是:,c1.perimeter())
已知半径 计算圆形的面积和周长
面向对象的好处:每一个角色都有属于自己的属性和方法;高可扩展性 可读性 规范性
缺点:结局不可控--玩家可控制

类和对象都有自己的命名空间,对象能访问类的命名空间,类不能访问对象的命名空间  
两个实例化例子,,小结
技术分享图片
 1 # class Person:
 2 #     COUNTRY = 中国人       # 静态属性
 3 #     def __init__(self,name):
 4 #         self.name = name
 5 #     def eat(self):
 6 #         print(%s在吃泔水%self.name)
 7 #
 8 # alex = Person(alex)
 9 # egon = Person(egon)
10 #
11 # print(alex.name)
12 # print(egon.name)
13 # print(alex.COUNTRY)
14 # alex.eat()   # Person.eat(alex)
15 # alex ---> Person
16 # 当一个类在创建一个实例的时候 就产生了一个这个实例和类之间的联系
17 # 可以通过实例 对象 找到实例化它的类
18 # 但是 类不能找到它的实例化
View Code
升级  修改静态属性  局部改变。。在访问变量的时候,都先使用自己命名空间中的,如果自己的空间中没有,再到类的空间中去找
在使用对象修改静态变量的过程中,相当于在自己的空间中创建了一个新的变量;
在类的静态变量的操作中,应该使用类名来直接进行操作,就不会出现乌龙问题
3种国籍的修改结果例子
技术分享图片
 1 class Person:
 2     COUNTRY = [中国人]       # 静态属性
 3     Country = 中国人         # 静态属性
 4     def __init__(self,name):
 5         self.name = name
 6     def eat(self):
 7         print(%s在吃泔水%self.name)
 8 alex = Person(alex)
 9 egon = Person(egon)
10 # print(alex.Country)
11 # alex.Country = 印度人
12 # print(alex.Country)
13 # print(egon.Country)
14 # print(Person.Country)
15 结果:# 中国人
16 # 印度人
17 # 中国人
18 # 中国人
19 
20 # alex.COUNTRY[0] = 印度人
21 # print(alex.COUNTRY)
22 # print(egon.COUNTRY)
23 # print(Person.COUNTRY)
24 # alex.COUNTRY = [印度人]
25 # print(egon.COUNTRY)
26 # print(Person.COUNTRY)
27 结果:
28 [印度人]
29 [印度人]
30 [印度人]
31 [印度人]
32 [印度人]
33 
34 # 在访问变量的时候,都先使用自己命名空间中的,如果自己的空间中没有,再到类的空间中去找
35 # 在使用对象修改静态变量的过程中,相当于在自己的空间中创建了一个新的变量
36 # 在类的静态变量的操作中  应该使用类名来直接进行操作 就不会出现乌龙问题
View Code

创建一个类 能够自动计算这个类有创建了多少个实例

技术分享图片
# class Foo:
#     count = 0
#     def __init__(self):
#         Foo.count += 1
#
# f1 = Foo()
# print(Foo.count)
# [Foo() for i in range(10)]
# print(Foo.count)

结果:
1
11
View Code

3.组合

组合:一个类的对象作为另外一个类对象的属性---   一般是点点的形式

基础数据类型 都是类
# alex : str的对象
# alex.name = alex
# alex.name.startswith(a)

例子:给alex装备一个武器
技术分享图片
 1 # class Person:
 2 #     def __init__(self,name,sex,hp,dps):
 3 #         self.name = name
 4 #         self.hp = hp
 5 #         self.dps = dps
 6 #         self.sex = sex
 7 #         self.bag = []
 8 #     def attack(self,dog):
 9 #         dog.hp -= self.dps
10 #         print(%s打了%s,%s掉了%s点血,剩余%s点血 % (self.name, dog.name, dog.name, self.dps, dog.hp))
11 #
12 # class Dog:
13 #     def __init__(self,name,kind,hp,dps):
14 #         self.name = name
15 #         self.hp = hp
16 #         self.dps = dps
17 #         self.kind = kind
18 #
19 #     def bite(self,person):
20 #         person.hp -= self.dps
21 #         print(%s打了%s,%s掉了%s点血,剩余%s点血 % (self.name, person.name, person.name, self.dps, person.hp))
22 #
23 # class Weapon:
24 #     def __init__(self,name,price,dps):
25 #         self.name = name
26 #         self.price = price
27 #         self.dps = dps
28 #     def kill(self,dog):
29 #         dog.hp -= self.dps
30 #
31 # alex = Person(alex,N/A,250,5)
32 # ha2 = Dog(哈士奇,藏獒,15000,200)
33 # # print(alex.name)
34 # roubaozi = Weapon(肉包子,600000,10000)
35 # alex.money = 1000000
36 # if alex.money >= roubaozi.price:
37 #     alex.weapon = roubaozi
38 #     alex.weapon.kill(ha2)
39 #     print(ha2.hp)
alex开挂买武器版-人狗大战

练习:已知圆形类,运用组合,求圆环的面积和周长
技术分享图片
 1 # 圆形类 --> 圆环类
 2 # 已知圆形类 的基础上 运用组合 求圆环的面积和周长
 3 # 一个类的对象给另一个类对象当属性
 4 
 5 # 圆环
 6 # 圆
 7 # 圆环的面积
 8 
 9 from math import pi
10 class Circle:
11     def __init__(self,r):
12         self.r = r
13     def area(self):
14         return pi * self.r ** 2
15     def perimeter(self):
16         return self.r *pi * 2
17 
18 class Ring:
19     def __init__(self,outside_r,inside_r):
20         self.out_circle = Circle(outside_r)
21         self.in_circle = Circle(inside_r)
22     def area(self):
23         return self.out_circle.area() - self.in_circle.area()
24     def perimeter(self):
25         return self.out_circle.perimeter() + self.in_circle.perimeter()
26 
27 r = Ring(10,5)
28 print(r.area())
29 print(r.perimeter())
圆环类
组合 是描述了一种什么有什么的关系,eg:圆环有圆、人有武器
?。。。
小结。。
交互:人打狗、狗咬人
实例找类。。。看博客例子

4.继承
面向对象的三大特性  继承 多态 封装
继承
为何会有继承? ---解决代码的冗余问题
父类 基类 超类---Parent类
子类 派生类---Son类
单继承
技术分享图片
 1 class Parent:
 2     pass
 3 
 4 class Son(Parent):  #Son类继承Parent类
 5     pass
 6 
 7 
 8 class Parent1:
 9     pass
10 class Parent2:
11     pass
12 class Son(Parent1,Parent2):  #Son类继承Parent类
13     pass
继承

多继承:多个父类
构建时:先想到对象,子类,最后父类
人狗例子!!--图!
技术分享图片
 1 # class Animal:
 2 #     def __init__(self, name, hp, dps):
 3 #         self.name = name
 4 #         self.hp = hp
 5 #         self.dps = dps
 6 #     def eat(self):
 7 #         print(%s吃药回血了%self.name)
 8 # class Person(Animal):
 9 #     def __init__(self, name, hp, dps,sex):
10 #         super().__init__(name,hp,dps)    # Animal.__init__(self,name,hp,dps)
11 #         self.sex = sex           # 派生属性
12 #     def attack(self,dog):
13 #         dog.hp -= self.dps
14 #         print(%s打了%s,%s掉了%s点血,剩余%s点血 % (self.name, dog.name, dog.name, self.dps, dog.hp))
15 #
16 # class Dog(Animal):
17 #     def __init__(self,name,hp,dps,kind):
18 #         super().__init__(name, hp, dps)   # Animal.__init__(self, name, hp, dps)
19 #         self.kind = kind         # 派生属性
20 #     def bite(self,person):
21 #         person.hp -= self.dps
22 #         print(%s打了%s,%s掉了%s点血,剩余%s点血 % (self.name, person.name, person.name, self.dps, person.hp))
23 # alex = Person(alex,250,5,N/A)
24 # ha2 = Dog(哈士奇,15000,200,藏獒)
25 # print(alex.__dict__)
26 # print(ha2.__dict__)
27 # ha2.eat()
28 # alex.eat()
29 # ha2.bite(alex)
30 # alex.attack(ha2)
31 # 对象的内存空间 - 创建这个对象的类的内存空间 - 父类的
人狗-继承版

实例化发生的时候,1.创建了一个对象2.把子类创建的对象传给...5...
继承的特征:先找对象的内存空间--创建这个类的对象的内存空间--父类的内存空间
注意:加sex时,需要对sex赋值--派生属性
强制调用--图!
简单写法super().__init__(name,hp,dps) #不写self
子类中不同位置赋值,结果不一样,取最后赋值的值
面试题:in son例子
技术分享图片
 1 # class Foo:
 2 #     def __init__(self):
 3 #         self.func()
 4 #     def func(self):
 5 #         print(in Foo)
 6 #
 7 # class Son(Foo):
 8 #     def func(self):
 9 #         print(in Son)
10 # Son()
inson

抽象类与接口类--可先忽略--java实用

钻石继承 继承顺序,小乌龟继承顺序--广度优先算法 -->
print(D.mro()) #查看顺序
python两种类:
经典类 python3已经灭绝了,py2还存在,在py2中只要程序员不主动继承object,这个类就是经典类。遵循深度优先算法(一条路走到黑)
新式类 python3所有的类都是新式类,所有的新式类都继承object--在多继承中遵循广度优先算法
讨论题:都加super b+super,,找到c!!
技术分享图片
 1 # class A:
 2 #     def f(self):
 3 #         print(in A)
 4 #
 5 # class B(A):
 6 #     def f(self):
 7 #         print(in B)
 8 #         super().f()
 9 #
10 # class C(A):
11 #     pass
12 #     def f(self):
13 #         print(in C)
14 #         super().f()
15 #
16 # class D(B,C):
17 #     def f(self):
18 #         print(in D)
19 #         super().f()
20 #
21 # d = D()
22 # d.f()      
23 D-B-C-A
钻石继承
技术分享图片
 1 # class A:
 2 #     def f(self):
 3 #         print(in A)
 4 #
 5 # class B(A):
 6 #     pass
 7 #     # def f(self):
 8 #     #     print(in B)
 9 #
10 # class C(A):
11 #     pass
12 #     # def f(self):
13 #     #     print(in C)
14 #
15 #
16 # class D(B,C):
17 #     pass
18 #     # def f(self):
19 #     #     print(in D)
20 #
21 # class E(C):
22 #     pass
23 #     # def f(self):
24 #     #     print(in B)
25 #
26 # class F(D,E):
27 #     pass
28 #     # def f(self):
29 #     #     print(in C)
30 #
31 # # d = D()
32 # # d.f()
33 #
34 # print(F.mro())
小乌龟继承

F-D-B-E-C-A


super和找父类是两件事
在单继承中 super就是找父类
在多级继承中 super的轨迹 是根据整个模型的起始点而展开的一个广度优先顺序 ,遵循mro规则的
小结。。

继承小结

继承的作用

减少代码的重用
提高代码可读性
规范编程模式

几个名词

抽象:抽象即抽取类似或者说比较像的部分。是一个从具题到抽象的过程。
继承:子类继承了父类的方法和属性
派生:子类在父类方法和属性的基础上产生了新的方法和属性

抽象类与接口类

技术分享图片
1.多继承问题
在继承抽象类的过程中,我们应该尽量避免多继承;
而在继承接口的时候,我们反而鼓励你来多继承接口


2.方法的实现
在抽象类中,我们可以对一些抽象方法做出基础实现;
而在接口类中,任何方法都只是一种规范,具体的功能需要子类实现
技术分享图片

钻石继承

新式类:广度优先
经典类:深度优先

 



5.多态 了解,不常用
在python中处处都是多态
java中是强数据类型的,传值时指定数据类型--在java中应用

在python中,数据类型:类 例子!

技术分享图片
 1 # 在python中处处都是多态
 2 
 3 # 多态
 4 # java
 5 # class Person():pass
 6 #
 7 # alex = Person()
 8 # print(type(alex))  # Person
 9 # print(type(123))
10 # print(type(123))
11 
12 # def func(Dog person):
13 #     pass
14 #
15 # func(ha2)
16 
17 # class Animal:
18 #     pass
19 #
20 # class Dog(Animal):pass
21 # class Person(Animal):pass
22 #
23 #
24 # def func(a):
25 #     pass
26 #
27 # func(alex)
28 # func(ha2)
多态

 

 



































































以上是关于six day--面向对象的主要内容,如果未能解决你的问题,请参考以下文章

VSCode自定义代码片段——JS中的面向对象编程

VSCode自定义代码片段9——JS中的面向对象编程

面向对象day1

day6-2面向对象

day6--面向对象初识

Python学习之路——Day7(面向对象)