
الگوی طراحـــــــــی Decorator
الگوی طراحی Decorator یکی از الگوهای ساختاری (Structural Patterns) است که هدف آن افزودن ویژگیها به یک شیء به صورت پویا و بدون نیاز به تغییر در کد اصلی است. با استفاده از این الگو، میتوانیم برخی از ویژگیها یا عملیاتها را به یک شیء اضافه کنیم، بدون اینکه باید آن شیء را تغییر دهیم یا از زیرکلاسها استفاده کنیم.
برای درک بهتر الگوی Decorator، بهتر است یک مثال کاربردی در دنیای واقعی را در نظر بگیریم. فرض کنید شما یک سیستم مدیریت کاربران دارید که از طریق وب درخواستها را مدیریت میکند. همچنین، میخواهید برخی از کارها را لاگ کنید تا بتوانید بهبودهای لازم را انجام دهید. در این مثال، ما از الگوی Decorator برای افزودن قابلیت لاگ کردن به سیستم کاربران استفاده میکنیم.
برای درک بهتر این الگو، با یک مثال ملموس و کاربردی در دنیای واقعی آشنا میشویم:
1. Component (اجزا): اینجا کلاس `UserService` را تعریف میکنیم که وظیفه مدیریت کاربران را بر عهده دارد.
1public interface IUserService
2{
3 User GetUserById(int userId);
4 void AddUser(User user);
5 void UpdateUser(User user);
6 void DeleteUser(int userId);
7}
2. ConcreteComponent (اجزای اصلی): اینجا کلاس `UserServiceImpl` را تعریف میکنیم که از `IUserService` ارثبری کردهاست و وظیفههای مدیریت کاربران را پیادهسازی میکند.
1public class UserServiceImpl : IUserService
2{
3 private Dictionary<int, User> users;
4
5 public UserServiceImpl()
6 {
7 users = new Dictionary<int, User>();
8 }
9
10 public User GetUserById(int userId)
11 {
12 return users.ContainsKey(userId) ? users[userId] : null;
13 }
14
15 public void AddUser(User user)
16 {
17 users[user.Id] = user;
18 }
19
20 public void UpdateUser(User user)
21 {
22 if (users.ContainsKey(user.Id))
23 {
24 users[user.Id] = user;
25 }
26 }
27
28 public void DeleteUser(int userId)
29 {
30 users.Remove(userId);
31 }
32}
3. Decorator (تزئینکننده): اینجا کلاس `LoggingUserService` را تعریف میکنیم که از `IUserService` ارثبری کردهاست و به عنوان تزئینکننده، ویژگی لاگ کردن را به سرویس مدیریت کاربران اضافه میکند.
1public class LoggingUserService : IUserService
2{
3 private IUserService userService;
4
5 public LoggingUserService(IUserService userService)
6 {
7 this.userService = userService;
8 }
9
10 public User GetUserById(int userId)
11 {
12 Log("GetUserById");
13 return userService.GetUserById(userId);
14 }
15
16 public void AddUser(User user)
17 {
18 Log("AddUser");
19 userService.AddUser(user);
20 }
21
22 public void UpdateUser(User user)
23 {
24 Log("UpdateUser");
25 userService.UpdateUser(user);
26 }
27
28 public void DeleteUser(int userId)
29 {
30 Log("DeleteUser");
31 userService.DeleteUser(userId);
32 }
33
34 private void Log(string action)
35 {
36 Console.WriteLine($"Logging: User Service - {action}");
37 }
38}
4. Client (کلاینت): اینجا برنامهای را با توجه به الگوی Decorator ایجاد میکنیم و امکان مدیریت کاربران با ویژگی لاگ کردن را به کاربر میدهیم.
1public class Program
2{
3 public static void Main()
4 {
5 // ایجاد سرویس اصلی
6 IUserService userService = new UserServiceImpl();
7
8 // ایجاد سرویس با قابلیت لاگ کردن
9 IUserService loggingUserService = new LoggingUserService(userService);
10
11 // مدیریت کاربران با ویژگی لاگ کردن
12 loggingUserService.AddUser(new User(1, "John"));
13 loggingUserService.UpdateUser(new User(1, "John Doe"));
14 loggingUserService.DeleteUser(1);
15 }
16}
خروجی برنامه به صورت زیر خواهد بود:
Logging: User Service - AddUser
Logging: User Service - UpdateUser
Logging: User Service - DeleteUser
در این مثال با استفاده از الگوی Decorator، توانستیم ویژگی لاگ کردن را به سیستم مدیریت کاربران اضافه کنیم بدون اینکه بخواهیم کد اصلی را تغییر دهیم. این الگو به ما امکان افزودن ویژگیهای جدید به یک شیء به صورت پویا را میدهد و کد را قابل خواندن و تعمیر میکند.