单例/观察者模式

==============          单例模式        =======================

单例模式是一种设计模式,即保证系统中只有一个类的实例,且该实例易于外界访问,从而方便对对象的访问,可以控制资源使用,个人理解类似于大家在一块黑板上讨论东西,不关心参与讨论的对象,单例就相当于黑板。
        游戏中我一般在一个场景中设置一个GameController类为单例模式,其中提供若干辅助操作对象的方法,如控制参数设置,提供计算方法等,也会设置一个单例的声音管理器专门管理声音的统一播放。Unity中我这样设置单例。

public class GameManager : MonoBehaviour
{
    private static  GameManager  _instance;

    public static  GameManager Instance         //此段有时省略
    {
        get { return   _instance; }
    }

    void Awake()        
    {
        _instance = this;     //使自身可被调用
    }
}


   常规写法:

      

public class Singleton
{
    static Singleton instance;
 
    public static Singleton Instance {
        get {
            if (instance == null) {
                instance = new Singleton ();
            }
             return instance;
        }
    }
}


===========          观察者模式         ============= 

有时被称作发布/订阅模式,观察者模式定义了一种一对多的依赖关系,让多个观察者对象同时监听某一个主题对象。这个主题对象在状态发生变化时,会通知所有观察者对象,使它们能够自动更新自己

当我们玩游戏时,经常会出现一些事件,而这个事件可能会影响到许多个模块时就可以用到观察者模式。例如:当我们在游戏中被丧尸咬时,我们就触发了变身丧尸的特殊事件,此时我们本身的人物模型可能会改变,同时系统的背景音乐和战斗方式也可能改变。此时就是一个事件影响多个模块的状况了,就可以用到观察者模式,废话不多说直接上代码。

[csharp]  view plain  copy
  1. /// <summary>  
  2. /// 抽象观察者,定义接收通知的接口  
  3. /// </summary>  
  4. public abstract class Observer  
  5. {  
  6.     public abstract void OnNotify();  
  7. }  

        首先我们定义一个抽象类Observer,Obserber中我们定义抽象方法,这就是当我们接收到事件时要执行的方法了。

[csharp]  view plain  copy
  1. /// <summary>  
  2. /// 抽象主题(抽象被观察者)类,内含观察者列表和实现接收各种通知  
  3. /// </summary>  
  4. public abstract class Subject  
  5. {  
  6.     private List<Observer> observerList = new List<Observer>();  
  7.     /// <summary>  
  8.     /// 添加观察者  
  9.     /// </summary>  
  10.     /// <param name="observer"></param>  
  11.     public void AddObserver(Observer observer)  
  12.     {  
  13.         observerList.Add(observer);  
  14.     }  
  15.     /// <summary>  
  16.     /// 移除观察者  
  17.     /// </summary>  
  18.     /// <param name="observer"></param>  
  19.     public void RemoveObserver(Observer observer)  
  20.     {  
  21.         observerList.Remove(observer);  
  22.     }  
  23.     /// <summary>  
  24.     /// 推送通知  
  25.     /// </summary>  
  26.     public void Notify()  
  27.     {  
  28.         foreach (Observer o in observerList)  
  29.         {  
  30.             o.OnNotify();  
  31.         }  
  32.     }  
  33. }  

        然后是定义一个抽象主题类,抽象主题类中包含添加和移除Observer的方法,定义一个Notify方法作为推送方法。我们推送消息到Observer链表中的各个Observer方法,Observer方法就开始执行监听的方法了。

[csharp]  view plain  copy
  1. /// <summary>  
  2. /// 具体主题(被观察者)类,实现要推送的主题  
  3. /// </summary>  
  4. public class Boss : Subject  
  5. {  
  6.     private string _command;  
  7.     public string Command  
  8.     {  
  9.         get { return _command; }  
  10.         set { _command = value; }  
  11.     }  
  12. }  
        具体主题类是真正实现要推送的消息,我们确认一个事件是否推送和如何推送消息的方法等都是在这里完成的。

[csharp]  view plain  copy
  1. /// <summary>  
  2.    /// 观察者类,当接收到推送通知时,实现各个模块功能  
  3.    /// </summary>  
  4.    public class EmployeeA:Observer  
  5.    {  
  6.        private string _name;  
  7.        private string _doSomething;  
  8.        private Boss _boss;  
  9.   
  10.        public string Name  
  11.        {  
  12.            get { return _name; }  
  13.            set { _name = value; }  
  14.        }  
  15.        public string DoSomething  
  16.        {  
  17.            get { return _doSomething; }  
  18.            set { _doSomething = value; }  
  19.        }  
  20.        public EmployeeA(Boss boss)  
  21.        {  
  22.            _boss = boss;  
  23.        }  
  24.        public override void OnNotify()  
  25.        {  
  26.            if (_boss.Command == "下达命令")  
  27.            {  
  28.                Debug.Log("我是" + _name + "我要" + DoSomething);  
  29.            }  
  30.        }  
  31.    }  

        观察者类,这个是获取推送消息时真正要执行的一段程序,在这里具体化要执行的程序的工作内容。




下面是完整的代码:

[csharp]  view plain  copy
  1. using UnityEngine;  
  2. using System.Collections;  
  3. using System.Collections.Generic;  
  4. using System;  
  5.   
  6. public class ObserverPattern : MonoBehaviour {  
  7.     /// <summary>  
  8.     /// 抽象观察者,定义接收通知的接口  
  9.     /// </summary>  
  10.     public abstract class Observer  
  11.     {  
  12.         public abstract void OnNotify();  
  13.     }  
  14.   
  15.     /// <summary>  
  16.     /// 抽象主题(抽象被观察者)类,内含观察者列表和实现接收各种通知  
  17.     /// </summary>  
  18.     public abstract class Subject  
  19.     {  
  20.         private List<Observer> observerList = new List<Observer>();  
  21.         /// <summary>  
  22.         /// 添加观察者  
  23.         /// </summary>  
  24.         /// <param name="observer"></param>  
  25.         public void AddObserver(Observer observer)  
  26.         {  
  27.             observerList.Add(observer);  
  28.         }  
  29.         /// <summary>  
  30.         /// 移除观察者  
  31.         /// </summary>  
  32.         /// <param name="observer"></param>  
  33.         public void RemoveObserver(Observer observer)  
  34.         {  
  35.             observerList.Remove(observer);  
  36.         }  
  37.         /// <summary>  
  38.         /// 推送通知  
  39.         /// </summary>  
  40.         public void Notify()  
  41.         {  
  42.             foreach (Observer o in observerList)  
  43.             {  
  44.                 o.OnNotify();  
  45.             }  
  46.         }  
  47.     }  
  48.   
  49.     /// <summary>  
  50.     /// 具体主题(被观察者)类,实现要推送的主题  
  51.     /// </summary>  
  52.     public class Boss : Subject  
  53.     {  
  54.         private string _command;  
  55.         public string Command  
  56.         {  
  57.             get { return _command; }  
  58.             set { _command = value; }  
  59.         }  
  60.     }  
  61.   
  62.     /// <summary>  
  63.     /// 观察者类,当接收到推送通知时,实现各个模块功能  
  64.     /// </summary>  
  65.     public class EmployeeA:Observer  
  66.     {  
  67.         private string _name;  
  68.         private string _doSomething;  
  69.         private Boss _boss;  
  70.   
  71.         public string Name  
  72.         {  
  73.             get { return _name; }  
  74.             set { _name = value; }  
  75.         }  
  76.         public string DoSomething  
  77.         {  
  78.             get { return _doSomething; }  
  79.             set { _doSomething = value; }  
  80.         }  
  81.         public EmployeeA(Boss boss)  
  82.         {  
  83.             _boss = boss;  
  84.         }  
  85.         public override void OnNotify()  
  86.         {  
  87.             if (_boss.Command == "下达命令")  
  88.             {  
  89.                 Debug.Log("我是" + _name + "我要" + DoSomething);  
  90.             }  
  91.         }  
  92.     }  
  93.   
  94.     public class EmployeeB : Observer  
  95.     {  
  96.         private string _name;  
  97.         private string _doSomething;  
  98.         private Boss _boss;  
  99.   
  100.         public string Name  
  101.         {  
  102.             get { return _name; }  
  103.             set { _name = value; }  
  104.         }  
  105.         public string DoSomething  
  106.         {  
  107.             get { return _doSomething; }  
  108.             set { _doSomething = value; }  
  109.         }  
  110.         public EmployeeB(Boss boss)  
  111.         {  
  112.             _boss = boss;  
  113.         }  
  114.         public override void OnNotify()  
  115.         {  
  116.             if (_boss.Command == "下达命令")  
  117.             {  
  118.                 Debug.Log("我是" + _name + "我要" + DoSomething);  
  119.             }  
  120.         }  
  121.     }  
  122.   
  123.     public class EmployeeC : Observer  
  124.     {  
  125.         private string _name;  
  126.         private string _doSomething;  
  127.         private Boss _boss;  
  128.   
  129.         public string Name  
  130.         {  
  131.             get { return _name; }  
  132.             set { _name = value; }  
  133.         }  
  134.         public string DoSomething  
  135.         {  
  136.             get { return _doSomething; }  
  137.             set { _doSomething = value; }  
  138.         }  
  139.         public EmployeeC(Boss boss)  
  140.         {  
  141.             _boss = boss;  
  142.         }  
  143.         public override void OnNotify()  
  144.         {  
  145.             if (_boss.Command == "下达命令")  
  146.             {  
  147.                 Debug.Log("我是" + _name + "我要" + DoSomething);  
  148.             }  
  149.         }  
  150.     }  
  151.   
  152.     void Start()  
  153.     {  
  154.         Boss boss = new Boss();  
  155.         EmployeeA employeeA = new EmployeeA(boss);  
  156.         EmployeeA employeeB = new EmployeeA(boss);  
  157.         EmployeeA employeeC = new EmployeeA(boss);  
  158.   
  159.         employeeA.Name = "雇员A";  
  160.         employeeA.DoSomething = "打扫卫生";  
  161.         employeeB.Name = "雇员B";  
  162.         employeeB.DoSomething = "整理货物";  
  163.         employeeC.Name = "雇员C";  
  164.         employeeC.DoSomething = "清算账目";  
  165.   
  166.         boss.AddObserver(employeeA);  
  167.         boss.AddObserver(employeeB);  
  168.         boss.AddObserver(employeeC);  
  169.   
  170.         boss.Command = "下达命令";  
  171.         boss.Notify();  
  172.     }  
  173.   
  174. }  

        其实观察者模式可以这么理解,我们不妨把它看做是一个超市,具体观察者是超市的老板,老板要下达命令给员工,具体主题是超市的员工,员工收到了老板下达的命令就开始工作了,抽象主题就是一个任务表,任务表中包含所需要工作员工的名单,我们要告诉名单中的员工你别偷懒了,开始干活吧,抽象观察者就是一个工作的大致内容,例如:年底盘查,但是我们不去关心年底盘查具体的步骤该怎么做,怎么做的事情由员工自己来负责。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值