程序虽小,五脏俱全,介绍了私有成员、封装、继承、动态等概念,对于理解python中这些抽象的概念很有帮助
class Employee:
"""
私有属性姓名和薪水,双下划线开头的变量或方法统称为私有成员(私有属性、方法),私有成员只能在类的内部
使用,这意味着类的外部(包括子类)都不能调用私有成员。
"""
__name = None
__salary = None
# 构造方法,初始化类的属性
def __init__(self, name, salary):
self.__name = name
self.__salary = salary
# 返回年薪
def get_annual(self):
return self.__salary * 12
"""
公共方法(相对于私有方法),返回私有属性姓名,外部可以调用此公共方法实现对私有属性姓名的访问(这就是
封装的好处之一,可以把数据保护起来)
"""
def get_name(self):
return self.__name
# 公共方法,修改私有属性姓名
def set_name(self, name):
self.__name = name
# 公共方法,返回私有属性薪水
def get_salary(self):
return self.__salary
# 公共方法,修改私有属性薪水
def set_salary(self, salary):
self.__salary = salary
"""
定义子类普通工人,继承Employee,引出继承的概念,子类可以继承所有的属性和方法,包括私有成员,但是无法直接访问私有成员
"""
class Woker(Employee):
# 定义方法工作,打印姓名,通过父类提供的公共方法
def work(self):
print(f'{
self.get_name()}在工作。')
# 定义子类管理层
class Manager(Employee):
__bonus = None
"""
构造方法,其中name和salary可以通过父类的构造器初始化,super().方法的方式调用构造器完成对其初
始化,此处的self为啥不写,是因为此处相当于调用,self为隐式传入
"""
def __init__(self, name, salary, bonus):
super().__init__(name, salary)
self.__bonus = bonus
# 定义方法管理,打印姓名,通过父类提供的公共方法
def manager(self):
print(f'{
self.get_salary()}在管理。')
# 返回年薪,此处仍然使用super()调用父类方法,注super()只能调用直接父类成员
# 重写父类get_annual()方法,可以做一些业务改变,体会重写的作用
def get_annual(self):
return super().get_annual() + self.__bonus
"""
定义函数,参数为Employee类,此处为类型注解,同时引入多态概念,后面我们创建多个子类对象,作为参数传入
这个函数,在python中子类是可以传递给父类类型的,比如传入的是w1,返回的是w1.get_annual(),程序首先会查
找Worker类是否存在get_annual()方法,发现没有找到,就会到父类查找,找到了,就执行,此时注意self为对象
本身,因此w1和m1两个
**不同子类对象调用相同的方法get_annual()产生不同的状态,这就成为多态**。
"""
def show_emp_annual(e:Employee):
return e.get_annual()
# isinstance(object, class)函数判断对象是否为某个类或子类的对象
def working(e:Employee):
if isinstance(e, Woker):
e.work()
elif isinstance(e, Manager):
e.manager()
else:
pass
w1 = Woker('tom', 12000)
m1 = Manager('jack', 25000, 10000)
print(show_emp_annual(w1))
print(show_emp_annual(m1))
working(w1)
working(m1)