مؤشرات الدوال

الناقل : elmasry | الكاتب الأصلى : Super_emad55 | المصدر : www.arabteam2000-forum.com

بسم الله الرحمن الرحيم,
أود أن اطرح موضوع ممتع و مهم و مخفي عن كثير من المبرمجين و هو "المؤشرات إلى دوال" أو ما يسمى "Function Pointers" لن أطيل عليكم بالمقدمة, لنبدأ بالتوضيحات,

لنفرض أن لدينا الدوال الاتية بداخل برنامج ما:

float Plus (float a, float b) { return a+b; }
float Minus (float a, float b) { return a-b; }
float Multiply (float a, float b) { return a*b; }
float Divide (float a, float b) { return a/b; }

فاذا اردنا استخدامها في برنامج معين, سوف نقوم بالاتي:
نكتب الداله الاتيه, لنستدعيها من الmain
float Switch(float a, float b, char opCode)
{
        float result;
        switch(opCode) // execute operation
        {
        case '+' : result = Plus (a, b); break;
        case '-' : result = Minus (a, b); break;
        case '*' : result = Multiply(a, b); break;
        case '/' : result = Divide (a, b); break;
        }
        return result;
}

ليكون ال main لدينا كالاتي:
void main()
{
        cout << Switch(10, 20, '+') << endl;
        cout << Switch(10, 20, '*') << endl;

}


للبرنامج اعلاه الامر واضح جدا.
الان هل ياترى نستطيع ان نبدل ‘+’ او ‘*’ باسم الداله نفسه؟؟!!
يعني هل نستطيع ان نقول بالاتي:
Instead of 
  Switch(10, 20, '+')
Can we do
 Switch(10, 20, Plus)

لحسن الحظ و لقوة لغة ال c++ نعم نستطيع, فكما ان اسم المصفوفه هو مؤشر لاول عنصر فيها, اسم الداله هو مؤشر لها !! معقول !!

نعم اخي, و كل ما تحتاجه هو ان تخبر ال compiler من أي نوع الداله هي.

الكثير ينتظر الامثله لكي يتضح الوضع.
حسنا هنا مثال واضح جدا:

لنفرض ان الداله التي نستخدمها هي

float Plus (float a, float b) { return a+b; }

فتكون الدالة المؤشره لداله بهذا الشكل
typedef float (* PF) (float a, float b)

typedef: دائما بهذا الشكل.
Float: نوع الداله الاصليه
(* PF): اسم المؤشر
(float a, float B): كما هو في الداله الاصليه


و الأن المفاجأه الكبرى, انظروا ماذا يمكننا ان نفعل الان

void main()
{
        PF my_function;
        my_function = Divide;

        cout << my_function(10, 20) << endl;
        cout << (* my_function)(10, 20) << endl;
}


قد تقول انا فهمت هذه
cout << my_function(10, 20) << endl;

ولكن ماهذا
cout << (* my_function)(10, 20) << endl;

اخي الكثير يحب ان يعمل برنامجه معقد و يصعب على الاخرين فهمه "هذا مرض بس اش نسوي :) "
هاتان الجملتان يقومان بنفس الوظيفه تماما.

ارجوا ان لا اكون اطلت الحديث, و لكن الموضوع لم ينتهي بعد, فالc++
بحر غميق لازم نتحلى بالصبر لنتخطاه.
سوف اكمل الشرح, اذا كان شرحي واضح و كلامي مفهوم.