面向对象分析与设计——案例:天龙八部技能系统

面向对象分析与设计

知识点:

  1. 面向对象的三大特征:从设计者的角度理解,

    1. 封装:将需求拆分为一个个类(分而治之)、每一个变化点封装成一个独立的类(封装变化)

    2. 继承:通过抽象出一个父类来约束子类,隔离子类的多变性(隔离变化)

    3. 多态:利用重写,使同一父类的方法在不同子类实现不同

  2. 六大原则:

    1. 开闭原则

    2. 类的单一职责

    3. 依赖倒置

    4. 组合复用原则

    5. 里氏替换

    6. 迪米特原则

  3. 类与类的关系

    1. 泛化关系

    2. 关联(组合)关系

    3. 依赖关系

案例:天龙八部技能系统
  1. 目的:通过练习该案例,初步理解面向对象设计思路,设计软件架构,熟悉python面向对象语法

  2. 需求:根据技能表设计技能系统
    在这里插入图片描述

  3. 面向对象设计流程

在这里插入图片描述

  1. 思考过程:

    1. 拿到需求后,曾经想过将一个技能设计一个类(类的单一职责),但罗列之后发现类与类之间存在重复的部分。

    2. 寻找到变化点–技能的具体效果,封装成一个个类,再设计一个技能释放器类统一调用这些类

    3. 因为技能效果类存在变化,使用继承的特性,抽象出一个父类技能效果,用来约束这些子类,隔离这些变化。用技能释放器类调用技能效果父类,不用关注具体的子类。符合了依赖倒置的原则和开闭原则。

    4. 利用多态的重写特性,将子类的共性个性化,里氏替换

    5. 通过配置文件加载列表

  2. 这样架构的优势:

    1. 一个需求改变(增加一个技能效果),只需要修改一个类。避免了散弹式修改

    2. 增加/修改技能效果,程序不用修改。依赖注入:根据配置文件,决定程序的功能

  3. 六大原则的具体体现

    • 开闭原则:增加新的影响效果,只需要创建新类, 不需要修改技能释放器.

    • 类的职责单一:释放器负责释放技能. 具体影响效果类负责某一种算法. 影响效果类负责隔离释放器与具体效果的变化.

    • 依赖倒置:技能释放器调用影响效果,没有调用具体效果类(伤害生命…) 子类依赖父类,但父类不依赖子类. 技能释放器通过字符串(配置文件)创建具体效果对象.

    • 组合复用:技能释放器与影响效果使用关联(组合)关系,而不是继承关系.

    • 里氏替换:父类出现的地方可以被子类替换,在替换后依然保持原功能(重写)所有具体影响效果,都可以将抽象(父)的影响效果替换掉

    • 迪米特原则:低耦合,存在隔离。具体影响效果之间,没有联系. 技能释放器与具体影响效果也有隔离.

在这里插入图片描述

"""
  天龙八部 技能系统
"""

class ImpactEffect:
  """
    影响效果
  """

  def impact(self):
    """
      影响效果,由技能释放器调用,由具体效果类实现.
    :return:
    """
    raise NotImplementedError()


class DamageEffect(ImpactEffect):
  """
    伤害生命效果
    可以被所有需要伤害生命的技能使用
  """

  def __init__(self, value):
    self.value = value

  def impact(self):
    print("伤害你的%d生命" % self.value)


class LowerMoveSpeed(ImpactEffect):
  """
    降低移动速度效果
  """

  def __init__(self, speed, time):
    self.speed = speed
    self.time = time

  def impact(self):
    print("降低速度为%d,持续时间%d." % (self.speed, self.time))


class SkillDeployer:
  """
    技能释放器
  """

  def __init__(self, name):
    self.name = name
    self.__list_impact = self.__config_skill()

  def __config_skill(self):
    """
      配置技能
    """
    # 配置文件中,记录的信息.
    dict_skill_config_info = {
      "金刚伏魔": ["DamageEffect(100)"],
      "降龙十八掌": ["LowerMoveSpeed(50,60)", "DamageEffect(100)"]
    }
    # 根据键(技能名称)从字典中获取值(str列表)
    list_skill_info = dict_skill_config_info[self.name]
    # 根据字符串列表,创建影响效果对象的列表.
    # "DamageEffect(100)" -->DamageEffect的对象
    list_skill_instance = []
    for item in list_skill_info:
      list_skill_instance.append(eval(item))
    # 返回技能列表
    return list_skill_instance
    # 建议使用列表推导式
    # return [eval(item) for item in list_skill_info]

  def generate_skill(self):
    """
      生成(释放)技能
    :return:
    """
    print(self.name, "技能释放啦")
    # 遍历影响效果列表,执行每个效果.
    for item in self.__list_impact:
      item.impact()


# 测试
# 创建技能(确定技能名称,加载技能效果)
xlsbz = SkillDeployer("降龙十八掌")
xlsbz.generate_skill()

jgfm = SkillDeployer("金刚伏魔")
jgfm.generate_skill()
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值