Unity 策略模式(实例详解)

文章目录

简介

在Unity中使用策略模式,我们可以将不同的行为或算法封装成独立的类(策略),然后根据需要在运行时动态选择和切换这些策略。下面我将通过5个简化的代码示例来说明如何在Unity中实现策略模式。

示例1:角色攻击行为

csharp 复制代码
// 定义策略接口(抽象策略类)
public abstract class AttackStrategy
{
    public abstract void ExecuteAttack(Character target);
}

// 具体策略类 - 近战攻击
public class MeleeAttack : AttackStrategy
{
    public override void ExecuteAttack(Character target)
    {
        Debug.Log($"{target.name} 使用近战攻击了 {target.Target.name}");
        // 实现具体的近战攻击逻辑...
    }
}

// 具体策略类 - 远程攻击
public class RangedAttack : AttackStrategy
{
    public override void ExecuteAttack(Character target)
    {
        Debug.Log($"{target.name} 发射了一枚远程攻击向 {target.Target.name}");
        // 实现具体的远程攻击逻辑...
    }
}

// 上下文类 - 角色
public class Character
{
    public AttackStrategy CurrentAttackStrategy { get; set; }

    public void ChangeAttackStrategy(AttackStrategy newStrategy)
    {
        CurrentAttackStrategy = newStrategy;
    }

    public void PerformAttack()
    {
        if (CurrentAttackStrategy != null)
        {
            CurrentAttackStrategy.ExecuteAttack(this);
        }
    }
}

// 使用示例
Character player = new Character();
player.CurrentAttackStrategy = new MeleeAttack(); // 设置初始攻击策略为近战
player.PerformAttack();

// 游戏进程中动态切换策略
player.ChangeAttackStrategy(new RangedAttack());
player.PerformAttack();

示例2:游戏内购折扣策略

csharp 复制代码
// 抽象折扣策略
public abstract class DiscountStrategy
{
    public abstract float CalculateDiscount(float originalPrice);
}

// 具体折扣策略 - 普通价格
public class NormalDiscount : DiscountStrategy
{
    public override float CalculateDiscount(float originalPrice)
    {
        return originalPrice; // 不打折
    }
}

// 具体折扣策略 - 五折优惠
public class HalfOffDiscount : DiscountStrategy
{
    public override float CalculateDiscount(float originalPrice)
    {
        return originalPrice * 0.5f;
    }
}

// 上下文类 - 购物车
public class ShoppingCart
{
    public DiscountStrategy CurrentDiscountStrategy { get; set; }

    public float GetFinalPrice(float itemPrice)
    {
        return itemPrice * CurrentDiscountStrategy.CalculateDiscount(itemPrice);
    }

    public void SetDiscountStrategy(DiscountStrategy newDiscount)
    {
        CurrentDiscountStrategy = newDiscount;
    }
}

// 使用示例
ShoppingCart cart = new ShoppingCart();
cart.CurrentDiscountStrategy = new NormalDiscount();
float finalPrice = cart.GetFinalPrice(100); // 原价购买

cart.SetDiscountStrategy(new HalfOffDiscount());
finalPrice = cart.GetFinalPrice(100); // 半价购买

示例3:NPC寻路策略

csharp 复制代码
// 抽象寻路策略
public abstract class PathfindingStrategy
{
    public abstract List<Vector3> FindPath(Vector3 start, Vector3 end);
}

// 具体寻路策略 - A*寻路
public class AStarPathfinding : PathfindingStrategy
{
    public override List<Vector3> FindPath(Vector3 start, Vector3 end)
    {
        // 实现A*算法寻找路径
        // ...
        return pathList;
    }
}

// 具体寻路策略 - Dijkstra寻路
public class DijkstraPathfinding : PathfindingStrategy
{
    public override List<Vector3> FindPath(Vector3 start, Vector3 end)
    {
        // 实现Dijkstra算法寻找路径
        // ...
        return pathList;
    }
}

// 上下文类 - NPC实体
public class NPC
{
    public PathfindingStrategy CurrentPathfindingStrategy { get; set; }

    public void MoveTo(Vector3 destination)
    {
        var path = CurrentPathfindingStrategy.FindPath(transform.position, destination);
        // 根据路径移动NPC
        // ...
    }

    public void SetPathfindingStrategy(PathfindingStrategy newPathfinding)
    {
        CurrentPathfindingStrategy = newPathfinding;
    }
}

// 使用示例
NPC npc = new NPC();
npc.CurrentPathfindingStrategy = new AStarPathfinding();
npc.MoveTo(targetPosition);

// 更改寻路策略
npc.SetPathfindingStrategy(new DijkstraPathfinding());
npc.MoveTo(anotherTargetPosition);

示例4:动画过渡策略

csharp 复制代码
// 抽象动画过渡策略
public abstract class TransitionStrategy
{
    public abstract void ApplyTransition(Animator animator, string targetState);
}

// 具体动画过渡策略 - 直接切换
public class DirectTransition : TransitionStrategy
{
    public override void ApplyTransition(Animator animator, string targetState)
    {
        animator.CrossFade(targetState, 0f);
    }
}

// 具体动画过渡策略 - 平滑过渡
public class SmoothTransition : TransitionStrategy
{
    public override void ApplyTransition(Animator animator, string targetState)
    {
        animator.CrossFade(targetState, 0.5f);
    }
}

// 上下文类 - 动画控制器
public class AnimationController
{
    public TransitionStrategy CurrentTransitionStrategy { get; set; }

    public void ChangeAnimation(string stateName)
    {
        CurrentTransitionStrategy.ApplyTransition(animator, stateName);
    }

    public void SetTransitionStrategy(TransitionStrategy newStrategy)
    {
        CurrentTransitionStrategy = newStrategy;
    }
}

// 使用示例
AnimationController animCtrl = new AnimationController();
animCtrl.CurrentTransitionStrategy = new DirectTransition();
animCtrl.ChangeAnimation("Run");

// 更改过渡策略
animCtrl.SetTransitionStrategy(new SmoothTransition());
animCtrl.ChangeAnimation("Idle");

示例5:敌人AI决策策略

csharp 复制代码
// 抽象AI决策策略
public abstract class AIActionStrategy
{
    public abstract void DecideAction(Enemy enemy);
}

// 具体AI决策策略 - 随机行动
public class RandomAI : AIActionStrategy
{
    public override void DecideAction(Enemy enemy)
    {
        int randomChoice = Random.Range(0, 3);
        switch (randomChoice)
        {
            case 0:
                enemy.Attack();
                break;
            case 1:
                enemy.Defend();
                break;
            case 2:
                enemy.Flee();
                break;
        }
    }
}

// 具体AI决策策略 - 精确计算行动
public class CalculatedAI : AIActionStrategy
{
    public override void DecideAction(Enemy enemy)
    {
        // 根据战场情况、玩家状态等精确计算并执行动作
        // ...
    }
}

// 上下文类 - 敌人实体
public class Enemy
{
    public AIActionStrategy CurrentAIAction { get; set; }

    public void UpdateAI()
    {
        CurrentAIAction.DecideAction(this);
    }

    public void SetAIAction(AIActionStrategy newAI)
    {
        CurrentAIAction = newAI;
    }
}

// 使用示例
Enemy enemy = new Enemy();
enemy.CurrentAIAction = new RandomAI();
enemy.UpdateAI(); // 随机执行动作

// 更改AI策略
enemy.SetAIAction(new CalculatedAI());
enemy.UpdateAI(); // 根据计算结果执行动作

以上每个示例都展示了策略模式的基本应用,在Unity中可以根据具体项目需求灵活运用这一设计模式。

python推荐学习汇总连接:
50个开发必备的Python经典脚本(1-10)

50个开发必备的Python经典脚本(11-20)

50个开发必备的Python经典脚本(21-30)

50个开发必备的Python经典脚本(31-40)

50个开发必备的Python经典脚本(41-50)


​最后我们放松一下眼睛

相关推荐
xiaogutou11214 分钟前
2026年历史课件PPT模板选购指南:教师备课效率与精度的平衡方案
开发语言·c#
Eiceblue3 小时前
使用 C# 将 Excel 转换为 Markdown 表格(含批量转换示例)
开发语言·c#·excel
天人合一peng3 小时前
unity 生成标记根据背景色变色为明显的颜色
unity·游戏引擎
魔士于安4 小时前
Unity 超市总动员 超市收银台 超市货架 超市购物手推车 超市常见商品
游戏·unity·游戏引擎·贴图·模型
CandyU24 小时前
Unity —— 数据持久化
unity·游戏引擎
zh路西法4 小时前
【Unity实现Oneshot胶卷显形】游戏窗口化与Win32API的使用
游戏·unity·游戏引擎
迪捷软件5 小时前
显控系统虚拟仿真的工程化路径
游戏引擎·cocos2d
不会编程的懒洋洋5 小时前
WPF XAML+布局+控件
xml·开发语言·c#·视觉检测·wpf·机器视觉·视图
唐青枫6 小时前
别再层层传参了!C#.NET AsyncLocal 异步上下文透传实战
c#·.net
明如正午7 小时前
【C#】托管调试助手 “PInvokeStackImbalance“:的调用导致堆栈不对称。原因可能是托管的 PInvoke 签名与非托管的目标签名不匹配。
c#