Стратег (Strategy) нь тус тусдаа хайрцаглагдан тэдгээрийн бие биеэ орлолтыг хангасан алгоритмын багцыг тодорхойлох загварчлалын хэвийг илэрхийлнэ. Нөхцөл байдлаас шалтгаалан ашиглагдаж буй алгоритмыг тухайн алгоритмыг хэрэглэж байгаа обьектоос хамааралгүйгээр өөрөөр амархан сольж болдог.
Хэвийг хаана ашиглах
- Төлөв байдлаараа ялгаатай нэг төрлийн хэдэн классууд байх үед нэг үндсэн классыг өгөөд төлөв байдлын өөр хувилбаруудыг тусдаа классуудад гаргаад шаардлагатай үед тэдгээрийг хэрэглэх.
- Нөхцлөөс хамааран алгоритмын хувилбаруудаас амархан сонголт хийх боломжийг хангах хэрэгтэй үед.
- Програм ажиллах явцдаа обьектуудын төлөв байдлыг өөрчлөх шаардлагатай үед
- Тодорхой ажиллагааг ашиглаж буй класс түүний хэрэгжүүлэлтийн талаар юуг ч мэдэх ёсгүй үед
Стратег хэвийг UML дээр дараах схемээр илэрхийлж болно.
Хэвийн бүтцийг C# хэл дээр дараах байдлаар тодорхойлно.
public interface IStrategy
{
void Algorithm();
}
public class ConcreteStrategy1 : IStrategy
{
public void Algorithm()
{}
}
public class ConcreteStrategy2 : IStrategy
{
public void Algorithm()
{}
}
public class Context
{
public IStrategy ContextStrategy { get; set; }
public Context(IStrategy _strategy)
{
ContextStrategy = _strategy;
}
public void ExecuteAlgorithm()
{
ContextStrategy.Algorithm();
}
}
Оролцогчид
- Algorithm() аргыг тодорхойлсон IStrategy интерфейс. Энэ бол алгоритмын бүх хэрэгжүүлэгчдийн ерөнхий интерфейс. Интерфейсийн оронд энд абстракт классыг ашиглаж болно.
- IStrategy интерфейсийг хэрэгжүүлэх ConcreteStrategy1, ConcreteStrategy2 классууд өөрийн Algorithm() аргуудыг санал болгоно. Ийм төрлийн хэрэгжүүлэгч классууд олон байж болно.
- Context класс IStrategy обьектын холбоосыг хадгалах бөгөөд IStrategy интерфейстэй агрегац харьцаагаар холбогдоно.
Тодорхойлолтод IStrategy обьектыг ContextStrategy шинжид авсан байгаа ч түүнд дотоод /private/ хувьсагч тодорхойлсон ч болно. Харин обьетыг динамикаар тогтоох бол тусгай арга ашиглана.
Одоо жишээ авч үзье. Цахилгаан, бензин, хий гэх мэтээр түлшний төрөл бүрийн эх үүсвэртэй суудлын машинууд байдаг. Бүр хосолсон түлштэй ч бий. Ерөнхийдөө бол машинууд төстэй ч голдуу түлшний эх үүсвэрээрээ ялгаатай байдаг. Энэ тохиолдолд стратег хэвийг ашиглах бүрэн боломжтой.
class Program
{
static void Main(string[] args)
{
Car auto = new Car(4, "Volvo", new PetrolMove());
auto.Move();
auto.Movable = new ElectricMove();
auto.Move();
Console.ReadLine();
}
}
interface IMovable
{
void Move();
}
class PetrolMove : IMovable
{
public void Move()
{
Console.WriteLine("Бензинээр явдаг");
}
}
class ElectricMove : IMovable
{
public void Move()
{
Console.WriteLine("Цахилгаанаар явдаг");
}
}
class Car
{
protected int passengers; // зорчигчийн тоо
protected string model; // машины марк, загвар
public Car(int num, string model, IMovable mov)
{
this.passengers = num;
this.model = model;
Movable = mov;
}
public IMovable Movable { private get; set; }
public void Move()
{
Movable.Move();
}
}
Програмыг ажлуулбал
үр дүнг авна.
Жишээнд IStrategy -ийн үүргийг Move() аргыг тодорхойлсон IMovable интерфейс гүйцэтгэн харин интерфейсийг хэрэгжүүлэгч алгоритмуудын бүлгийг ElectricMove, PetroleMove классууд илэрхийлнэ. Алгоритмыг Car класс ашиглана.
Хэвүүд эхэндээ ойлгомж муутай тул нэмэлт материалуудыг судлан практик дадлагыг сайн хийхийг зөвлөе.