Unity开发常用设计模式(初级)

Posted 六大米nb

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Unity开发常用设计模式(初级)相关的知识,希望对你有一定的参考价值。

单例模式

单例模式比较简单

以下代码重点演示单例的会是同一个地址,返回同一个哈希值

using System.Collections;
using System.Collections.Generic;
using UnityEngine;


public class MySingleton

private static MySingleton instance;

public static MySingleton Instance

get

if (instance == null)
instance = new MySingleton();
return instance;



private MySingleton()

Debug.Log("构造函数执行");


public void Show()

Debug.Log("Show");



public class DesignPattern : MonoBehaviour

// Start is called before the first frame update
void Start()

MySingleton single1 = MySingleton.Instance;
single1.Show();
Debug.Log(single1.GetHashCode());

MySingleton single2 = MySingleton.Instance;
single2.Show();
Debug.Log(single2.GetHashCode());

MySingleton single3 = MySingleton.Instance;
single3.Show();
Debug.Log(single3.GetHashCode());
//以上这三个对象指向同一个地址



观察者模式

代码示例:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System;

//这里介绍观察者模式
//例子是:猫来了,所有的老鼠开始逃跑

public class Animal

protected string strName;

public Animal(string name)

this.strName = name;


public virtual void Run()





public class Cat: Animal

public Action action;//发布者
public Cat(string name):base(name)//构造函数



public void Coming(/*Animal mouseA, Animal mouseB, Animal mouseC*/)

Debug.Log(strName + "来了");
//mouseA.Run();
//mouseB.Run();
//mouseC.Run();
//在没有观察者模式的时候需要挨个调用

if (action != null)
action();//触发事件;通过多播委托完成一对多的关系

this.Run();


public override void Run()//函数的重载

Debug.Log(strName + "开始追");



public class Mouse: Animal

public Mouse(string name, Cat cat):base(name)

cat.action += this.Run;//订阅者


public override void Run()//事件处理器

Debug.Log( strName + "开始逃跑");



public class ObserverPattern : MonoBehaviour

// Start is called before the first frame update
void Start()

Cat cat = new Cat("小野猫");

Animal mouseA = new Mouse("mouseA", cat);
Animal mouseB = new Mouse("mouseB", cat);
Animal mouseC = new Mouse("mouseC", cat);
Animal mouseD = new Mouse("mouseD", cat);

//cat.Coming(mouseA, mouseB, mouseC);
cat.Coming();


运行结果:

Unity开发常用设计模式(初级)_游戏开发

以下代码展示观察者模式和非观察者模式的写法差异

//普通写法
//缺点在于如果后续需要新增相应的对象,那么每次都需要在cat的函数中手动新增响应对象
public class Cat: Animal

public Cat(string name):base(name)//构造函数



public void Coming(Animal mouseA, Animal mouseB, Animal mouseC)

Debug.Log(strName + "来了");
mouseA.Run();
mouseB.Run();
mouseC.Run();
this.Run();


public override void Run()//函数的重载

Debug.Log(strName + "开始追");



//观察者模式的写法
public class Cat: Animal

public Action action;
public Cat(string name):base(name)//构造函数



public void Coming(Animal mouseA, Animal mouseB, Animal mouseC)

Debug.Log(strName + "来了");
if(action!= null)
action();//在Mouse的构造函数中将其Run方法注册给这个cat的
this.Run();


public override void Run()//函数的重载

Debug.Log(strName + "开始追");



public class Mouse: Animal

public Mouse(string name, Cat cat):base(name)

cat.action += this.Run;//订阅者


public override void Run()//事件处理器

Debug.Log( strName + "开始逃跑");



工厂家族

简单工厂模式

关键词:创建型模式,本质上是一种静态工厂方法模式(Static Factory Method)

主要思想:

Unity开发常用设计模式(初级)_unity_02

我们创建了两个脚本,包含四个类:

  • MouseProduct:父类,还有两个品牌的子类Dell和HP
  • MainFactory:一个MainFactory类+一个SimpleFactory类,SimpleFactory类在MainFactory中进行调用;其中SimpleFactory类中还用到了一个枚举

MouseProduct脚本:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

namespace MouseManufactoring

public abstract class MouseProduct

public abstract void Print();


public class DellMouse : MouseProduct

public override void Print()

Debug.Log("生产了一个戴尔鼠标");



public class HpMouse : MouseProduct

public override void Print()

Debug.Log("生产了一个HP鼠标");



MainFactory脚本:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using MouseManufactoring;

public enum MouseType DellMouse, HpMouse,;

public class MainFactory : MonoBehaviour

void Start()

RunFactoryMode();


public void RunNormal()

DellMouse dellMouse = new DellMouse();
dellMouse.Print();

HpMouse hpMouse = new HpMouse();
hpMouse.Print();


public void RunFactoryMode()

SimpleFactory simpleFactory = new SimpleFactory();//将简单工厂实例化

simpleFactory.CreateMouse(MouseType.DellMouse).Print();
simpleFactory.CreateMouse(MouseType.HpMouse).Print();





public class SimpleFactory

public MouseProduct CreateMouse(MouseType type)

MouseProduct mouse = null;
switch (type)

case MouseType.DellMouse:
mouse = new DellMouse();
break;
case MouseType.HpMouse:
mouse = new HpMouse();
break;


return mouse;

也可以做如下改造使得可以控制生产的品牌:

public enum MouseType  DellMouse, HpMouse,;

public class MainFactory : MonoBehaviour

public MouseType brand;
void Start()

RunFactoryMode(brand);


public void RunNormal()

DellMouse dellMouse = new DellMouse();
dellMouse.Print();

HpMouse hpMouse = new HpMouse();
hpMouse.Print();


public void RunFactoryMode(MouseType type)

SimpleFactory simpleFactory = new SimpleFactory();//将简单工厂实例化

simpleFactory.CreateMouse(type).Print();

缺陷:简单工厂模式如果需要再增加一个产品,需要新建一个类、枚举,并且需要修改CreateMouse的方法,违背了开闭原则。


工厂模式

关键词:解决简单工厂模式中,新增产品品牌的时候,需要直接修改工厂类的问题。

解决了简单工厂模式中出现的开闭原则问题,一个中间件只能生产一种产品。以下展示了简单工厂和工厂模式的区别。

Unity开发常用设计模式(初级)_中间件_03

本次我们创建了3个脚本:

  • 产品脚本:由一个抽象类和其子类组成,子类分别代表不同的品牌,包含各自的Print函数
  • 中间件脚本:由一个抽象类和其子类组成,子类分别代表不同品牌的工厂,包含各自的生产函数
  • 主要工厂脚本:挂载在游戏物体上,在Start中调用一个运行方法

产品脚本:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

namespace FactoryPattern

public abstract class PorductFactoryPattern

public abstract void Print();


public class DellMouse: PorductFactoryPattern

public override void Print()

Debug.Log("生产了一个Dell鼠标");



public class HPMouse : PorductFactoryPattern

public override void Print()

Debug.Log("生产了一个HP鼠标");


中间件脚本:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using FactoryPattern;
public abstract class MidBase

public abstract PorductFactoryPattern CreateMouse();


public class DellFactoryMid: MidBase//Dell中间件

public override PorductFactoryPattern CreateMouse()

return new DellMouse();



public class HPFactoryMid: MidBase//HP中间件

public override PorductFactoryPattern CreateMouse()

return new HPMouse();

主要工厂脚本:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using FactoryPattern;

public class MainFactoryPattern : MonoBehaviour

void Start()

RunFactoryMode();


public void RunNormal()//普通模式的运行方法

DellMouse dellMouse = new DellMouse();
dellMouse.Print();

HPMouse hpMouse = new HPMouse();
hpMouse.Print();


public void RunFactoryMode(MouseType type)//简单工厂模式的运行方法

SimpleFactory simpleFactory = new SimpleFactory();//将简单工厂实例化

simpleFactory.CreateMouse(type).Print();


public void RunFactoryMode()

DellFactoryMid dellFactoryMid = new DellFactoryMid();
dellFactoryMid.CreateMouse().Print();

HPFactoryMid hpFactoryMid = new HPFactoryMid();
hpFactoryMid.CreateMouse().Print();


抽象工厂模式

关键词:解决生产系列产品的问题,比如我们不只是生产鼠标,我们还生产键盘

具体的脚本构成:

鼠标脚本:鼠标抽象父类+鼠标子类

键盘脚本:键盘抽象父类+键盘子类

中间件脚本:中间件抽象父类+中间件子类(生成鼠标和键盘)

主要工厂脚本:Start中调用运行方法


适配器模式(Adapter Pattern)

Unity开发常用设计模式(初级)_unity_04

脚本构成:

具体数据线脚本:可以用抽象父类,也可以不用

适配器脚本:根据枚举判断不同的类型调用各自的方法

主要调用脚本:在Start中进行调用


具体数据线脚本:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

namespace AdapterPattern

public abstract class Lines

public abstract void Charge();


public class androidLine: Lines

public override void Charge()

Debug.Log("这是安卓充电线在充电中……");



public class iosLine: Lines

public override void Charge()

Debug.Log("这是苹果充电线在充电中……");


适配器脚本:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using AdapterPattern;

public interface IAdapter

void Charge(LineType type);


public enum LineType None, ios, android, ;

public class Adapter: IAdapter

AndroidLine androidLine = new AndroidLine();
IOSLine iOSLine = new IOSLine();
public void Charge(LineType type)

if (type == LineType.ios)

iOSLine.Charge();

else if (type == LineType.android)

androidLine.Charge();


主要调用脚本:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using AdapterPattern;

public class MainAdapter : MonoBehaviour

public LineType type;
// Start is called before the first frame update
void Start()

Adapter adapter = new Adapter();
//IAdapter adapter = new Adapter();
//这里这种写法也是可以的,还没有弄懂为什么,记个Todo
adapter.Charge(type);


以上是关于Unity开发常用设计模式(初级)的主要内容,如果未能解决你的问题,请参考以下文章

如何理解Unity组件化开发模式

unity怎么给物体上颜色

unity中怎样用代码获取物体组件中的相关属性

unity怎么设置物体坐标?

Unity3D - UGUI的初级应用

unity获取物件组件常用方法总结