Միջնորդ (նախագծման ձևանմուշ)

Միջնորդ (անգլ.՝ Mediator pattern), վարքագծային նախագծման ձևանմուշ, որը որոշում է թե օբյեկտները միմյանց հետ ինչպես պետք է փոխհամագործակցեն։ Ձևանմուշը վարքագծային է համարվում նրանով, քանի որ այն կարող է փոփոխել ծրագրերի թողարկման վարքը։

Միջնորդ
ՏեսակՎարքագծային
Նշանակությունդասերի միմյանց հետ փոխկապակցում է միջնորդ օբյեկտի օգնությամբ
Նկարագրությունը ԳօՖի
"Design Patterns" գրքում
Այո

Սովորաբար ծրագիրը բաղկացած է մեծ թվով դասերից։ Այյպիով տրամաբանությունը և հաշվարկը բաժանվում են այդ դասերի միջև։ Քանի որ ծրագրում մեծ թվով դասեր կան, դրանց տեխնիկական սպասարկումը և դասերի միջև փոխկապակցվածություն ապահովելը դառնում է բարդ։ Արդյունքում դա ծրագիրը դարձնում է դժվար ընթերցվող և սպասարկվող։ Բացի այդ դա բերում է նրան, որ դժվար է դառնում փոխել ծրագիրը, քանի որ ցանկացած փոփոխություն կարող է ազդել մի քանի դասերի վրա։

Միջնորդ ձևանմուշը օբյեկտների միջև կապ է ստեղծում միջնորդ օբյեկտի միջոցով։ Այսպիսով դասի օբյեկտները միմյանց հետ չեն կապվում անմիջականորեն, այլ կապվում եմ միջնորդի օգնությամբ։ Դա թույլացնում է օբյեկտների միջև կապվածությունը և թուլացնում է կապվածության գործակիցը։

Օրինակներ

խմբագրել
#include <iostream>
#include <string>
 
class Colleague;
class Mediator;
class ConcreteMediator;
class ConcreteColleague1;
class ConcreteColleague2;
 
class Mediator
{
public:
 virtual void Send(std::string const& message, Colleague *colleague) const = 0;
};
 
class Colleague
{
protected:
 Mediator* mediator_;

public:
 explicit Colleague(Mediator *mediator):mediator_(mediator)
 {
 }
};
 
class ConcreteColleague1:public Colleague
{
public:
 explicit ConcreteColleague1(Mediator* mediator):Colleague(mediator)
 {
 }
 
 void Send(std::string const& message)
 {
 mediator_->Send(message, this);
 }
 
 void Notify(std::string const& message)
 {
 std::cout << "Colleague1 gets message '" << message << "'" << std::endl;
 }
};
 
class ConcreteColleague2:public Colleague
{
public:
 explicit ConcreteColleague2(Mediator *mediator):Colleague(mediator)
 {
 }
 
 void Send(std::string const& message)
 {
 mediator_->Send(message, this);
 }
 
 void Notify(std::string const& message)
 {
 std::cout << "Colleague2 gets message '" << message << "'" << std::endl;
 }
};
 
class ConcreteMediator:public Mediator
{
protected:
 ConcreteColleague1 *m_Colleague1;
 ConcreteColleague2 *m_Colleague2;
public:
 void SetColleague1(ConcreteColleague1 *c)
 {
 m_Colleague1=c;
 }
 
 void SetColleague2(ConcreteColleague2 *c)
 {
 m_Colleague2=c;
 }
 
 virtual void Send(std::string const& message, Colleague *colleague) const
 {
 if (colleague==m_Colleague1)
 {
 m_Colleague2->Notify(message);
 }
 else if (colleague==m_Colleague2)
 {
 m_Colleague1->Notify(message);
 }
 }
};
 
int main()
{
 ConcreteMediator m;
 
 ConcreteColleague1 c1(&m);
 ConcreteColleague2 c2(&m);
 
 m.SetColleague1(&c1);
 m.SetColleague2(&c2);
 
 c1.Send("How are you?");
 c2.Send("Fine, thanks");
 
 std::cin.get();
 return 0;
}

Output
Colleague2 gets message 'How are you?'
Colleague1 gets message 'Fine, thanks'
// Mediator pattern — Structural example
using System;

namespace DoFactory.GangOfFour.Mediator.Structural
{
    /// <summary>
    /// MainApp startup class for Structural
    /// Mediator Design Pattern.
    /// </summary>
    class MainApp
    {
        /// <summary>
        /// Entry point into console application.
        /// </summary>
        static void Main()
        {
            ConcreteMediator m = new ConcreteMediator();

            ConcreteColleague1 c1 = new ConcreteColleague1(m);
            ConcreteColleague2 c2 = new ConcreteColleague2(m);

            m.Colleague1 = c1;
            m.Colleague2 = c2;

            c1.Send("How are you?");
            c2.Send("Fine, thanks");

            // Wait for user
            Console.ReadKey();
        }
    }

    /// <summary>
    /// The 'Mediator' abstract class
    /// </summary>
    abstract class Mediator
    {
        public abstract void Send(string message, Colleague colleague);
    }

    /// <summary>
    /// The 'ConcreteMediator' class
    /// </summary>
    class ConcreteMediator : Mediator
    {
        public ConcreteColleague1 Colleague1 { private get; set; }

        public ConcreteColleague2 Colleague2 { private get; set; }

        public override void Send(string message, Colleague colleague)
        {
            if (colleague == Colleague1)
            {
                Colleague2.Notify(message);
            }
            else
            {
                Colleague1.Notify(message);
            }
        }
    }

    /// <summary>
    /// The 'Colleague' abstract class
    /// </summary>
    abstract class Colleague
    {
        protected Mediator mediator;

        // Constructor
        public Colleague(Mediator mediator)
        {
            this.mediator = mediator;
        }
    }

    /// <summary>
    /// A 'ConcreteColleague' class
    /// </summary>
    class ConcreteColleague1 : Colleague
    {
        // Constructor
        public ConcreteColleague1(Mediator mediator)
        : base(mediator)
        {
        }

        public void Send(string message)
        {
            mediator.Send(message, this);
        }

        public void Notify(string message)
        {
            Console.WriteLine("Colleague1 gets message: " + message);
        }
    }

    /// <summary>
    /// A 'ConcreteColleague' class
    /// </summary>
    class ConcreteColleague2 : Colleague
    {
        // Constructor
        public ConcreteColleague2(Mediator mediator)
        : base(mediator)
        {
        }

        public void Send(string message)
        {
            mediator.Send(message, this);
        }

        public void Notify(string message)
        {
            Console.WriteLine("Colleague2 gets message: " + message);
        }
    }
}

Output
Colleague2 gets message: How are you?
Colleague1 gets message: Fine, thanks