تخطَّ إلى المحتوى
ARAB CODEمجتمع المطورين العرب

كيف تعمل البرمجة؟ من الكود الذي تكتبه إلى التعليمات التي ينفذها المعالج

درسنُشر ٢٤ أكتوبر ٢٠٢٦ · 0 رد · 1 مشاهدة#أساسيات#مبتدئ#مترجم#مفسر
قبل ساعتين

مقدمة

عندما تكتب print("مرحبا") وتضغط «تشغيل» تظهر الكلمة على الشاشة خلال جزء من الثانية. خلف هذه اللحظة سلسلة من الخطوات: تحويل النص الذي كتبته إلى تعليمات يفهمها المعالج، وحجز ذاكرة، وتنفيذ متتابع. فهم هذه السلسلة يجعلك تقرأ رسائل الأخطاء بثقة وتفهم لماذا يختلف أداء لغة عن أخرى.

أهداف التعلم

  • التمييز بين الكود المصدري ولغة الآلة.
  • فهم الفرق بين الترجمة المسبقة (Compilation) والتفسير (Interpretation) ومزيجهما.
  • معرفة دور الذاكرة والمكدس (Stack) والكومة (Heap) باختصار.
  • قراءة أي برنامج على أنه: مدخلات ← معالجة ← مخرجات.

1. المعالج لا يفهم إلا الأرقام

المعالج (CPU) ينفذ تعليمات بسيطة جداً مثل: اقرأ قيمة من الذاكرة، اجمع رقمين، قارن، اقفز إلى تعليمة أخرى. هذه التعليمات مخزنة كأرقام ثنائية تسمى لغة الآلة، وتختلف بين عائلات المعالجات (مثل x86-64 وARM). لا أحد تقريباً يكتب بلغة الآلة مباشرة؛ نكتب بلغات عالية المستوى ثم نحوّلها.

2. طريقتان رئيسيتان للتحويل

الترجمة المسبقة: برنامج اسمه المترجم (Compiler) يقرأ الكود كاملاً ويحوّله إلى ملف تنفيذي قبل التشغيل. أمثلة: C وC++ وGo وRust. الميزة سرعة التشغيل واكتشاف كثير من الأخطاء مبكراً؛ والثمن خطوة بناء إضافية وملف خاص بكل نظام.

// main.c
#include <stdio.h>
int main(void) {
    int total = 2 + 3;
    printf("المجموع = %d\n", total);
    return 0;
}
gcc main.c -o main   # الترجمة: ينتج ملفاً تنفيذياً
./main               # التشغيل

التفسير: برنامج اسمه المفسّر (Interpreter) يقرأ الكود وينفذه أثناء التشغيل. أمثلة تقليدية: Python وRuby. الميزة المرونة وسرعة التجربة؛ والثمن أداء أبطأ عادةً، وأخطاء لا تظهر إلا عند الوصول إلى السطر المعني.

المزيج الحديث: لغات مثل Java وC# تترجم إلى «شيفرة وسيطة» (Bytecode) ينفذها آلة افتراضية، وكثير من المحركات (مثل محرك V8 لـ JavaScript) تستخدم الترجمة الفورية (JIT) لتسريع الأجزاء التي تتكرر كثيراً. لذلك تقسيم «مترجمة/مفسرة» تبسيط مفيد لكنه ليس قاطعاً.

3. الذاكرة: أين تعيش المتغيرات؟

عندما يعمل البرنامج يحصل على ذاكرة من نظام التشغيل، ويُقسم جزء مهم منها إلى:

  • المكدس (Stack): سريع ومنظم، يُخزن فيه سياق كل استدعاء دالة ومتغيراتها المحلية، ويُحرر تلقائياً عند انتهاء الدالة. الاستدعاء الذاتي غير المنتهي يملؤه فتظهر رسالة مثل Stack Overflow أو RecursionError.
  • الكومة (Heap): للبيانات التي يُحدد حجمها أو عمرها أثناء التشغيل (قوائم كبيرة، كائنات). في C تحررها بنفسك، وفي Python وJava وJavaScript يحررها جامع القمامة تلقائياً.

4. كل برنامج: مدخلات ← معالجة ← مخرجات

# برنامج صغير يقرأ درجات ويطبع المتوسط
grades = [int(x) for x in input("أدخل الدرجات مفصولة بمسافات: ").split()]
average = sum(grades) / len(grades)
print(f"المتوسط: {average:.2f}")
  • المدخلات: نص من المستخدم.
  • المعالجة: تحويله إلى أرقام، جمعها، القسمة على العدد.
  • المخرجات: سطر على الشاشة.

اسأل نفسك هذه الأسئلة الثلاثة قبل كتابة أي برنامج، وستتضح الخطوات.

تمرين عملي

  1. اكتب برنامج المتوسط أعلاه بلغتك المفضلة وشغّله.
  2. أدخل سطراً فارغاً. ماذا حدث؟ (ستحصل على قسمة على صفر). عدّل البرنامج ليطبع رسالة واضحة بدلاً من الانهيار.
  3. إن كانت لغتك مترجمة، لاحظ متى ظهر خطأ نوع البيانات: أثناء الترجمة أم التشغيل؟

أخطاء شائعة

  • الخلط بين خطأ الترجمة وخطأ التشغيل: الأول يمنع البناء أصلاً، والثاني يظهر أثناء العمل وقد يعتمد على المدخلات.
  • افتراض أن المفسَّر «لا يحتاج اختباراً»: غياب خطوة الترجمة يعني أن أخطاء كثيرة لا تظهر إلا عند تنفيذ الفرع المعني، فالاختبارات أهم.
  • تجاهل نص رسالة الخطأ: معظم الرسائل تذكر الملف ورقم السطر ونوع المشكلة؛ اقرأها كاملة قبل البحث عنها.

الخلاصة

الكود الذي نكتبه نص يُحوَّل — بترجمة مسبقة أو تفسير أو مزيج منهما — إلى تعليمات بسيطة ينفذها المعالج، ويستخدم البرنامج الذاكرة بتنظيم واضح بين المكدس والكومة. هذا الفهم أساس لكل ما يأتي بعده: الأداء، والأخطاء، واختيار اللغة.

مصادر مقترحة

  • كتاب Code: The Hidden Language of Computer Hardware and Software لـ Charles Petzold.
  • دورة CS50 من جامعة هارفارد (متاحة مجاناً).
  • وثائق Python الرسمية: «The Python Tutorial».

الرد على الموضوع

سجّل الدخول للمشاركة في النقاش.

نقاشات مشابهة