Menu
Coddy logo textTech
flag Ar iconالعربيةdown icon

نمط المصنع (Factory Pattern)

جزء من قسم البرمجة كائنية التوجه في رحلة C# على Coddy. الدرس 53 من 70.

إن نمط Factory هو نمط إنشائي يفوّض إنشاء الكائنات إلى method أو class منفصل. وبدلًا من استخدام new مباشرةً في التعليمات البرمجية، تطلب من factory إنشاء الكائنات نيابةً عنك. وهذا يُركّز منطق الإنشاء ويجعل تعليماتك البرمجية أكثر مرونة.

تخيّل سيناريو تحتاج فيه إلى إنشاء أنواع مختلفة من المستندات. من دون factory، يصبح الكود الخاص بك مقترنًا بشكل وثيق بفئات محددة:

// بدون Factory - منطق الإنشاء المتناثر
IDocument doc;
if (type == "pdf")
    doc = new PdfDocument();
else if (type == "word")
    doc = new WordDocument();

تُجسّد factory عملية اتخاذ هذا القرار في مكان واحد:

public interface IDocument
{
    void Open();
}

public class PdfDocument : IDocument
{
    public void Open() => Console.WriteLine("Opening PDF");
}

public class WordDocument : IDocument
{
    public void Open() => Console.WriteLine("Opening Word");
}

public class DocumentFactory
{
    public IDocument Create(string type)
    {
        return type switch
        {
            "pdf" => new PdfDocument(),
            "word" => new WordDocument(),
            _ => throw new ArgumentException("Unknown type")
        };
    }
}

الآن يطلب كود العميل ببساطة ما يحتاج إليه دون معرفة الأصناف الملموسة:

var factory = new DocumentFactory();
IDocument doc = factory.Create("pdf");
doc.Open();  // فتح PDF

يتألق نمط Factory عندما تحتاج إلى إضافة أنواع جديدة لاحقًا. تتطلب إضافة SpreadsheetDocument إجراء تغييرات في factory فقط، وليس في كل مكان يتم فيه إنشاء المستندات. يجعل هذا الفصل قاعدةَ التعليمات البرمجية لديك أسهل في الصيانة والاختبار.

challenge icon

التحدي

سهل

لنَبْنِ نظامًا للإشعارات باستخدام نمط Factory. بدلًا من إنشاء أنواع الإشعارات المختلفة مباشرةً في جميع أنحاء التعليمات البرمجية، ستُركّز منطق الإنشاء في فئة factory تحدد الإشعار الذي يجب إنشاؤه استنادًا إلى معرّف نصي بسيط.

ستنظّم تعليماتك البرمجية عبر ثلاثة ملفات:

  • Notification.cs: عرّف واجهة INotification في مساحة الأسماء Notifications مع method واحدة هي Send(string message) تُرجع سلسلة نصية. ثم أنشئ ثلاث فئات تطبّق هذه الواجهة:
    • EmailNotification - تُرجع "Email: {message}"
    • SmsNotification - تُرجع "SMS: {message}"
    • PushNotification - تُرجع "Push: {message}"
  • NotificationFactory.cs: أنشئ فئة NotificationFactory في مساحة الأسماء نفسها، مع method باسم Create(string type) تُرجع INotification المناسبة استنادًا إلى سلسلة النوع:
    • "email" تُرجع EmailNotification
    • "sms" تُرجع SmsNotification
    • "push" تُرجع PushNotification
    بالنسبة إلى أي نوع غير معروف، أرجِع EmailNotification باعتباره القيمة الافتراضية.
  • Program.cs: اجمع كل شيء معًا من خلال إنشاء instance من factory واستخدامها لإنشاء الإشعارات استنادًا إلى الإدخال. يتولى factory جميع القرارات المتعلقة بالفئة الفعلية التي ينبغي إنشاء instance منها.

ستتلقى مدخلين:

  • نوع الإشعار (مثلًا: sms)
  • الرسالة المراد إرسالها (مثلًا: Your order has shipped)

استخدم factory لإنشاء نوع الإشعار المناسب، ثم استدعِ method الخاصة به Send مع الرسالة واطبع result.

على سبيل المثال، إذا كانت المدخلات هي push وMeeting in 5 minutes، فينبغي أن يكون الناتج:

Push: Meeting in 5 minutes

لاحظ أن التعليمات البرمجية الرئيسية لا تستخدم أبدًا new EmailNotification() أو ما شابه؛ فهي تطلب ببساطة من factory ما تحتاج إليه. وإذا أضفت لاحقًا SlackNotification، فلن تحتاج إلا إلى تحديث factory، وليس كل موضع ينشئ الإشعارات!

جرّب بنفسك

using System;
using Notifications;

class Program
{
    public static void Main(string[] args)
    {
        // اقرأ الإدخال
        string type = Console.ReadLine();
        string message = Console.ReadLine();

        // TODO: أنشئ مثيلاً من NotificationFactory

        // TODO: استخدم المصنع لإنشاء الإشعار المناسب

        // TODO: استدعِ الطريقة Send واطبع النتيجة
    }
}
quiz iconاختبر نفسك

يتضمن هذا الدرس اختبارًا قصيرًا. ابدأ الدرس للإجابة عليه وتتبّع تقدمك.

جميع دروس البرمجة كائنية التوجه

تدرّب بنفسك: مترجم C# عبر الإنترنت