Python-Level1-day13:面向对象思想多态之重写自定义方法;MVC框架

 作业
1. 三合一
2. 当天练习独立完成
​
3. 父类:车(品牌,速度)
   创建子类:电动车(电池容量,充电功率)
   使用属性保护速度在0~260,电池容量在0~10000范围内
   直接打印对象格式:
       xx的速度是xx
       xx的速度是xx,电池容量是xx,充电功率是xx
​
4.定义函数,根据员工编号,删除员工信息,返回是否删除成功
class Employee:
    def __init__(self, eid, did, name, money):
        self.eid = eid
        self.did = did
        self.name = name
        self.money = money
​
# 员工列表
list_employees = [
    Employee(1001, 9002, "师父", 60000),
    Employee(1002, 9001, "孙悟空", 50000),
    Employee(1003, 9002, "猪八戒", 20000),
    Employee(1004, 9001, "沙僧", 30000),
    Employee(1005, 9001, "小白龙", 15000),
]
​
5. (选做)完成2048 向左向右移动函数
 --定义向左移动函数,改变list_map中的数据
    思路:将list_map每行赋值给list_merge
         调用合并函数(练习2)
​
 -- 定义向右移动函数,改变list_map中的数据
    思路:将list_map每行,反转,赋值给list_merge
         调用合并函数
         因为切片反转会创建新容器,所以还需要将list_merge还原给list_map
​
 温馨提示:画内存图哦
​

 
class Car:
    def __init__(self, brand, speed):
        self.brand = brand
        self.speed = speed
​
    @property
    def speed(self):
        return self.__speed
​
    @speed.setter
    def speed(self, value):
        if 0 < value < 260:
            self.__speed = value
        else:
            raise Exception("速度异常")
​
    def __str__(self):
        return f" {self.brand}的速度是{self.speed}"
​
​
class EleCar(Car):
    def __init__(self, brand, speed, rongliang, gonglv):
        super().__init__(brand, speed)  # 优点是继承了数据同时也继承属性
        self.rongling = rongliang
        self.gonglv = gonglv
​
    @property
    def rongling(self):
        return self.__rongling
​
    @rongling.setter
    def rongling(self, value):
        if 0 < value < 1000:
            self.__rongling = value
        else:
            self.__rongling = 1000
​
    def __str__(self):
        # return f" {self.brand}的速度是{self.speed},电池容量是{self.rongling},充电功率是{self.gonglv}"
        # 继承父类方法
        return super().__str__() + f",电池容量是{self.rongling},充电功率是{self.gonglv}"
​
# 即使子类没有写构造函数或者方法,只要叫一声父类全部继承过来
bc = Car("奔驰", 220)
print(bc)
​
am = EleCar("艾玛", 180, 10000, 220)
print(am)

# 4.定义函数,根据员工编号,删除员工信息,返回是否删除成功
class Employee:
    def __init__(self, eid, did, name, money):
        self.eid = eid
        self.did = did
        self.name = name
        self.money = money
​
    def __eq__(self, other):
        return self.eid == other
​
​
# 员工列表
list_employees = [
    Employee(1001, 9002, "师父", 60000),
    Employee(1002, 9001, "孙悟空", 50000),
    Employee(1003, 9002, "猪八戒", 20000),
    Employee(1004, 9001, "沙僧", 30000),
    Employee(1005, 9001, "小白龙", 15000),
]
​
​
# 这么写虽可以实现,但失去一片内置方法的森林
# def delete_eid(eid):
#     for i in range(len(list_employees)):
#         if list_employees[i].eid == eid:
#             del list_employees[i]
#             return True
#     return False
​
def delete_eid(cid):
    if cid in list_employees:
        list_employees.remove(cid)  # 内部怎么调eq你不用管
        return True
    return False
​
​
print(delete_eid(1005))
print(list_employees)
​

"""
5. (选做)完成2048 向左向右移动函数
 --定义向左移动函数,改变list_map中的数据
    思路:将list_map每行赋值给list_merge
         调用合并函数
​
 -- 定义向右移动函数,改变list_map中的数据
    思路:将list_map每行,反转,赋值给list_merge
         调用合并函数
         因为切片反转会创建新容器,
         所以还需要将list_merge还原给list_map
​
 温馨提示:画内存图哦
"""
list_merge = [2, 0, 2, 0]
​
def zero_to_end():
    for i in range(len(list_merge) - 1, -1, -1):
        if list_merge[i] == 0:
            del list_merge[i]
            list_merge.append(0)
​
def merge():
    zero_to_end()
    for i in range(len(list_merge) - 1):
        if list_merge[i] == list_merge[i + 1]:
            list_merge[i] += list_merge[i + 1]
            del list_merge[i + 1]
            list_merge.append(0)
​
map = [
    [2, 0, 0, 2],
    [4, 2, 0, 2],
    [2, 4, 2, 4],
    [0, 4, 0, 4],
]
​
def move_left():
    global list_merge
    for line in map:
        list_merge = line
        merge()
​
def move_right():
    global list_merge
    for line in map:
        list_merge = line[::-1]# 切片读取数据时产生新列表
        merge()
        line[::-1] = list_merge  # 所以需要还原数据(list_merge --> map)
        # line = list_merge[::-1] # 错误,修改的是变量line不是map
        # line[:] = list_merge[::-1]
​
​
#move_right()
print(map)

多态之重写自定义函数

(1) 定义:子类实现了父类中相同的方法(方法名、参数),在调用该方法时,实际执行的

是子类的方法体。

(2) 快捷键:ctrl + O 选择重写的方法

(3) 作用:在继承的基础上,体现类型的个性(一个行为有不同的实现),增强程序灵活性。

"""
    重写自定义函数 - 面向对象精髓
"""
# 老张开车去东北  跨类调用
"""
class Person:
    def __init__(self, name=""):
        self.name = name
​
    def go_to(self, position, vehicle):
        print(self.name, "去", position)
        vehicle.run()
​
​
class Car:
    def run(self):
        print("嘟嘟嘟~")
​
​
lz = Person()
c = Car()
lz.go_to("东北", c)
"""
​
​
# 要求:日后可能坐飞机,划船,骑车...
# 缺点:违背开闭原则(增加新功能,不修改客户端代码)
​
class Person:
    def __init__(self, name=""):
        self.name = name
​
    def go_to(self, position, vehicle):
        print(self.name, "去", position)
        # 根据不同类型,决定不同行为(行驶/飞行)
        if type(vehicle) == Car:
            vehicle.run()
        elif type(vehicle) == Airplane:
            vehicle.fly()
​
class Car:
    def run(self):
        print("嘟嘟嘟~")
​
class Airplane:
    def fly(self):
        print("嗖嗖嗖~")
​
lz = Person()
c = Car()
a = Airplane()
lz.go_to("东北", c)
lz.go_to("东北", a)

img

"""
    改造
    编码时调用交通工具(父类);运行时执行汽车(儿子)
    共同父类Object 里面有str等内置方法
​
    多态:  # 编码时调用父类
          # 运行时执行子类
"""
​
​
class Person:
    def __init__(self, name=""):
        self.name = name
​
    def go_to(self, position, vehicle):
        print(self.name, "去", position)
        if isinstance(vehicle, Vehicle):
            # 先行确定用法
            # 编码时调用交通工具(爸爸)
            # 运行时执行汽车(儿子)
            vehicle.transport()
​
​
class Vehicle:
​
    def transport(self):
        pass
​
​
class Car(Vehicle):
#ctrl+o 选择从写的方法
    def transport(self):
        print("嘟嘟嘟~")
​
​
class Airplane(Vehicle):
    def transport(self):
        print("嗖嗖嗖~")
​
​
lz = Person()
c = Car()
a = Airplane()
lz.go_to("东北", c)
lz.go_to("东北", a)
​
​

img

 

"""
    练习1:以面向对象思想,描述下列情景:
    情景:手雷爆炸,可能伤害敌人(头顶爆字)或者玩家(碎屏)。
    变化:还可能伤害房子、树、鸭子....
    要求:增加新事物,不影响手雷.
    画出架构设计图
​
    面向对象三大特征:
        封装(分):创建了手雷、敌人、玩家
        继承(隔):创建了目标类,隔离手雷与敌人、玩家的变化
        多态(做):敌人对于受伤做的是头顶爆字
                 玩家对于受伤做的是碎屏
"""
​
"""
版本1:一次炸一个
​
class Grenade:
    def explode(self, target):
        print("爆炸啦")
        target.damage() 
​
#父类
class Target: 
    def damage(self):
        pass
​
​
class Player(Target):
    def damage(self):
        print("碎屏")
​
​
​
class Enemy: 
    def damage(self):  
        print("头顶爆字")
​
​
g = Grenade()
p = Player()
g.explode(p)
e = Enemy()
g.explode(e)
"""
​
​
# 版本2:一次炸多个
class Grenade:
    def explode(self, *args):  # 多实参合一元组
        print("爆炸啦")
        for target in args:
            target.damage()
​
​
class Target:
    def damage(self):
        pass
​
​
class Player(Target):
    def damage(self):
        print("碎屏")
​
​
class Enemy:  #小鸭子原则
    def damage(self):
        print("头顶爆字")
​
​
g = Grenade()
g.explode(Player(), Enemy())
​

"""
    练习2:创建图形管理器
        1. 记录多种图形(圆形、矩形....)
        2. 提供计算总面积的方法.
​
        满足:开闭原则
        测试:
            创建图形管理器,存储多个图形对象。
            通过图形管理器,调用计算总面积方法.
​
    封装(分):创建了GraphicsManager、Circle、Rectangle
    继承(隔):创建了Graphics,隔离GraphicsManager和Circle、Rectangle的变化
    多态(做):Circle重写了Graphics的get_area方法
             Rectangle重写了Graphics的get_area方法
"""
​
"""
class GraphicsManager:
    def __init__(self):
        self.all_graphics = []
​
    def calculate_total_area(self):
        total_area = 0
        for item in self.all_graphics:
            # 多态
            # 编码时调用图形
            # 运行时执行矩形、圆形
            total_area += item.get_area()
        return total_area
​
class Graphics:
    def get_area(self):
        pass
​
class Circle(Graphics):
    def __init__(self, r):
        self.r = r
​
    def get_area(self):
        return 3.14 * self.r ** 2
​
class Rectangle(Graphics):
    def __init__(self, l, w):
        self.l = l
        self.w = w
​
    def get_area(self):
        return self.l * self.w
​
manager = GraphicsManager()
manager.all_graphics.append(Circle(5))
manager.all_graphics.append(Rectangle(2, 3))
print(manager.calculate_total_area())
"""
​
​
# 进一步封装
​
class GraphicsManager:
    def __init__(self):
        self.__all_graphics = []
​
    @property
    def all_graphics(self):
        return self.__all_graphics
​
    def add_graphics(self, graph):
        if isinstance(graph, Graphics):
            self.__all_graphics.append(graph)
​
    def calculate_total_area(self):
        total_area = 0
        for item in self.__all_graphics:
            total_area += item.get_area()
        return total_area
​
​
class Graphics:
​
    def __init__(self, name=""):
        self.name = name
​
    def get_area(self):
        pass
​
​
class Circle(Graphics):
    def __init__(self, name, r):
        super().__init__(name)
        self.r = r
​
    def get_area(self):
        return 3.14 * self.r ** 2
​
​
class Rectangle(Graphics):
    def __init__(self, name, l, w):
        super().__init__(name)
        self.l = l
        self.w = w
​
    def get_area(self):
        return self.l * self.w
​
​
manager = GraphicsManager()
manager.add_graphics(Circle("圆形", 5))
manager.add_graphics(Rectangle("矩形", 2, 3))
# 打印所有图形总面积
print(manager.calculate_total_area())
# 读取所有图形名称
for item in manager.all_graphics:
    print(item.name)
​

"""
    一家公司有如下几种岗位:
        程序员:底薪 + 分红
        测试员:底薪 + Bug数 × 5
        ....
        销售:底薪 + 销售额 × 0.03
​
    创建员工管理器
        -- 记录所有员工
        -- 提供计算总薪资的方法
"""
​
​
class Employee_Manger:
    def __init__(self):
        self.__employees = []  # 没有property对外不可读不可写
​
    @property  # 对外可读
    def employees(self):
        return self.__employees
​
    def add_employ(self, *emp):
        for item in emp:
            if isinstance(item, Employee):
                self.__employees.append(item)
​
    def cal_all_money(self):
        all_money = 0
        for item in self.__employees:
            all_money += item.caluate()
        return all_money
​
​
class Employee:
    def __init__(self, base_money):
        self.base_money = base_money
​
    def caluate(self):
        pass
​
​
class TestEmp(Employee):
    def __init__(self, base_money, fenghong):
        super().__init__(base_money)
        self.fenghong = fenghong
​
    def caluate(self):
        return self.base_money + self.fenghong
​
​
class ChengxuEmp(Employee):
    def __init__(self, base_money, bug):
        super().__init__(base_money)
        self.bug = bug
​
    def caluate(self):
        return self.base_money + self.bug * 500
​
​
class XiaoshouEmp(Employee):
    def __init__(self, base_money, xiaoshoue):
        super().__init__(base_money)
        self.xiaoshoue = xiaoshoue
​
    def caluate(self):
        return self.base_money + self.xiaoshoue * 0.5
​
​
manger = Employee_Manger()
test1 = TestEmp(100, 5)
chengxuyuan1 = ChengxuEmp(150, 5)
xiaoshou1 = XiaoshouEmp(50, 30)
manger.add_employ(test1, chengxuyuan1, xiaoshou1)
print(manger.cal_all_money())
​
​

软件基本框架MVC

"""
    MVC学生管理系统
​
"""
​
​
class StudentModel:
    """
        学生模型:封装数据
    """
​
    def __init__(self, name="", age=0, score=0):
        self.name = name
        self.age = age
        self.score = score
        self.sid = 0  # 学生全球唯一标识符,
        # 由软件自动确定,不是人录入
​
​
class StudentView:
    """
        学生视图:处理界面逻辑
    """
​
    def __init__(self, controller):
        self.controller = controller
​
    def display_menu(self):
        print("按1键录入学生信息")
        print("按2键显示学生信息")
        print("按3键删除学生信息")
        print("按4键修改学生信息")
​
    def select_menu(self):
        item = input("请输入您的选项:")
        if item == "1":
            # 先写方法调用,再alt+回车自动生成
            self.input_student()
        elif item == "2":
            pass
​
    def input_student(self):
        stu = StudentModel()
        stu.name = input("请输入学生姓名:")
        stu.score = int(input("请输入学生成绩:"))
        stu.age = int(input("请输入学生年龄:"))
        self.controller.add_student(stu)
        print("添加成功")
​
​
class StudentController:
    """
        学生控制器:负责处理业务逻辑
    """
​
    start_id = 1000
​
    @classmethod
    def set_student_id(cls, stu):
        cls.start_id += 1
        stu.sid = cls.start_id
​
    def __init__(self):
        self.students = []
​
    def add_student(self, stu):
        StudentController.set_student_id(stu)
        self.students.append(stu)
​
​
controller = StudentController()
view = StudentView(controller)
while True:
    view.display_menu()
    view.select_menu()
​

class CommodityModel:
​
    def __init__(self, name="", price=0):
        self.name = name
        self.price = price
        self.cid = 0
​
​
class CommodityView:
​
    def __init__(self, controller):
        self.controller = controller
​
    def display_menu(self):
        print("按1键录入商品信息")
        print("按2键显示商品信息")
        print("按3键删除商品信息")
        print("按4键修改商品信息")
​
    def select_menu(self):
        item = input("请输入您的选项:")
        if item == "1":
            self.input_commodity()
        elif item == "2":
            pass
​
    def input_commodity(self):
        cmd = CommodityModel()
        cmd.name = input("请输入商品姓名:")
        cmd.price = int(input("请输入商品单价:"))
        self.controller.add_commodity(cmd)
        print("添加成功")
​
​
class CommodityController:
    start_id = 1000
​
    @classmethod
    def set_comodity_id(cls, com):
        cls.start_id += 1
        com.cid = cls.start_id
​
    def __init__(self):
        self.comoditys = []
​
    def add_commodity(self, com):
        CommodityController.set_comodity_id(com)
        self.comoditys.append(com)
​
​
controller = CommodityController()
view = CommodityView(controller)
while True:
    view.display_menu()
    view.select_menu()
​

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

dpq666dpq666

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值