博客地址:blog.liujunliang.com.cn
写在前面
在游戏中计算各个觉得的攻击值、防御值时,由于各个角色的职业不同,攻击值和防御值计算算法就会不一样
通常使用if....else语句来抉择不同类型之间的算法将带来程序复杂和难以维持,当有新的算法或行为时违背开闭原则
策略模式是对算法的包装,是把使用算法的责任和算法本身分割开来。委托给不同的对象管理。
模式角色
环境类:对策略进行二次封装,目的是避免高层模块对策略的直接调用
抽象策略:这是一个抽象角色,通常由一个接口或抽象类实现,其提供所有具体策略类所需要的接口
具体策略:包装相关的算法或行为
模式结构图
代码案例
定义一个抽象类(抽象策略)
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public abstract class IStrategy
{
public abstract int GetAttackValue();
public abstract int GetDefenseValue();
}
创建实现接口的实体类(具体策略)
战士
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class WarriorStrategy : IStrategy
{
public override int GetAttackValue()
{
Debug.Log("得到战士攻击值");
return 0;
}
public override int GetDefenseValue()
{
Debug.Log("得到战士防御值");
return 0;
}
}
法师
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class MasterStrategy : IStrategy
{
public override int GetAttackValue()
{
Debug.Log("得到法师攻击值");
return 0;
}
public override int GetDefenseValue()
{
Debug.Log("得到法师防御值");
return 0;
}
}
创建环境类
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Context
{
private IStrategy strategy;
public Context(IStrategy strategy)
{
this.strategy = strategy;
}
public void SetStrategy(IStrategy strategy)
{
this.strategy = strategy;
}
public int GetAttackValue()
{
return strategy.GetAttackValue();
}
public int GetDefenseValue()
{
return strategy.GetDefenseValue();
}
}
使用Context来查看当它改变策略Strategy时的行为变化
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Main : MonoBehaviour
{
private Context context;
// Use this for initialization
void Start ()
{
context = new Context(new WarriorStrategy());
context.GetAttackValue();
context.GetDefenseValue();
context.SetStrategy(new MasterStrategy());
context.GetAttackValue();
context.GetDefenseValue();
}
}
运行Unity,一切正常
模式优点
1、避免使用多重条件
2、易于扩展
3、策略类之间只有切换