مراجعة: Logger Factory
جزء من قسم البرمجة كائنية التوجه في رحلة C على Coddy. الدرس 57 من 61.
التحدي
سهللنبنِ Logger Factory: نظامًا يوضّح قوة الجمع بين نمط Factory وتعدّد الأشكال. ستنشئ factory تطبيقات logger مختلفة استنادًا إلى flag للإعدادات، مما يسمح للكود بالتبديل بين مخرجات console المفصّلة وتسجيل "dummy" الصامت دون تغيير طريقة استخدام logger.
ستنظّم كودك عبر ثلاثة ملفات:
logger.h: عرّف بنيةLoggerالتي تعمل كواجهة. يجب أن تحتوي على مؤشّر دالة لـlogيأخذLogger*ورسالة من النوعconst char*. صرّح بدالة factory، وهيcreate_logger، التي تأخذ flag من النوع integer (1 لـ console و0 لـ dummy) وتُرجعLogger*. صرّح أيضًا بدالةfree_loggerلإجراء Cleanup.logger.c: نفّذ نوعين ملموسين من logger. يضمّنConsoleLoggerبنيةLoggerبوصفها أول عضو فيه، ويحتوي على دالة log تطبع الرسائل بالتنسيق[LOG] message. يضمّنDummyLoggerأيضًا بنيةLogger، لكن دالة log الخاصة به لا تفعل شيئًا. فهي تعود ببساطة دون طباعة. أنشئ دوال Constructor لكل نوع لتخصيص الذاكرة وربط دالة log المناسبة. ثم نفّذcreate_loggerبوصفها factory تتحقق من flag وتُرجع نوع logger المناسب على هيئةLogger*. نفّذfree_loggerلتحرير الذاكرة.main.c: اقرأ integer (1 أو 0) لتحديد logger الذي يجب إنشاؤه. استخدم factory لإنشاء logger المناسب، ثم استدعِ دالةlogالخاصة به مع رسالتين:"Starting application"و"Shutting down". وأخيرًا، حرّر logger.
سيستقبل برنامجك مُدخلًا واحدًا: integer يشير إلى نوع logger (1 لـ console و0 لـ dummy).
مثال على المخرجات عندما يكون المُدخل 1:
[LOG] Starting application
[LOG] Shutting downمثال على المخرجات عندما يكون المُدخل 0:
(لا توجد مخرجات: يتجاهل dummy logger جميع الرسائل بصمت)
تكمن الأناقة هنا في أن main.c يستخدم logger بالطريقة نفسها بغضّ النظر عن النوع الذي يستلمه. يقرّر factory ما يجب إنشاؤه، ويضمن تعدّد الأشكال تنفيذ السلوك الصحيح. هذا النمط لا يُقدّر بثمن في التطبيقات الحقيقية، حيث قد ترغب في تسجيل مفصّل أثناء التطوير، لكن في تشغيل صامت في بيئة الإنتاج.
جرّب بنفسك
#include <stdio.h>
#include "logger.h"
int main() {
// اقرأ علامة نوع المسجل (1 لوحدة التحكم، 0 للوهمي)
int flag;
scanf("%d", &flag);
// TODO: استخدم المصنع لإنشاء المسجل المناسب
// TODO: Call the logger's log function with "Starting application"
// TODO: Call the logger's log function with "Shutting down"
// TODO: حرّر المسجل
return 0;
}
جميع دروس البرمجة كائنية التوجه
1أساسيات البرمجة التركيبية
ملفات الترويسةحواجز التضمينملفات المصدرالدوال الساكنةمراجعة: آلة حاسبة تركيبية4التغليف (Encapsulation)
مفهوم الـ Opaque Pointersتعريف الـ Opaque Structsالـ Getters والـ Settersالتحقق من البيانات في الـ Settersملخص: الصندوق السري2الكائنات والأساليب
الـ Structs ككائناتمؤشر 'Self'صحة استخدام Constالمؤشر مقابل القيمةالأساليب المساعدةملخص: Point Manager5مشروع: حساب بنكي بسيط
إعداد المشروعتنفيذ الحساب3دورة حياة الكائن
نمط المنشئ (Constructor Pattern)نمط الهادم (Destructor Pattern)تهيئة الـ Stackالنسخ العميق (Deep Copy)مراجعة: String Wrapper6الوراثة عبر التركيب
تضمين الـ Structقاعدة العضو الأولالوصول إلى أعضاء الأبعملية الـ Upcastingمراجعة: هرمية الأشكال9مشروع: رسّام الأشكال
نظرة عامة على المشروعتنفيذ الدائرةتنفيذ المستطيلاستخدام تعدد الأشكالحاوية الأشكالتدرّب بنفسك: مترجم C عبر الإنترنت