C++الثوابت
- مفهوم الثوابت
- تعريف متغير ثابت
- تعريف مؤشر كثابت
- تعريف مؤشر لثابت
- تعريف باراميتر الدالة كثابت
- تعريف خصائص ثابتة في الكلاس
- تعريف الكائن كثابت
- الكلمة
mutable - الكلمة
#define
مفهوم الثوابت
الثابت ( Constant ) عبارة عن أي شيء يتم تعريفه بشكل لا يمكن إعادة تغيير قيمته.
لتعريف المتغير أو الكائن كثابت نستخدم الكلمة const و عندها نصبح غير قادرين على تغيير قيمته.
الكلمة const يمكن استخدامها مع الأشياء التالية:
- المتغيرات (Variables).
- المؤشرات (Pointers).
- باراميترات لدوال (Functions Parameters).
- خصائص الكلاس (Class Member Variables).
- دوال الكلاس (Class Member Functions).
- الكائنات (Objects).
تعريف متغير ثابت
إذا قمت بتعريف متغير ثابت فلا يمكنك تغيير قيمته لاحقاً و لا بد لك من إعطاؤه قيمة مباشرةً عند تعريفه.
القيمة الموضوعة بداخل المتغير يمكن الحصول عليها بشكل عادي مثل القيمة التي يتم وضعها بداخل متغير عادي و لكن لا يمكن تغييرها فقط.
في المثال التالي قمنا بتعريف متغير ثابت إسمه x قيمته 10 و من ثم حاولنا إعادة تغيير قيمته.
المثال الأول
main.cpp
سنحصل على النتيجة التالية عند التشغيل.
في المثال التالي قمنا بتعريف متغير ثابت إسمه x قيمته 10 و من ثم حاولنا إعادة تغيير قيمته.
المثال الثاني
main.cpp
سيظهر الخطأ التالي عند التشغيل و الذي يعني أنه لا يمكن تغيير القيمة الموجودة في المتغير x.
error: assignment of read-only variable 'x'
تعريف مؤشر كثابت
المؤشر العادي يمكن في أي وقت جعله يشير لأي شيء موجود في الذاكرة كما سبق و شاهدنا.
تعريف المؤشر نفسه كثابت يجعل المؤشر مخصص للشيء الذي تم جعله يشير إليه عند تعريفه مع عدم القدرة على جعله يشير لشيء آخر لاحقاً.
في المثال التالي قمنا بتعريف متغير إسمه x قيمته 5 و متغير إسمه y قيمته 7.
بعدها قمنا بإنشاء مؤشر ثابت إسمه ptr يشير لقيمة المتغير x و من ثم حاولنا جعله يشير لقيمة المتغير y مما سيؤدي لحدوث مشكلة عند التشغيل.
مثال
main.cpp
سيظهر الخطأ التالي عند التشغيل و الذي يعني أنه لا يمكن تغيير القيمة التي يشير إليها المؤشر ptr.
error: assignment of read-only variable 'ptr'
تعريف مؤشر لثابت
إذا كنت تملك متغير ثابت يمكنك إنشاء مؤشر له و لكن عندها يجب أن تنشئ المؤشر كثابت أيضاً مما يجعلك غير قادر على جعله يشير لشيء آخر لاحقاً.
في المثال التالي قمنا بتعريف متغير ثابت إسمه x قيمته 10 و مؤشر ثابت إسمه ptr يشير لقيمته.
في الأخير قمنا بعرض القيمة التي يشير إليها المؤشر ptr في الذاكرة.
مثال
main.cpp
سنحصل على النتيجة التالية عند التشغيل.
في المثال السابق, المؤشر الثابت ptr الذي قمنا بتعريفه في السطر 11 يمكننا تعريفه كالتالي و الحصول على نفس النتيجة.
و هذه طريقة مختلفة أيضاً لتعريفه.
تعريف باراميتر الدالة كثابت
في حال كنت تنوي تمرير قيمة متغير ثابت لدالة و تريد أن يتم معاملة القيمة التي يتم تمريرها كأنها قيمة ثابتة أيضاً, يجب أن تعرف نوع البارميتر في الدالة كثابت.
في المثال التالي قمنا بتعريف دالة إسمها addOne عند استدعاءها نمرر لها عدد فتقوم بإضافة 1 عليه و ترجع قيمته.
المثال الأول
main.cpp
سنحصل على النتيجة التالية عند التشغيل.
في المثال التالي قمنا بإعادة المثال السابق و لكننا هذه المرة جعلنا القيمة التي يتم تمريرها للدالة يتم إعتبارها قيمة ثابتة مما سيؤدي لحدوث خطأ عند التشغيل.
ملاحظة: قمنا بتعليم السطر الذي أجرينا عليه التعديل باللون الأصفر.
المثال الثاني
main.cpp
سيظهر الخطأ التالي عند التشغيل و الذي يعني أنه لا يمكن تغيير قيمة الثابت n.
error: increment of read-only parameter 'n'
أمثلة إضافية على التعامل مع القيم الثابتة التي يتم تمريرها للدوال.
شاهد الأمثلة
تعريف خصائص ثابتة في الكلاس
إذا أردت تعريف خصائص ثابتة في الكلاس, بمعنى أنه لا يمكن تغيير القيم التي نعطيهم إياها لاحقاً, فلا بد لك من تمرير قيم لكل خاصية ثابتة قمت بتعريفها في الكائن لحظة إنشاء الكائن و نفعل ذلك من خلال كونستركتور الكائن كما سنرى الآن.
في المثال التالي قمنا بتعريف كلاس إسمه Player يحتوي على متغير ثابت إسمه name بالإضافة إلى كونستركتور يسمح لنا بتمرير قيمة للثابت name.
مثال
main.cpp
سنحصل على النتيجة التالية عند التشغيل.
في المثال السابق, إذا أردت تسمية الباراميتر الموضوع في الكونستركتور name كإسم الخاصية و الحصول على نفس النتيجة فسيصبح شكل الكونستركتور كالتالي.
معلومة: في حال كنت تريد تمرير قيمة لأكثر من ثابت في الكونستركتور, فيجب أن تضع فواصل بين كل قيمتين كالتالي.
تعريف الكائن كثابت
إذا أردت إنشاء كائن ثابت بمعنى أنه لا يمكن تغيير قيمة أي خاصية موجودة فيه فيمكنك إنشاء الكائن ككائن ثابت.
عند إنشاء كائن ثابت من كلاس لا يمكنك استدعاء أي دالة في الكلاس تتعامل مع أحد الخصائص الموجودة فيه إلا إذا قمت بجعل الدالة من الأساس ثابتة أيضاً.
في المثال التالي قمنا بتعريف كلاس إسمه Player يحتوي على متغيرين إسمهما name و age كخصائص عادية.
كما أننا قمنا بتعريف كونستركتور يسمح لنا بتمرير قيم للخصائص name و age و دالة ثابتة يمكن استخدامها لعرض قيمهما بشكل مرتب.
مثال
main.cpp
سنحصل على النتيجة التالية عند التشغيل.
الكلمة mutable
في حال كنت تنوي إنشاء كائن ثابت من الكلاس و لكنك تريد جعل بعض الخصائص الموجودة فيه غير ثابتة بمعنى أنه يمكن تغيير قيمها لاحقاً بعد إنشاء الكائن, يجب أن تعرف الخاصية التي تريد جعل قيمتها غير ثابتة mutable حتى يفهم المترجم أنك تريد ذلك.
في المثال التالي قمنا بتعريف كلاس إسمه Player يحتوي على ثلاث متغيرات إسمهم name و age و job كخصائص في الكلاس.
الخاصية job جعلنا نوعها mutable حتى نستطيع تغيير قيمتها متى أردنا من الكائن الذي ننشئه من الكلاس حتى و إن قمنا بإنشائه ككائن ثابت.
كما أننا قمنا بتعريف كونستركتور يسمح لنا بتمرير قيم للخصائص name و age و دالة ثابتة يمكن استخدامها لعرض قيم كل الخصائص بشكل مرتب.
مثال
main.cpp
سنحصل على النتيجة التالية عند التشغيل.
الكلمة #define
الكلمة #define يمكن أن تستخدم لتعريف متغير قيمته ثابتة مثل الكلمة const و لكن بأسلوب مختلف.
في المثال التالي قمنا بتعريف متغير ثابت إسمها MAX_VALUE قيمته تساوي 1000.
مثال
main.cpp
سنحصل على النتيجة التالية عند التشغيل.
الكلمة #define قد تسبب مشاكل غير متوقعة في البرنامج لأن نوع القيمة التي يتم وضعها فيها ليس محدداً, لذلك يفضّل تعريف المتغير الثابت دائماً بواسطة الكلمة const بدلاً من الكلمة #define.