享元模式

模式定义

享元模式(Flyweight Pattern):运用共享技术有效地支持大量细粒度对象的复用。系统只使用少量的对象,而这些对象都很相似,状态变化很小,可以实现对象的多次复用。
目的:解决多次创建(大)对象引起的性能问题。

术语

  1. 内部状态:存储在享元对象内部并且不会随环境改变而改变的状态,因此内部状态可以共享。
  2. 外部状态是随环境改变而改变的、不可以共享的状态。
    享元对象的外部状态必须由客户端保存,并在享元对象被创建之后,在需要使用的时候再传入到享元对象内部。

UML类图

  • 抽象享元类 Flyweight 享元类接口,通过它可以接受并作用于外部状态
  • 具体享元类 ConcreteFlyweight 实现了抽象享元接口,实例称为享元对象(被多次复用的对象,客户端通过享元工厂创建);
  • 非共享具体享元类 UnsharedConcreteFlyweight 不能被共享的抽象享元类的子类(客户端直接new该对象)
  • 享元工厂类 FlyweightFactory 用于创建并管理享元对象,它针对抽象享元类编程,将各种类型的具体享元对象存储在一个享元池中。
    根据业务直接从享元池中获取享元类对象,或创建新的享元类添加到享元池

代码结构

public static class FlyweightApp
	{
		public static void Run()
		{
			int extrinsicstate = 22;

			FlyweightFactory factory = new FlyweightFactory();

			// Work with different flyweight instances

			Flyweight fx = factory.GetFlyweight("X");
			fx.Operation(--extrinsicstate);

			Flyweight fy = factory.GetFlyweight("Y");
			fy.Operation(--extrinsicstate);

			Flyweight fz = factory.GetFlyweight("Y");
			fz.Operation(--extrinsicstate);

			UnsharedConcreteFlyweight fu = new UnsharedConcreteFlyweight();

			fu.Operation(--extrinsicstate);
		}
	}

	public abstract class Flyweight
	{
		public abstract void Operation(int extrinsicstate);
	}
	public class ConcreteFlyweight : Flyweight
	{
		public override void Operation(int extrinsicstate)
		{
			Console.WriteLine("ConcreteFlyweight: " + extrinsicstate);
		}
	}
	public class UnsharedConcreteFlyweight : Flyweight
	{
		public override void Operation(int extrinsicstate)
		{
			Console.WriteLine("Unshared ConcreteFlyweight: " + extrinsicstate);
		}
	}

	public class FlyweightFactory
	{
		private Hashtable flyweights = new Hashtable();

		public FlyweightFactory()
		{
			flyweights.Add("X", new ConcreteFlyweight());
			flyweights.Add("Y", new ConcreteFlyweight());
			flyweights.Add("Z", new ConcreteFlyweight());
		}
		public Flyweight GetFlyweight(string key)
		{
			return ((Flyweight)flyweights[key]);
		}
	}

情景模式

一服装店聘请一个男模和一个女模试穿衣服(请多了服装店付不起钱),但是有很多衣服需要试穿。

public static class FlyweightApp
	{
		public static void Run()
		{
			List<string> maleCloths = new List<string>() { "男鞋", "短裤", "衬衫" };
			List<string> femaleCloths = new List<string>() { "超短裤", "齐逼小短裙", "肉色袜裤" };

			ModelFactory modelFactory = new ModelFactory();
			Model male = modelFactory.GetFlyweight(Gender.male);
			Model female = modelFactory.GetFlyweight(Gender.female);

			foreach (string item in maleCloths)
			{
				male.Display(item);
			}

			foreach (string item in femaleCloths)
			{
				female.Display(item);
			}


		}
	}
	public enum Gender
	{
		male, female
	}

	public abstract class Model
	{
		public abstract void Display(string cloth);
	}
	public class MaleModel : Model
	{
		public override void Display(string cloth)
		{
			Console.WriteLine("我是帅气的男模,我穿的是{0}", cloth);
		}
	}
	public class FemaleModel : Model
	{
		public override void Display(string cloth)
		{
			Console.WriteLine("我是骚气的女模,我穿的是{0}", cloth);
		}
	}

	public class ModelFactory
	{
		private Hashtable flyweights = new Hashtable();

		public ModelFactory()
		{
			flyweights.Add(Gender.male, new MaleModel());
			flyweights.Add(Gender.female, new MaleModel());
		}
		public Model GetFlyweight(Gender key)
		{
			return ((Model)flyweights[key]);
		}
	}
原文地址:https://www.cnblogs.com/LoveTomato/p/8386554.html