الفريق العربي للبرمجةأرشيف المنتديات · 2000 – 2023
نسخة أرشيفية للقراءة فقط — التسجيل والمشاركة مغلقان، والمحتوى محفوظ كما كان.

سؤال محير جديد .. صلب البرمجة الكائنية .. من يجيب .. ؟؟(الصنف الفارغ)

مغلق
بدأه سنان محمد صالح في 15 فبراير 2008 · 7 رد · 1,694 مشاهدة · في اختبر قداراتك
مشاركة: واتساب X فيسبوك تيليجرام
#1 صاحب الموضوع

السلام عليكم ورحمة الله وبركاته ..

كما عودتكم اخوتي .. على الاسئله القوية والتي تجعل الشخص يفكر بما امامه وهو متاكد من هذا صعب الحصول .. ولكنه يحصل .. سبب الحصول هو ما اريده في اغلب الاحيان .. وما اريده هو الان سبب ما حدث في مايلي ..

لدينا الكود التالي ..

class x {
  };

class y {
	int n;
};

   void main() {
	   cout << sizeof(x)<<endl;
	   cout << sizeof(y) <<endl;
}

كود واضح .. ولكن تفسير سريع له .. قمت بتعريف الصنف الفارغ x والذي لايحتوي اي معلومات بداخله ..وبعده عرفت الصنف y والذي يحتوي على متغير n من نوع صحيح ..

وبعد القيام بعملية معرفة الحجم في الدالة main .. ضهرت لنا نتيجة غريبه نوعا ما ..

وهي .. ان الصنف الاول رغم انه لايحتوي اي شئ فان حجمه ثابت وهو 1 ..

والصنف الثاني حجمه هو بحجم المتغير الذي بداخله ( لدي الربو سي 3 ) ضهر لي حجمه 2 .. واذا كنتم تستعملون مترجم اخر فقيمة المتغير من الممكن ان تختلف .

اذا .. السؤال هو التالي ..

لو فرضنا كما هو الحال في جميع المترجمات ان int ياخذ 2 ..

ماهو سبب ضهور حجم الصنف الاول 1 على الرغم من انه فارغ .. بينما الصنف الثاني اضهر حجم الصنف 2 وهو نفسه حجم المتغير ..؟؟ ولم يضف اليه 1 كما في الصنف الفارغ ..لكي يصبح 3 .. (1 من الصنف و2 من المتغير 2 +1 = 3 ) ..؟؟؟؟؟؟؟

استخدموا القاعده التي اتبعها دائما في اي سؤال يطرح علي (بسيط كان ام صعب) .. فكر .. حلل .. اجب ..

انتظر ردودكم واجابتكم .. والاجابات تكون هنا بالموضوع لكي يستفيد الجميع فهو سؤال وليس لغز ..

تحياتي العطرة للجميع ...

يَارَبُ إِن ضَاقَت قُلُوُب الْنَّاسٍ عَنْ مّافِي .. مِنْ خَيْرٍٍ فَعَفْوكَ لَا يَضِيْقْ ..

#2

السلام عليكم ,,

ايه يا أخوانا سؤالين في ظرف 10 دقايق :D

حبة حبة علينا :P

عموماً هذا الشيئ يرجع للمترجم نفسه, و ليس من مواصفات لغة ++C نفسها,

و حجم الصنف في الحالة التي يكون فيه member variables هو حجم تلك المتغيرات,

أما في حالة كونه فارغاً فإنه من غير المنطقي أن يكون حجمه 0 bytes,

لماذا ؟

تصور أن الصنف كان فارغاً!

و قمنا بإنشاء مصفوفة من ذلك الصنف!

EmptyClass obj[5];

ماهو عنوان الكائن الخامس في المصفوفة! هو نفسه عنوان الكائن الأول! ليس هكذا تعامل الذواكر :D

أصغر حجم يمكن أن نحجزه في الذاكرة هو byte واحد, بالتالي يصبح حجم ذلك الكائن byte واحد فقط, من أجل تلافي المشاكل الناتجة عن ما يسمى بـ Zero Size Objects على ما أعتقد,

تحياتي أخ سنان و في انتظار الألغاز القادمة :P

#3

السلام عليكم:

أعتقد اي كلاس ينشئ مباشرتا دالة البناء وتكون باسم نفس الكلاس

يمكن الحجم حجم دالة البناء.

تم تعديل هذه المشاركة بواسطة فهدالشلوي في 15 فبراير 2008 في 13:58

tvquran_6.gif

#4
اقتباس
و حجم الصنف في الحالة التي يكون فيه member variables هو حجم تلك المتغيرات,

أما في حالة كونه فارغاً فإنه من غير المنطقي أن يكون حجمه 0 bytes,

ليست 100 % يا خالد ولكنك على مقربه من الحل ..

++++++++++++==========================+++++++++++++

اقتباس
السلام عليكم:

أعتقد اي كلاس ينشئ مباشرتا دالة البناء وتكون باسم نفس الكلاس

يمكن الحجم حجم دالة البناء.

لالا يا فهد .. اين كنا واين نحن الان ..

ارجع الى السؤال يا فهد وشاهد .. لقد كتبت في السؤال ( الصنف الفارغ ) اي انه لا يحتوي دالة بناء .. فمن اين اتيت بدالة البناء ومن اين اتيت بحجمها .. وحتى لو كانت دالة بناء فليست بها المشكله ..

===========

على العموم لي عود ان شاءلله لكي اوضح السبب من وراء ذلك .. ولكني انتظر قليلا هل من الممكن الاجابة .. ؟؟

تحياتي العطرة ..

يَارَبُ إِن ضَاقَت قُلُوُب الْنَّاسٍ عَنْ مّافِي .. مِنْ خَيْرٍٍ فَعَفْوكَ لَا يَضِيْقْ ..

#5

حسب علمي ان دالة البناء افتراضية تنشئ اذا لم يتم إنشاءها

والله أعلم

لكن حسب إجابة خالد تنشى مصفوفة طولها واحد وجحمها بايت.

tvquran_6.gif

#6

الجواب يا اخوان هو التالي ..

لنعيد كتابة الصنف مرة اخرى الان .. مع الدالة main .. وهو صنف مشابه للصنف x الذي في السؤال ( ايضا حجمه 1 بايت ) ..

class empty {
  };


}

هذا الكود هو لتعريف الصنف والذي اسمه empty . .. مميزات هذا الصنف انه فارغ ولا يحتوي اي بيانات في داخله ..

لنفرض اننا عرفنا كائنين من هذا الصنف

empty ob1, ob2;

كل كائن في لغة لسي ++ ياخذ حجم واحد بايت (اذا كان الصنف فارغا) وياخذ حجم بيانات الصنف اذا كان يحتوي على بيانات ومعلومات .. والسبب في ذلك .. هو لكي يكون لكل كائن عنوان خاص به .. فلو فرضنا ان الكائن الفارغ ياخذ حجم صفر بايت .. فسيكون للكائن نفس العنوان من الذاكرة.. فالكائنين اعلاه ob1 و ob2 .. لكل واحد منهما عنوان خاص به .. وكل واحد منهما ياخذ حجم الصنف المشتق منه وهو واحد بايت ...

class Empty { };

	void emfun()
	{
		Empty a, b;
		if (&a == &b) cout << "impossible: report error ";

		Empty* p1 = new Empty;
		Empty* p2 = new Empty;
		if (p1 == p2) cout << "impossible: report error ";
	}

في هذا المثال اعلاه .. الصنف الفارغ اعلاه empty يعرف كائنين a,b .. ومؤشرين p1 و p2 .. الكائنين ياخذان الحجم واحد بايت وقد انتهينا من هذا . .

ولكن انظروا الى الشرط ..

if (&a == &b) cout << "impossible: report error ";

هذا الشرط يختبر مساواة عناوين الكائنين a و b .. اذا كانا متساويين يطبع مستحييييل .. اي ان عنواوين الكائنات دائما دائما تكون مختلفة .. وهذا هو سبب اخذها للحجم واحد اذا كانت فارغه ..

اما بالنسبه للمؤشرين p1 و p2 .. فانها تشير الى بيانات من نوع الصنف نفسه وهو empty ..

عند اختبار مساواة قيم العنواوين التي تشير اليها هذين المؤشرين فانهما ايضا دائما غير متساووين ..

if (p1 == p2) cout << "impossible: report error ";

والسبب في ذلك هو ان العنوان الذي يحمله المؤشر الاول يختلف عن العنوان الذي يحمله المؤشر الثاني .. مما يؤدي الى ان يكون حجم الكائن واحد بايت ..

هذا السبب هو السبب العام لحصول هذا الامر .. وكملاحظة فان الهيكل الفارغ Empty Structure ايضا يحمل الحجم واحد بايت ..

وللسبب نفسه اعلاه ..

وهناك سبب اخر ولكن لا يمكننا الاعتماد عليه لتفسير هذه الحالة وهو ان الsizeof دائما لا ترجع صفر بايت ..بالنسبه لل(class, struct, or union type) .. حيث انها ترجع حجم هذه البيانات زائدا ما يسمى ب padding added بالنسبة للمحتويات .. ..

وهذا ما ورد من ال MSDN .. بالنسبه للسبب الثاني .. وهو سيكون اوضح من شرحي للنقطة الثانية ..

اقتباس
"When the sizeof operator is applied to a class, struct, or union type, the

result is the number of bytes in an object of that class, struct, or union

type, plus any padding added to align members on word boundaries. (The /Zp

[pack structure members] compiler option and the pack pragma affect alignment

boundaries for members.) The sizeof operator never yields 0, even for an

empty class."

ارجو ان تكونوا قد استفدتم شيئا ولو بسيطا من الاشياء العميقة في البرمجة الكائنية ..

اي شئ غير واضح في ما ورد اعلاه ارجو الاستفسار وانا حاضر في الخدمة ..

تحياتي العطرة ..

تم تعديل هذه المشاركة بواسطة سنان محمد صالح في 16 فبراير 2008 في 18:09

يَارَبُ إِن ضَاقَت قُلُوُب الْنَّاسٍ عَنْ مّافِي .. مِنْ خَيْرٍٍ فَعَفْوكَ لَا يَضِيْقْ ..

#7

أحسنت ياسنان معلومات قيمة بارك الله فيك.

ننتظر لغزك القادم لكن لا تستعجل عليه اهم شئ يكون قوي بما فيه الكفايه.

تم تعديل هذه المشاركة بواسطة فهدالشلوي في 16 فبراير 2008 في 19:42

tvquran_6.gif

#8
اقتباس
أحسنت ياسنان معلومات قيمة بارك الله فيك.

ننتظر لغزك القادم لكن لا تستعجل عليه اهم شئ يكون قوي بما فيه الكفايه.

اشكرك اخي فهد .. ان شاءالله هناك الغاز قادمة .. وقوية في نفس الوقت ..

تحياتي العطرة ..

يَارَبُ إِن ضَاقَت قُلُوُب الْنَّاسٍ عَنْ مّافِي .. مِنْ خَيْرٍٍ فَعَفْوكَ لَا يَضِيْقْ ..

هذا الموضوع مغلق.

مواضيع مشابهة