一、前情提要:
实例或对象:只有数据属性
类:有数据属性和函数属性
实例对象:可以调用类的数据属性和函数属性
二、静态属性
@property (静态属性)----------将函数属性伪装成数据属性访问
类:不能调用(调用只能拿到一个内存地址,并不会执行)
实例:可以调用
class Player:
def __init__(self, name, age, height, position):
self.name = name
self.age = age
self.height = height
self.position = position
@property
def Jumpshot(self):
print('%s来了一记后仰跳投' % self.name)
def dumk(self):
print('%s高高跃起,献上一记战斧劈扣' % self.name)
p1 = Player('lebron', 34, '2.03m', 'sf')
p1.Jumpshot #lebron来了一记后仰跳投
p1.dumk() #lebron高高跃起,献上一记战斧劈扣
print(Player.Jumpshot) #<property object at 0x000002AB2295C9F8>
print(Player.dumk(p1)) #lebron高高跃起,献上一记战斧劈扣
作用:当对象有重复的方法需求时,可将这个方法封装到类中。
名词解释:封装,即隐藏对象的属性和实现细节,仅对外公开接口,控制在程序中属性的读和修改的访问级别;将抽象得到的数据和行为(或功能)相结合,形成一个有机的整体,也就是将数据与操作数据的源代码进行有机的结合,形成“类”,其中数据和函数都是类的成员。
在面向对象编程中,封装(encapsulation)是将对象运行所需的资源封装在程序对象中——基本上,是方法和数据。对象是“公布其接口”。其他附加到这些接口上的对象不需要关心对象实现的方法即可使用这个对象。这个概念就是“不要告诉我你是怎么做的,只要做就可以了。”对象可以看作是一个自我包含的原子。对象接口包括了公共的方法和初始化数据。
三、类方法
@classmethod(类方法)---------与类绑定,与实例无任何关系
类:可以调用
对象:不可以调用(其实可以调用d1.test_classmethod(),不会出错, 但是一般不会这样定义和调用)
class Player:
home = 'NBA'
def __init__(self, name, age, height, position):
self.name = name
self.age = age
self.height = height
self.position = position
def Jumpshot(self):
print('%s来了一记后仰跳投' % self.name)
@classmethod
def info(cls,name):
print('%s是一名%s球员' % (name,cls.home))
Player.info('lebron james') #用类来调用类方法,这样就与实例隔离了 lebron james是一名NBA球员
作用:之前如果要调用类的数据属性,先要实例化对象,再通过这个对象来调用类的数据属性。而通过类方法,可不用实例化,直接调用类的数据属性。
四、静态方法
@staticmethod(静态方法-类的工具包)----------不与类绑定,也不与对象绑定,名义上归属类管理,但是不能调用类属性和实例属性。
类:可以调用
对象:可以调用
class Player:
home = 'NBA'
def __init__(self, name, age, height, position):
self.name = name
self.age = age
self.height = height
self.position = position
def Jumpshot(self):
print('%s来了一记后仰跳投' % self.name)
@staticmethod
def info(p1, p2):
print('%s和%s正在1v1斗牛' % (p1, p2))
pla = Player('lebron', 34, '2.03m', 'sf')
pla.info('lebron james', 'kevin durant') # 对象可以调用 lebron james和kevin durant正在1v1斗牛
Player.info('lebron james', 'kevin durant') #类也可以调用 lebron james和kevin durant正在1v1斗牛
类的工具包,staticmethod静态方法只是名义上的归属类管理,不能调用类数据属性和实例的数据属性
五、组合
组合的用途:
1.做关联
2.部分组成整体
class School:
def __init__(self, name, addr):
self.name = name
self.addr = addr
def choice(self):
print('%s 选课系统开启啦' % self.name)
class Course:
def __init__(self, name, period, school):
self.name = name
self.period = period
self.school = school
s1 = School('中南大学软件学院','铁道')
s2 = School('中南大学商学院', '本部')
c1 = Course('c语言', '3-18周', s1) #课程和学校就行绑定
print(c1.__dict__)
#需求查找c语言课程所在校区。
print(c1.school.addr) #这就是一种组合,将课程类和学校类关联起来
>>>
{'name': 'c语言', 'period': '3-18周', 'school': <__main__.School object at 0x000001F4CBD992B0>}
铁道
#选课系统;分校区和创建课程
class School:
def __init__(self, name, addr):
self.name = name
self.addr = addr
def choice(self):
print('%s 选课系统开启啦' % self.name)
class Course:
def __init__(self, name, period, school):
self.name = name
self.period = period
self.school = school
#实例出学院
s1 = School('自动化学院', '本部校区')
s2 = School('软件学院', '铁道校区')
s3 = School('家具与艺术设计学院', '新校区')
msg = '''
1:自动化学院 本部
2:软件学院 铁道
3:家具与艺术设计学院 新校区
'''
while True:
print(msg)
meun = {
'1': s1,
'2': s2,
'3': s3
}
choice = input('选择学院>>:')
sch_obj = meun[choice] #实例化出来的学院,根据用户的输入,实例化出不同的学院
name = input('课程名>>:')
period = input('课程周期>>:')
new_course = Course(name, period, sch_obj)
print('课程【%s】属于%s' % (new_course.name, new_course.school.addr))
课程关联校区,老师关联课程,对于这种类与类之间没什么共同点,要做关联就可以通过组合来实现。