Паттерн “Посредник” (Mediator1 )
Содержание
Введение Необходимость паттерна “Посредник” возникает
- Когда нужно реализовать взаимодействие между объектами, которые не должны знать о существовании друг друга.
Существует 2 основных варианта этого паттерна:
Взаимодействующие объекты знают о медиаторе, медиатор может знать или не знать о медиаторе.
Медиатор знает о существовании всех объектов, объекты ничего не знают.
Ниже представлена UML-диаграмма данного паттерна.
Синхронизация информации между агентами.
В данном примере воспользуемся паттерном “Медиатор” для синхронизации информации между агентами. Реализуем самый простой вариант этого паттерна, когда объекты и медиатор знают друг о друге.
**C#**
Класс-агент. Ему известно о медиаторе _hq
.
class Agent
{
private List<string> _intel = new List<string>();
private Hq _hq;
private readonly string _name;
private string GetGeneratedIntel()
{
return $"Secret intel: {Guid.NewGuid().GetHashCode()}";
}
public void RecieveIntel(string intel)
{
_intel.Add(intel);
}
public void SyncIntel()
{
var intel = GetGeneratedIntel();
_intel.Add(intel);
_hq.SendIntelToAllAgents(this, intel);
}
public string GetTotalIntel()
{
return $"{_name}\n{_intel.Aggregate((f,s)=> $"{f}\n{s}")}";
}
public Agent(Hq hq, string name)
{
_name = name;
_hq = hq;
}
}
Класс-медиатор. Он знает обо всех агентах и синхронизирует их состояние. Агенты, однако, не знают друг о друге.
class Hq
{
private List<Agent> _agents = new List<Agent>();
public Hq()
{
_agents.AddRange(
new List<Agent>()
{
new Agent(this, "Joe"),
new Agent(this, "Smith"),
new Agent(this, "Roberto"),
new Agent(this, "Cherry"),
new Agent(this, "Razor"),
new Agent(this, "Blade"),
new Agent(this, "Gustav"),
new Agent(this, "Petya")
}
);
}
public void SendIntelToAllAgents(Agent sender, string intel)
{
foreach(var agent in _agents.Where(a=> a!= sender))
{
agent.RecieveIntel(intel);
}
}
public void CheckAgents()
{
foreach (var agent in _agents)
{
agent.SyncIntel();
}
}
public string GetTotalIntel()
{
return _agents.Select(a => a.GetTotalIntel()).Aggregate((f, s) => $"{f}\n{s}");
}
}
Используем реализованную функциональность.
class Program
{
static void Main(string[] args)
{
var hq = new Hq()
for (var i = 0; i < 10; i++)
{
hq.CheckAgents();
}
Console.WriteLine(hq.GetTotalIntel());
}
}
Весь код использованный в проекте доступен на GitHub .
Литература
[1]: Mediator pattern from Wiki [2]: Тепляков С. Паттерны проектирования на платформе .NET – СПб.: Питер, 2015. — 57-68 c. [3]: Design Patterns: Elements of Reusable Object-Oriented Software