JavaScript: الدوال في جافاسكريبت

آخر تحديث: 2026-10-13

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

تصريحات ذات صلة:setTimeout forEach filter return const let var map

1. ما هي الدالة؟

الدالة "تُغلّف" قطعة منطق، تعطيها اسمًا، وتتيح لك استدعائها متى احتجت:

HTML
<!DOCTYPE html>
<html lang="ar" dir="rtl">
<head><meta charset="UTF-8"><title>استدعاء الدوال</title></head>
<body>
<div id="output"></div>
<script>
function sayHello() {
  document.getElementById('output').textContent += 'مرحبا!\n';
}

sayHello();
sayHello();
</script>
</body>
</html>

فوائد الدوال:


2. إعلان الدالة مقابل تعبير الدالة

هناك طريقتان رئيسيتان لإنشاء الدوال:

HTML
<script>
// إعلان الدالة
function greet(name) {
  return `مرحبا، ${name}!`;
}

// تعبير الدالة
let greet2 = function(name) {
  return `مرحبا، ${name}!`;
};
</script>

الفرق الرئيسي: إعلانات الدوال تُرفع — يمكنك استدعائها قبل ظهورها في الكود. تعبيرات الدوال لا تُرفع; يجب تعريفها أولاً.

HTML
<script>
// إعلان الدالة: استدعاء قبل التعريف — يعمل بشكل جيد
hello();  // يعمل بدون خطأ
function hello() { console.log('مرحبا'); }

// تعبير الدالة: استدعاء قبل التعريف — خطأ
// hi();     // TypeError: hi is not a function
// let hi = function() { console.log('مرحبا'); };
</script>
⚠️ ملاحظة: الوصول إلى متغير let قبل إعلانه يُطلق خطأ "المنطقة الزمنية الميتة" (TDZ) — وليس undefined. لذلك عرّف دائمًا تعبيرات الدوال قبل استخدامها.


3. المعلمات والمعاملات الافتراضية

تقبل الدوال البيانات الخارجية عبر المعلمات:

HTML
<script>
function add(a, b) {
  return a + b;
}
add(1, 2);  // 3
</script>

المعلمات التي لا تمررها تكون undefined. قدم ES6 المعلمات الافتراضية:

HTML
<script>
function greet(name, greeting = 'مرحبا') {
  return `${greeting}، ${name}!`;
}

greet('سارة');           // 'مرحبا، سارة!'
greet('سارة', 'أهلا');    // 'أهلا، سارة!'
</script>
💡 تلميح: ضع المعلمات الافتراضية في نهاية القائمة. وضعها أولاً بلا معنى — لا يمكن للمتصلين تخطيها لتمرير اللاحقة.


4. القيم المُرجعة

return تُرسل نتيجة إلى المتصل وتوقف الدالة فورًا:

HTML
<script>
function square(n) {
  return n * n;
}

let result = square(5);  // 25
</script>

دالة بدون return (أو مع return; فقط) تُرجع undefined.

HTML
<script>
function doNothing() {
  // لا يوجد return
}
doNothing();  // undefined
</script>
⚠️ ملاحظة: سطر جديد بعد return يسبب إدخال نقطة فاصلة تلقائي، مما يجعلها تُرجع undefined:

return     // يصبح: return; undefined
  obj;     // هذا السطر لا يُنفذ أبدًا

الحل: احتفظ بالقيمة المُرجعة على نفس السطر، أو لفّها بأقواس.


5. الدوال السهمية (=>)

الدوال السهمية هي بنية أقصر قُدمت في ES6:

HTML
<script>
// دالة عادية
let double = function(n) {
  return n * 2;
};

// دالة سهمية
let double2 = (n) => n * 2;

// جمل متعددة تتطلب أقواسًا وreturn صريح
let greet = (name) => {
  let msg = `مرحبا، ${name}!`;
  return msg;
};
</script>

قواعد البناء:

▶ مثال: استخدام الدوال الأساسي

▶ جرّب الكود

▶ مثال: حاسبة بسيطة

▶ جرّب الكود

6. نطاق الدالة

المتغيرات المعلنة داخل دالة محلية — ت tồnيد فقط داخل تلك الدالة. هذا هو النطاق:

HTML
<script>
function test() {
  let x = 10;    // متغير محلي
  const y = 20;
  var z = 30;
}
test();
// console.log(x);  // ReferenceError: x is not defined
</script>

يمكن للدوال الوصول إلى المتغيرات الخارجية (أساس الإغلاق)، لكن الكود الخارجي لا يمكنه الوصول إلى المتغيرات داخل الدالة:

HTML
<!DOCTYPE html>
<html lang="ar" dir="rtl">
<head><meta charset="UTF-8"><title>نطاق الدالة</title></head>
<body>
<pre id="output"></pre>
<script>
let global = 'متغير عام';

function show() {
  let local = 'متغير محلي';
  document.getElementById('output').textContent +=
    'داخل الدالة — global: ' + global + '\n' +
    'داخل الدالة — local: ' + local + '\n';
}
show();
document.getElementById('output').textContent +=
  'خارج الدالة — global: ' + global + '\n' +
  'خارج الدالة — local: غير قابل للوصول (متغير محلي)';
</script>
</body>
</html>
⚠️ ملاحظة: تعيين متغير داخل دالة بدون let/const/var يُنشئ متغيرًا عامًا — مصدر شائع للأخطاء. أعلن دائمًا المتغيرات بـ let أو const.

▶ مثال: عرض النطاق

▶ جرّب الكود

7. مقدمة في الاستدعاءات الخلفية

جافاسكريبت تتيح لك تمرير دالة كوسيط لدالة أخرى — الدالة المُمرَّرة تسمى استدعاء خلفي:

HTML
<!DOCTYPE html>
<html lang="ar" dir="rtl">
<head><meta charset="UTF-8"><title>الاستدعاءات الخلفية</title></head>
<body>
<pre id="output"></pre>
<script>
function processArray(arr, callback) {
  for (let item of arr) {
    callback(item);
  }
}

let names = ['سارة', 'أحمد', 'محمد'];
processArray(names, function(name) {
  document.getElementById('output').textContent += 'مرحبا، ' + name + '\n';
});
</script>
</body>
</html>

لقد استخدمت بالفعل الاستدعاءات الخلفية — وسائط forEach وmap وfilter كلها دوال استدعاء خلفي:

HTML
<script>
// الدالة المجهولة هنا هي استدعاء خلفي
[1, 2, 3].forEach(function(n) {
  console.log(n);
});

// الدوال السهمية تجعلها أكثر اختصارًا
[1, 2, 3].forEach(n => console.log(n));
</script>
💡 تلميح: الاستدعاءات الخلفية هي روح جافاسكريبت. معالجات الأحداث، والمؤقتات، وطلبات الشبكة كلها تعتمد على آلية الاستدعاء الخلفي. في الوقت الحالي، فقط تذكر: "يمكن تمرير دالة كوسيط". سنذهب أعمق لاحقًا.

▶ مثال: الاستدعاءات الخلفية في العمل

▶ جرّب الكود

تصريحات ذات صلة:setTimeout forEach filter return const let var map

❓ أسئلة شائعة

س ما الفرق بين الدوال السهمية والدوال العادية؟
ج بالإضافة إلى بنية أقصر، الدوال السهمية ليس لها this الخاص بها — تُرثه من النطاق المحيط. عندما تحتاج this للإشارة إلى الكائن الحالي (في الأساليب أو معالجات الأحداث)، استخدم دالة عادية. للدوال البسيطة المساندة، بنية السهم تعمل بشكل رائع.
س هل يمكن لدالة إرجاع عدة قيم؟
ج ليس مباشرة، لكن يمكنك إرجاع مصفوفة أو كائن وإزالة هيكلته: function getInfo() { return [name, age]; } — ثم استدعِ بـ let [name, age] = getInfo().
س ماذا لو كان لدي معلمات كثيرة جدًا؟
ج عندما يكون لديك أكثر من 3 معلمات، فكّر في استخدام كائن: function createUser({ name, age, city }) {} — استدعِه بـ createUser({ name: 'سارة', age: 20, city: 'القاهرة' }). الترتيب لا يهم، وهو أكثر قراءة بكثير.

📖 ملخص


📝 تمارين

  1. أساسي (الصعوبة ⭐): اكتب دالة greet(name) تعيد "Hello, [name]!". اختبرها مع 3 أسماء مختلفة.
  2. متوسط (الصعوبة ⭐⭐): أنشئ دالة sum(a, b, ...rest) تقبل أي عدد من الوسائط وتعيد مجموعها. استخدم معامل الباقي.
  3. تحدي (الصعوبة ⭐⭐⭐): أنشئ دالة factorial(n) تحسب المضروب بشكل تكراري. أضف التحقق من المدخلات.
Web-Tutorial.com

فريق Web-Tutorial التقني

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

100%