مفاهيم أساسية [++C]





السلام عليكم 


في أغلب الكتب التى تعلم ++C يبدأ الكاتب بعرض كود بسيط و يظهر لك مخرجاته كتحفيز لك بعدها يبدأ فى شرح ذلك الكود، مع العلم ان هذا النهج يعطيك دافع جيد و إنما يترك فجوة فى عقلك فى ماهية بعض الأكواد المكتوبة و ايضا فى سبب اختياره لنوع البرنامج نفسه و الذى يكون فى الأغلب Console، لذا اعتقد انه توجد بعض المفاهيم و المصطلحات الأساسيه التى لابد و ان تعرفها قبل ان تشرع فى كتابة برامجك بلغة ++C.

فى هذا الموضوع

[/here]لماذا Console؟
نحن نعرف ان لغة ++C مبنية
[1] على لغة C، و التى صنعت خصيصا للتسهيل فى تطوير نظام تشغيل Unix و الذى كانت الـ User Interface الأساسية به حينها هى Console، و من ثمَّ أصبحت هذه وحدة الإدخال و الإخراج الإفتراضية داخل لغة الـ C و التى انتقلت من بعدها للغة الـ ++C.

مع تطور الوقت ظهرت انظمة تشغيل جديده تحتوى على User Interface اكثر وداً
[2] من الـ Console. انظمة التشغيل الحديثة و المطوره إحتوى كل منهم على أساليب برمجية مختلفة للتعامل مع GUI/CUI و لكن تم الإبقاء على اسلوب برمجة CUI للتكامل[3] مع لغة C، أما بالنسبة للـ GUI فكان من الصعب إيجاد إسلوب برمجي موحد و ذلك لإختلاف تصميم GUI بكل نظام تشغيل، و بهذا اصبحت الـ CUI هى لغة الحوار الأساسية بين مبرمجي ++C/C مع نظام التشغيل.


مصطلحات أساسية
[4]
توجد العديد من المصطلحات المرتبطه الـ ++C منها الأساسي و منها المتقدم، التالي هو بعض المصطلحات الأساسية و معناها:

Header File: هو ملف به اكواد مشركة فبدلا من كتابتها بأكثر من ملف يتم كتابتها بهذا الملف و يعدها  يمكن أستخدامه أكثر من مرة و لكنه ليس اساسي لبناء البرنامج، هذا النوع من الملفات قد يكون بلا إمتداد (اللغه وحدها هى التى تستخدم هذا الشكل) او يأخذ أى من الأتي: h, hh, hpp, hxx

Source File: هو ملف يحتوى على الكود الأساسي للبرنامج. هذا النوع من الملفات يمثل وحدة بناء البرنامج، و قد يأخذ أى من الإمتدادات[5] التالية: cpp, cc, cxx

Preprocessror: هي المرحلة التى يقوم فيها Compiler بدمج جميع Header Files المستخدمه داخل Source File بالإضافة لتعديل بعض المحتويات و حذف اخرين.

Translation Unit: هو الملف الناتج من Preprocessror و يحتوى فقط على الكود الذى سيقوم Compiler بترجمته[6].

Compiler: هو برنامج يتم إدخال له Translation Unit و يقوم بإخراج Object Code.

Assembler: هو برنامج يتم تمرير له ملف كود مكتوب بالأسمبلي و يقوم بإنتاج Object Code.

Object Code: هو الملف الناتج من Compiler أو Assembler فى حالة إتمامه لعملية الترجمه و يحتوى على كود يشبه Executable Code.

Linker: هو برنامج يتم تمرير له Object Code او أكثر و يقوم بإجراء بعض العمليات عليهم و في حالة النجاح يقوم بإخراج الملف التنفيذى.


مراحل بناء برنامج
توجد بعض الخطوات الأساسية التى يقوم بها المترجم، كل خطوه قد تنقسم لمجموعة أخرين و لكن فى المجمل هذا هو الشكل العام لهذه الخطوات.

من الكود لأسمبلي Source code to Assembly language
يتم تمرير ملف الكود Source code للمترجم حيث يقوم بالأتي:
  • يقوم الـ Preproccessor بعمليات الـ Housekeeping مثل حذف الملاحظات و دمج محتويات الـ header files إن وجد أيهم، أيضا يقوم ببعض العمليات الأخرى[7]، إذا لم يجد الـ Preprocessor أى مشاكل اثناء عمله يقوم بإنتاج ملف جديد يسمي بـ Translation Unit.
  • فى هذه المرحله يقوم المترجم بالتحقق من بنية ملف الـ Translation Unit و انها تتبع قواعد اللغه، في هذا الأثناء قد يقوم المترجم بتوليد كود جديد حسب محتويات ملف الـ Translation Unit بعدها يبدأ في عملية تحويل الكود إلى النسخه التى تقابله بالأسمبلي[8].
من أسمبلي للنمط الثنائي Assembly language to object file
ملف الأسمبلي الناتج يتم تمريره للـ Assembler حيث يقوم بإنشاء ملف جديد يحتوى على لغة الأله Machine Language بالإضافة لبعض المعلومات الأخرى التى سيتم إحتياجها في المرحله التاليه. الملف الجديد الناتج يسمي بـ Object file، أشهر الإمتدادات لهذا النوع من الملفات: obj, o

من النمط الثنائي للملف التنفيذي Object File to Executable file
عملية التحويل للملف التنفيذى يقوم بها برنامج الـ Linker حيث يتم تمرير له Object File او أكثر و يقوم ببعض العمليات عليهم و من ثمَّ فى حالة نجاح العمليات يقوم بإنتاج الملف التنفيذي
[7].


أبجدية اللغه
فى اللغه العربية يوجد 28 حرف، و كما حفظناهم فهم يبدؤا بالحرف ألف (و يأخذ الشكل [أ] ) و ينتهوا بالحرف ياء (و يأخذ الشكل [ي] )، هذه الحروف هي أبجدية اللغه العربية. بالمثل مع لغة ++C حيث يوجد لدينا مجموعة من الحروف التى تمثل أبجديتها و هم:
A B C D E F G H I J K L M N O P Q R S T U V W X Y Za b c d e f g h i j k l m n o p q r s t u v w x y z0 1 2 3 4 5 6 7 8 9
توجد مجموعة من الرموز التى تستخدم مع أبجدية اللغه و هم:
_ { } [ ] # ( ) < > % : ; . ? * + - / ^ & | ? ! = , \ " '
هذه الحروف و الرموز تسمي بـ مجموعة الحروف و الرموز الأساسية أو basic source character set و هم وحدة بناء ملفات الكود الخاص بلغة ++C. بالإضافة لتلك الحروف و الرموز توجد بعض الحروف و الرموز الأخرى التى يمكن استخدامها داخل اللغه، هذه الحروف تأتي من Unicode و سيتم التكلم عنها لاحقاً.


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

داخل لغة ++C يمكننا إستخدام أى مجموعة من الحروف لتكوين كلمات، هذه الكلمات بعضها له معنى محدد داخل اللغه، و بالتالي انت لا تستطيع إستخدام هذه الكلمات بقصد الحصول على معنى أخر، و حيث ان هذه الكلمات لها معنى معروف فهذا يجعلهم 
كلمات محجوزه للغة ++C.

هذه الكلمات هي:
asm auto bool break case catch char class const const_cast continue default delete do doubledynamic_cast else enum explicit export extern false float for friend goto if inlineint long mutable namespace new operator private protected public register reinterpret_castreturn short signed sizeof static static_cast struct switch template this throw truetry typedef typeid typename union unsigned using virtual void volatile wchar_t while
و سيتم معرفة معني هذه الكلمات فيما بعد.


التواصل مع محتويات الـ Standard
الـ Standard الذى تأتي منه محتويات هذه السلسلة هو C++ Standard, Second Edition بتاريخ 2003-10-15 و عدد صفحات كتابه الإلكتروني 786 صفحة (ستجده بمكتبة كتب القسم).

أنظر معي هذه الفقرة من صفحة 30:
 
  Quote
1.3.12 undefined behavior                                               [defns.undefined]
behavior, such as might arise upon use of an erroneous program construct or erroneous data, for which this
International Standard imposes no requirements.
Undefined behavior may also be expected when this
International Standard omits the description of any explicit definition of behavior. [Note: permissible undefined
behavior ranges from ignoring the situation completely with unpredictable results, to behaving during
translation or program execution in a documented manner characteristic of the environment (with or without
the issuance of a diagnostic message), to terminating a translation or execution (with the issuance of a
diagnostic message). Many erroneous program constructs do not engender undefined behavior; they are required to be diagnosed.]
الفقرة داخل الـ Standard لها 3 عناصر يمكن تمييزها بهم و هم:
  • رقم الفقرة: هذا الرقم يستخدم لوصف مكان الفقرة داخل الـ Standard حيث الرقم 1 هو رقم الفصل و الرقم 3 يمثل رقم العنوان الفرعي و الرقم 12 هو رقم الفقرة.
  • عنوان الفقرة: هذا العنوان يصف بشكل مختصر محتوي الفقرة.
  • موقع الفقرة:كل الفقرات داخل الـ Standard لها إسم مختصر مثل [intro] و عندما توجد فقرة فرعية يتم إستخدام إسم الفقرة الحاوية ثم نقطة ثم إسم الفقرة الحالة و في حالتنا هذه فنحن نعرف ان الفقرة الحالية اسمها [undefined] و هي موجوده داخل الفقرة [defns]، فى الأغلب ستجد ان موقع الفقرة يتكون من جزء أو إثنان و عندما يحدث ان يتواجد اجزاء اخرى داخل موقع الفقرة فهذه الأجزاء تتبع أخر اسم مختصر داخل الموقع فمثلا [lib.string.ops] تعنى ان الفقرة string.ops موجوده داخل lib، هل تستطيع معرفة عدد أجزاء موقع هذه الفقرة[lib.string::find.first.of].
عندما أريد الإشارة داخل الـ Standard سأقوم بإستخدام رقم الفقرة حيث سيسهل الوصول لها و في احيان قليله قد أستخدم موقع الفقرة.


لماذا Unicode
ذكرنا منذ قليل أنه يمكنك إستخدام حروف Unicode جنبا إلى جنب مع الحروف و الرموز الأساسية باللغه . إذا كنت تعرف ما هي Unicode يمكنك تخطي هذا الجزء.

انظمة التشغيل القديمه تتبع مفهوم Code Page حيث يوجد لدينا الأرقام من صفر و حتى 255، كل الأرقام من صفر و حتى 127 محجوزة لتمثيل بعض الحروف الخاصه مثل بداية سطر او نهاية سطر او مساحة فارغة طويلة أو عريضة Vertical or Horizontal Tab و البقية لتمثيل الأبجدية الاتينية و الأرقام العربية
[9] و بعض الفواصل و الرموز، الحروف التى يتم تمثيلها فى ذلك المدى ثابتة بكل الـ code pages و تسمي ASCII، أما الأرقام من 128 و حتى 255 فالحروف التى تمثلهم تختلف بإختلاف الـ code page نفسها فمثلا ًWindows-1256 هو إسم code page و التى المدى من 128 حتى 255 يستخدم لتمثيل الأبجدية العربية، بالمثل مع باقي الـ code pages.

إسلوب الـ code page يجعل من الصعب كتابة نص يحتوى على اللغه العربية و الفرنسية و الكورية معا و السبب ان كل منهم له code page مختلفه عن الأخري و هذا يعنى ان نفس الكود و ليكن 180 يمثل حرف مختلف بكل code page و من هذا المنطلق أتت Unicode لحل هذه المشكلة.

Unicode هي منظمة قامت بتصميم نظام موحد لتمثيل حروف كل لغات العالم مع إعطاء كل حرف رقم كودي فريد لا يتكرر، كل حرف يتم تمثيله بعدد 32 بت. ارقام الحروف من صفر و حتى 127 داخل Unicode تماثل الموجودة داخل ASCII و بقية الأرقام مقسمه حسب كل لغة.

لنفترض اننا نريد كتابة فقرة باللغة العربية حينها سنستخدم الأرقام فى المدى 1536 حتى 1791 و التى تمثل الحروف العربية، و إذا نظرنا بتمعن للأرقام فى هذا المدى سنجد ان الحروف التى تمثلها هذه الأرقام يمكن تمثيل كل واحد منهم بـ 16 بت فقط و بهذا نستطيع تقليل مساحة الذاكرة المستخدمه للنصف (من 32 بت إلي 16 بت) و لكن إذا فعلنا هذا فهذا يعنى ان الحروف فى المدى اكبر من 16بت لن نستطيع ترميزها داخل برامجنا و لهذا قامت Unicode بتصميم وسيلة تتيح لنا حفظ الذاكرة و بنفس الوقت امكانية ترميز كل الحروف التى تقدمها لنا، هذه الوسيلة تسمي بـ Unicode Transformation Formats أو إختصارا UTF.

كل UTF يعتمد على مضاعفات عدد معين من البتات لتمثيل أى حرف، فمثلا تجد UTF-8 تستهلك على الأقل 8 بت لتمثيل أى حرف فإذا كانت قيمة الحرف اكبر من 127 حينها نحتاج إلى عدد 2 * 8 = 16 بت، أيضا يوجد UTF-16 و الذى يستهلك على الأقل 16 بت لتمثيل أى حرف و إذا تجاوز الحرف 16 بت حينها نحتاج 2 * 16 = 32 بت، و اخيرا لدينا UTF-32 و الذى يستهلك 32 بت لتمثيل أى حرف.

فلنفترض اننا نستخدم نظام UTF-8 و أردنا تمثيل علامة الضرب [x]، و قيمة الحرف هي 0xC397 و لكن هذا الرقم يمثل حرف فعلي داخل UTF-32 و ذاك الحرف يتبع رموز هان. لا تدع الشك يصل إليك حيث انه توجد فعلا وسيلة لتحديد الطريقة التى يتم تمثيل الحرف بها. داخل Unicode بعض الأرقام لها إستخدامات خاصه مثل تحدد نوع الـ UTF المستخدم و هذه الأرقام لا يوجد حروف لها و استخدامها يكون ضمنيا حتى إذا قام برنامج بقراءة محتويات ملف و وجد اى من هذه الأرقام فإنه يعرف فورا اى نظام UTF هذا الملف يتبعه.


داخل لغة ++C
تسمح لك ++C بأن تستخدم حروف Unicode داخل ملفات الكود الخاص بك و ذلك لتكوين كلمات جديده خاصه بك و توجد طريقتين يمكنك بهم كتابة حروف Unicode:
  • أستخدم محرر يدعم Unicode وسيقوم هو بتحويل الحروف التى تكتبها بما يقابلها من ارقام داخل Unicode.
  • تقوم بإستخدام صيغة محدده تسمح بها اللغه و ذلك بكتابة الرقم الذى يمثل الحرف بشكل معين و المترجم يتكفل بتحويله لحرف.
أيا كانت الطريقه التى ستستخدمها توجد بعض القيود على بعض الحروف، فمثلا لا يمكنك إستخدام الطريقه الثانية لوصف حرف أو رمز موجود داخل مجموعة الحروف و الرموز الأساسية، بالطبع يوجد سبب لهذا القيد و سيتم تناوله فيما بعد، أيضا توجد بعض الحروف التى يمنع إستخدامها فى اماكن معينه و لكن يسمح بإستخدامها داخل اماكن أخرى.


[here=ref11]خاتمه
فى هذا الموضوع عرفنا لماذا الـ Console هو وحدة الإداخل و الإخراج الأساسية داخل لغة ++C/C، أيضا عرفنا بعض المصطلحات الخاصة باللغه و كذلك كيف يقوم المترجم بتحويل الكود إلى النسخه التنفيذية و انتقلنا لنتحدث عن أبجدية و الكلمات المحجوزة بلغة ++C و عرفنا كيف تم تنظيم الـ Standard، أيضا تحدثنا عن Unicode و عن امكانية استخدامها لكتابة أكواد برامجنا.


و الله ولي التوفيق


شارك الموضوع

مواضيع ذات صلة

2 commentaires

commentaires
25 avril 2018 à 16:28 حذف

لم أستطع قراءة موضوع الى ل 5 ثواني فقط بسبب تضارب حروف عربية مع حروف لاتنية حاول ان تجد حل لها وشكرا لك على هذا مجهود :)

رد
avatar
28 avril 2018 à 14:46 حذف

شكرا أخي سأعالج الموضوع شكرا لك طبعا ان تصفحت الموضوع من الحاسوب لن تجد المشكل سأعالج الموضوع على الهاتف

رد
avatar