封装的好处:
1.写起来更简洁
2.维护更方便
3.将细节隐藏
类=变量(实例变量+类变量)+操作他们的方法:局部变量
本质:把需要管理的数据封装到实例里,然后基于类中的方法定义规则,以此来实现业务数据的完整性和一致性
class Person: # 父类
Count = 0
def __init__(self, name):
self.name = name
print(id(self.name))
def get_name(self): # self:传递的参数是实例的内存地址
# 告诉这个方法,使用哪个实例的数据
"""获取名字"""
return self.name
def set_name(self, value):
self.name = value
class Teacher(Person): # 子类
'''此类主要用于管理老师的数据'''
def __init__(self, name, salary):
Person.__init__(self, name) # 把父类中的实例变量存在了当前实例的地址中
# self.name = name
print(id(self.name))
self.salary = salary
Teacher.Count += 1
self.Count = 100
# 子类中需要初始化父类,提供完整的构造函数的初始化,满足父类的所有
# 参数使用要求
t = Teacher("吴老师", 1000) # 触发了__init__的执行了--》实例化
s = Teacher("李老师", 2000)
print(Teacher.Count)
print(t.Count)
print(s.__doc__)
print(s.get_name.__doc__)
#__new__:真正生产内存地址的方法
#类的帮助信息可以通过ClassName.__doc__查看
import random
class Solider:
def __init__(self,name):
self.name = name
self.blood = 100
self.exp = 0
self.alive_flag = "alive"
def fight(self,enemy):
print("%s 遇到了一个敌人%s,开打" %(self.name,enemy.name))
if self.exp > enemy.exp:
self.sub_blood(5)
enemy.sub_blood(10)
self.add_exp(5)
enemy.add_exp(10)
elif self.exp == enemy.exp:
self.sub_blood(5)
enemy.sub_blood(5)
self.add_exp(5)
enemy.add_exp(5)
else:
self.sub_blood(10)
enemy.sub_blood(5)
self.add_exp(10)
enemy.add_exp(5)
print("%s 遇到了一个敌人%s,打完了" %(self.name,enemy.name))
def sub_blood(self,value):
if isinstance(value,(int,float)):
self.blood-=value
print("%s掉了%s血" %(self.name,value))
if self.blood<=0:
self.alive_flag = "dead"
self.blood=0
print("%s被打死了" %self.name)
def add_exp(self,value):
if isinstance(value,(int,float)):
self.exp+=value
print("%s涨了%s经验" %(self.name,value))
s1 = Solider("张三")
s2 = Solider("李四")
s3=Solider("王五")
s4=Solider("赵璐")
scerio=[]
scerio.append(s1)
scerio.append(s2)
scerio.append(s3)
scerio.append(s4)
time=0
while time<30:
time+=1
t1=random.choice(scerio)
t2=random.choice(scerio)
if t1!=t2:
t1.fight(t2)
else:
continue
for i in scerio:
print("%s还有%s血,%s经验,%s" %(i.name,i.blood,i.exp,i.alive_flag))
class P:
def __init__(self,name):
self.name=name
def print_info(self):
print("info method is invoked")
@classmethod
def print_sth(cls):#类态方法需要有@classmethod,还要有cls
#不能用实例变量
print("class method is invoked")
@staticmethod
def print_p():#静态方法需要有@staticmethod,可以有参数也可以没有
#不能用实例变量
print("static method is invokde")
a=P("小花")
a.print_info() #通过实例调用实例方法
a.print_sth() #通过实例名调用类方法
P.print_sth() #通过类名称调用类方法
a.print_p()#通过实例名调用静态方法
P.print_p()#通过类名称调用静态方法
类的属性
#encoding=utf-8
class Foo:
def func(self):
print ("func!")
# 定义属性
@property
def prop(self):
return "gloryroad"
# ############### 调用 ###############
foo_obj = Foo()
foo_obj.func()
print (foo_obj.prop) #调用属性不需要括号,等于调用了prop方法,获取返回值
#encoding=utf-8
class Goods(object):
@property
def price(self):
print ('@property')
@price.setter
def price(self, value):
print ('@price.setter')
@price.deleter
def price(self):
print ('@price.deleter')
# ############### 调用
obj = Goods()
obj.price # 自动执行 @property 修饰的 price 方法,并获取方法的返回值
obj.price = 123 # 自动执行 @price.setter 修饰的 price 方法,并将 123 赋值给方法的参数
del obj.price # 自动执行 @price.deleter 修饰的 price 方法
#属性:
#当读取属性时,执行@property方法
#当修改属性时,执行@price.setter方法
#当删除属性时,执行@price.deleter方法
#encoding=utf-8
class Goods(object):
def __init__(self):
self.__good_price=0
@property
def price(self):
return self.__good_price
@price.setter
def price(self, value):
if isinstance(value,(int,float)) and value>=0:
self.__good_price=value
@price.deleter
def price(self):
print ('@price.deleter')
#例子中的@property的方法名是price,在外部访问就是实例名.price
g=Goods()
g.price=-10
print(g.price)
g.price=122
print(g.price)
g.__good_price=456 #生成一个公开可以访问的实例变量,和类里的不是同一个值
print(g.__good_price)
print(g.price)
'''结果:
0
122
456
122
'''