Skip to content

Latest commit

 

History

History

Folders and files

NameName
Last commit message
Last commit date

parent directory

..
 
 
 
 
 
 
 
 

هدف

درخواست را به عنوان یک شیء کپسوله می‌کند، از این رو اجازه می‌دهد تا بتوانید کارخوه‌ها را با درخواست‌ها، صف‌ها و یا لاگ‌های متفاوت پارامتری کنید.

ساختار

Class Digaram

Class Digaram

Sequence Diagram

Sequence Diagram

نکات طراحی

  • کپسوله کردن درخواست‌ها
  • پارامتری کردن کلاینت به طوری که بتواند درخواست‌های متفاوتی را دریافت کند. برای مثال پیشخدمت در طول روز درخواست‌های متفاوتی را دریافت می‌کند و یا در مثال ریموت کنترل، کنترلر می‌تواند درخواست‌های متفاوتی را دریافت کند.

از این الگو زمانی استفاده کنید که

  • نیاز به پشتیبانی از گزارش‌نویسی (logging) دارید.
  • لازم است تاریخچه را مدیریت کنید. (مثل عملیات undo/redo)
  • نیاز است تا از تراکنش‌ها پشتیبانی کنید.
  • نیاز به callback دارید.
  • نیاز است تا درخواست‌ها در زمان‌های متفاوت و یا در ترتیب‌های متفاوت (صف، پشته و ...) هندل شوند.
  • منبع درخواست باید از شیء‌ای که واقعاً درخواست را هندل می‌کند، جدا (دیکوپلینگ) شوند.

اجزاء الگو

  • Command: رابطی برای اجرای عملیات بیان می‌کند.
  • ConcreteCommand
  • Client: اشیاء ConcreteCommand را می‌سازد و receiverهای آن‌ها را تنظیم می‌کند.
  • Invoker: از Command می‌خواهد که درخواست‌اش را حمل کند.
  • Receiver

کاربردها

  1. Thread pools: رجوع شود به java.lang.Runnable
  2. Transactional behavior: قابل برگشت بودن عملیات
  3. Wizards: به تأخیر انداختن عملیات
  4. Macro Recording: می‌توانیم عملیات متفاوت و پشت سرهم را ضبط کنیم و سپس یکباره آن‌ها را اجرا کنیم. مثل ماکروها در ویرایشگرهای vim و Emacs و یا ماکروهای IDEها.
  5. Multi-level undo: چون عملیات به صورت شیء در پشته ذخیره می‌شود هر گاه کاربر بخواهد به اندازهٔ چند مرحله Undo کند، به راحتی با pop کردن اشیاء از پشته و اجرای عملیات undo امکان‌پذیر است.
  6. Job queue: تمامی اشیاء command را وارد صف می‌کنیم و هر کدام را از صف خارج کرده و یک نخ به آن‌ها اختصاص می‌دهیم تا کار آن‌ها تمام شود.

Null Object

اگر برای اسلاتی هیچ عملیاتی در نظر نداشته باشیم، می‌توانیم یک شیء Null به نام NoCommand درست کنیم و آن را به اسلات مورد نظر متصل کنیم.

مثال ۱ (پیاده‌سازی عملیات تراکنشی)

اگر بخواهیم چندین فرآیند را به صورت تراکنش انجام دهیم این الگوی طراحی می‌تواند به ما کمک کند. برای مثال فرض کنید که بخواهیم کارهای زیر را انجام دهیم:

  1. یک رکورد در دیتابیس ایجاد کن.
  2. سرویسی را صدا بزن تا تمامی رکوردهای مرتبط را به روزرسانی کند.
  3. سرویس دیگری را صدا بزن تا عملیات را لاگ کند. برای انجام این عملیات تراکنش گونه، می‌توانیم هر عمل را به صورت یک ConcreteCommand طراحی کنیم. که همهٔ این عملیات undo دارند. در آخر هر مرحله، آن کامند را وارد پشته می‌کنیم. اگر عملیات در مرحله‌ای شکست بخورد، سپس کامندها را یکی یکی از پشته خارج می‌کنیم و undo را روی آن‌ها اجرا می‌کنیم.

منبع: http://stackoverflow.com/a/12153801/225052

مثال ۲ (ریموت کنترل)

فرض کنید که کلی وسیله داریم که هر کدام اینترفیس مخصوص به خود برای روشن و خاموش شدن و به کار افتادن و عملیات‌های مختلف را داشته باشند.

  1. پنکه : روشن/خاموش/افزایش سرعت/کاهش سرعت
  2. تلویزیون: روشن/خاموش/شبکهٔ بعدی/شبکهٔ قبلی
  3. چراغ: روشن/خاموش
  4. استریو: روشن/خاموش/فعال کردن سی‌دی/فعال کردن دی‌وی‌دی/فعال کردن رادیو

می‌خواهیم یک کنترل از راه دور برای این دستگاه‌ها طراحی کنیم.

  1. نیازی نیست که کنترلر اینترفیس دستگاه‌های مختلف را بداند. فقط کافی‌ست که درخواست خودش را برای این دستگاه‌ها ارسال کند.
  2. با چنین طراحی‌ای هر گاه دستگاه جدیدی اضافه شود به راحتی می توان دکمهٔ جدیدی برای کنترل آن در کنترلر تعریف کرد.
  3. الگوی طراحی Command درخواست کنندهٔ عمل را از انجام‌دهندهٔ عمل جدا می‌کند.
  4. برای انجام چنین کاری «شیء فرمان» تعریف می‌کنیم: در خواست‌ها را کپسوله برای اشیاء مختلف کپسوله می‌کنیم مثلاً اشیائی به صورت زیر خواهیم داشت:
  5. ضبط صوت را روشن کن (یک شیء است)
  6. لامپ را خاموش کن (شیء)
  7. تلویزیون را خاموش کن (شیء)

مثال ۳ (رستوران)

  1. مشتری به پیشخدمت درخواست پخت غذای مخصوصی را می‌دهد. ‍createOrder()
  2. پیشخدمت درخواست را از مشتری گرفته takeOrder() و به روی میز سرآشپزها بگذارد orderUp().
  3. سرآشپز از روی درخواست غذای مورد نظر مشتری را تهیه می‌کند. makeBurger() و makeShake()

در این روش پیشخدمت از جزئیات با خبر نیست و فقط دستور مشتری را به سرآشپزها منتقل می‌کند.

مثال‌های واقعی

- All implementations of java.lang.Runnable - All implementations of javax.swing.Action