JavaScript
المصفوفات والكائنات في JavaScript — دليل شامل 2026
📅 2026-09-26⏱ 11 دقائق قراءة
في المقال السابق، تعلمت الدوال وكيف تنظم الكود. لكن البرامج الحقيقية تحتاج إلى تخزين **مجموعات من البيانات** — قوائم، سجلات، جداول. هنا تأتي **المصفوفات (Arrays)** و **الكائنات (Objects)**.
في هذا الدليل العملي، سنأخذك خطوة بخطوة لفهم المصفوفات والكائنات في JavaScript — من الإنشاء إلى الطرق المتقدمة، مع تمارين وحلول.
## ما هي المصفوفة (Array)؟
المصفوفة هي **قائمة مرتبة** من القيم. كل قيمة لها **فهرس (index)** يبدأ من 0.
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
console.log(fruits[0]); // تفاح
console.log(fruits[1]); // موز
console.log(fruits[2]); // برتقال
```
**شرح:**
- **`[]`:** أقواس مربعة لتعريف مصفوفة.
- **`"تفاح"`:** عنصر (element).
- **`fruits[0]`:** الوصول للعنصر الأول (الفهرس يبدأ من 0).
## لماذا نحتاج المصفوفات؟
بدون المصفوفات:
```javascript
const fruit1 = "تفاح";
const fruit2 = "موز";
const fruit3 = "برتقال";
```
مع المصفوفات:
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
```
**الفوائد:**
- **تجميع البيانات:** كل العناصر في متغير واحد.
- **سهولة المرور:** استخدام الحلقات.
- **الطرق الجاهزة:** `push`, `pop`, `map`, `filter`...
- **المرونة:** يمكن إضافة أو حذف عناصر.
## إنشاء مصفوفة
### 1. الطريقة المباشرة:
```javascript
const numbers = [1, 2, 3, 4, 5];
const names = ["أحمد", "محمد", "علي"];
const mixed = ["نص", 25, true, null];
```
### 2. باستخدام `new Array()`:
```javascript
const arr = new Array(1, 2, 3);
```
**⚠️ نصيحة:** استخدم الطريقة المباشرة `[]` — أبسط وأسرع.
### 3. مصفوفة فارغة:
```javascript
const empty = [];
```
## الوصول إلى العناصر
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
console.log(fruits[0]); // تفاح
console.log(fruits[1]); // موز
console.log(fruits[2]); // برتقال
console.log(fruits[3]); // undefined (لا يوجد)
```
### آخر عنصر:
```javascript
console.log(fruits[fruits.length - 1]); // برتقال
```
### الطول (length):
```javascript
console.log(fruits.length); // 3
```
## تعديل المصفوفة
### إضافة عنصر في النهاية (push):
```javascript
const fruits = ["تفاح", "موز"];
fruits.push("برتقال");
console.log(fruits); // ["تفاح", "موز", "برتقال"]
```
### حذف آخر عنصر (pop):
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
fruits.pop();
console.log(fruits); // ["تفاح", "موز"]
```
### إضافة في البداية (unshift):
```javascript
const fruits = ["موز", "برتقال"];
fruits.unshift("تفاح");
console.log(fruits); // ["تفاح", "موز", "برتقال"]
```
### حذف من البداية (shift):
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
fruits.shift();
console.log(fruits); // ["موز", "برتقال"]
```
### تعديل عنصر:
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
fruits[1] = "عنب";
console.log(fruits); // ["تفاح", "عنب", "برتقال"]
```
## الطرق الشائعة للمصفوفات
### 1. `map` — تحويل كل عنصر
```javascript
const numbers = [1, 2, 3, 4];
const doubled = numbers.map((n) => n * 2);
console.log(doubled); // [2, 4, 6, 8]
```
### 2. `filter` — تصفية العناصر
```javascript
const numbers = [1, 2, 3, 4, 5, 6];
const even = numbers.filter((n) => n % 2 === 0);
console.log(even); // [2, 4, 6]
```
### 3. `find` — إيجاد أول عنصر يطابق الشرط
```javascript
const numbers = [10, 20, 30, 40];
const found = numbers.find((n) => n > 25);
console.log(found); // 30
```
### 4. `reduce` — تجميع المصفوفة إلى قيمة واحدة
```javascript
const numbers = [1, 2, 3, 4];
const sum = numbers.reduce((acc, n) => acc + n, 0);
console.log(sum); // 10
```
### 5. `forEach` — المرور على العناصر
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
fruits.forEach((fruit) => {
console.log(fruit);
});
```
### 6. `includes` — التحقق من وجود عنصر
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
console.log(fruits.includes("موز")); // true
console.log(fruits.includes("عنب")); // false
```
### 7. `indexOf` — إيجاد فهرس عنصر
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
console.log(fruits.indexOf("موز")); // 1
console.log(fruits.indexOf("عنب")); // -1 (غير موجود)
```
### 8. `slice` — نسخ جزء من المصفوفة
```javascript
const numbers = [1, 2, 3, 4, 5];
const part = numbers.slice(1, 4);
console.log(part); // [2, 3, 4]
```
### 9. `splice` — حذف/إضافة عناصر
```javascript
const numbers = [1, 2, 3, 4, 5];
numbers.splice(2, 1); // احذف عنصراً واحداً من الفهرس 2
console.log(numbers); // [1, 2, 4, 5]
```
### 10. `sort` — ترتيب المصفوفة
```javascript
const numbers = [3, 1, 4, 1, 5, 9, 2, 6];
numbers.sort((a, b) => a - b);
console.log(numbers); // [1, 1, 2, 3, 4, 5, 6, 9]
```
### 11. `reverse` — عكس المصفوفة
```javascript
const numbers = [1, 2, 3, 4];
numbers.reverse();
console.log(numbers); // [4, 3, 2, 1]
```
### 12. `join` — تحويل المصفوفة إلى نص
```javascript
const fruits = ["تفاح", "موز", "برتقال"];
const str = fruits.join(", ");
console.log(str); // "تفاح, موز, برتقال"
```
## جدول طرق المصفوفات الأساسية
<table>
<thead>
<tr>
<th>الطريقة</th>
<th>الوظيفة</th>
</tr>
</thead>
<tbody>
<tr>
<td><code>push()</code></td>
<td>إضافة في النهاية</td>
</tr>
<tr>
<td><code>pop()</code></td>
<td>حذف من النهاية</td>
</tr>
<tr>
<td><code>unshift()</code></td>
<td>إضافة في البداية</td>
</tr>
<tr>
<td><code>shift()</code></td>
<td>حذف من البداية</td>
</tr>
<tr>
<td><code>map()</code></td>
<td>تحويل كل عنصر</td>
</tr>
<tr>
<td><code>filter()</code></td>
<td>تصفية العناصر</td>
</tr>
<tr>
<td><code>find()</code></td>
<td>إيجاد أول عنصر</td>
</tr>
<tr>
<td><code>reduce()</code></td>
<td>تجميع إلى قيمة</td>
</tr>
<tr>
<td><code>forEach()</code></td>
<td>المرور على العناصر</td>
</tr>
<tr>
<td><code>includes()</code></td>
<td>التحقق من وجود عنصر</td>
</tr>
<tr>
<td><code>indexOf()</code></td>
<td>فهرس عنصر</td>
</tr>
<tr>
<td><code>slice()</code></td>
<td>نسخ جزء</td>
</tr>
<tr>
<td><code>splice()</code></td>
<td>حذف/إضافة</td>
</tr>
<tr>
<td><code>sort()</code></td>
<td>ترتيب</td>
</tr>
<tr>
<td><code>reverse()</code></td>
<td>عكس</td>
</tr>
<tr>
<td><code>join()</code></td>
<td>تحويل إلى نص</td>
</tr>
</tbody>
</table>
## ما هو الكائن (Object)؟
الكائن هو **مجموعة من أزواج "مفتاح: قيمة"**. يُستخدم لتمثيل كيان له خصائص متعددة.
```javascript
const person = {
name: "أحمد",
age: 25,
city: "عمان",
isStudent: true,
};
console.log(person.name); // أحمد
console.log(person.age); // 25
```
**شرح:**
- **`{}`:** أقواس معقوفة لتعريف كائن.
- **`name`:** مفتاح (key).
- **`"أحمد"`:** قيمة (value).
- **`:`:** فاصل بين المفتاح والقيمة.
- **`,`:** فاصل بين الخصائص.
## الوصول إلى خصائص الكائن
### 1. باستخدام النقطة (Dot Notation):
```javascript
console.log(person.name); // أحمد
```
### 2. باستخدام الأقواس المربعة (Bracket Notation):
```javascript
console.log(person["name"]); // أحمد
```
**متى تستخدم الأقواس؟** عندما يكون المفتاح متغيراً:
```javascript
const key = "name";
console.log(person[key]); // أحمد
```
## تعديل الكائن
### إضافة خاصية جديدة:
```javascript
person.email = "ahmed@example.com";
console.log(person.email); // ahmed@example.com
```
### تعديل خاصية موجودة:
```javascript
person.age = 26;
console.log(person.age); // 26
```
### حذف خاصية:
```javascript
delete person.isStudent;
console.log(person.isStudent); // undefined
```
## طرق الكائنات
### 1. `Object.keys()` — الحصول على المفاتيح
```javascript
const person = { name: "أحمد", age: 25, city: "عمان" };
console.log(Object.keys(person)); // ["name", "age", "city"]
```
### 2. `Object.values()` — الحصول على القيم
```javascript
console.log(Object.values(person)); // ["أحمد", 25, "عمان"]
```
### 3. `Object.entries()` — الحصول على الأزواج
```javascript
console.log(Object.entries(person));
// [["name", "أحمد"], ["age", 25], ["city", "عمان"]]
```
### 4. `Object.assign()` — دمج الكائنات
```javascript
const obj1 = { a: 1, b: 2 };
const obj2 = { c: 3, d: 4 };
const merged = Object.assign({}, obj1, obj2);
console.log(merged); // { a: 1, b: 2, c: 3, d: 4 }
```
### 5. Spread Operator — نسخ ودمج
```javascript
const obj1 = { a: 1, b: 2 };
const obj2 = { ...obj1, c: 3 };
console.log(obj2); // { a: 1, b: 2, c: 3 }
```
## المصفوفات داخل الكائنات
يمكن دمج المصفوفات والكائنات:
```javascript
const user = {
name: "أحمد",
age: 25,
hobbies: ["قراءة", "برمجة", "رياضة"],
address: {
city: "عمان",
country: "الأردن",
},
};
console.log(user.hobbies[0]); // قراءة
console.log(user.address.city); // عمان
```
## المصفوفات من الكائنات
```javascript
const users = [
{ name: "أحمد", age: 25 },
{ name: "محمد", age: 30 },
{ name: "علي", age: 20 },
];
// الوصول
console.log(users[0].name); // أحمد
console.log(users[1].age); // 30
// التصفية
const adults = users.filter((u) => u.age >= 25);
console.log(adults);
// [{ name: "أحمد", age: 25 }, { name: "محمد", age: 30 }]
// التحويل
const names = users.map((u) => u.name);
console.log(names); // ["أحمد", "محمد", "علي"]
```
## تمارين عملية
### تمرين 1: إنشاء مصفوفة
أنشئ مصفوفة بأسماء 5 فواكه، ثم اطبع أول وآخر فاكهة.
**الحل:**
```javascript
const fruits = ["تفاح", "موز", "برتقال", "عنب", "فراولة"];
console.log(fruits[0]); // تفاح
console.log(fruits[fruits.length - 1]); // فراولة
```
### تمرين 2: مجموع الأرقام
احسب مجموع مصفوفة أرقام.
**الحل:**
```javascript
const numbers = [10, 20, 30, 40, 50];
const sum = numbers.reduce((acc, n) => acc + n, 0);
console.log(sum); // 150
```
### تمرين 3: التصفية
من مصفوفة أرقام، استخرج الأرقام الأكبر من 10.
**الحل:**
```javascript
const numbers = [5, 15, 8, 20, 3, 25];
const bigNumbers = numbers.filter((n) => n > 10);
console.log(bigNumbers); // [15, 20, 25]
```
### تمرين 4: إنشاء كائن
أنشئ كائناً `book` يحتوي على:
- title, author, year, price
**الحل:**
```javascript
const book = {
title: "تعلم JavaScript",
author: "أحمد محمد",
year: 2026,
price: 49.99,
};
console.log(book.title); // تعلم JavaScript
console.log(book.author); // أحمد محمد
```
### تمرين 5: مصفوفة كائنات
أنشئ مصفوفة بـ 3 طلاب (اسم، عمر، درجة)، ثم:
- اطبع أسماء الطلاب.
- احسب متوسط الدرجات.
**الحل:**
```javascript
const students = [
{ name: "أحمد", age: 20, grade: 85 },
{ name: "محمد", age: 22, grade: 90 },
{ name: "علي", age: 21, grade: 78 },
];
// الأسماء
const names = students.map((s) => s.name);
console.log(names); // ["أحمد", "محمد", "علي"]
// المتوسط
const avg = students.reduce((acc, s) => acc + s.grade, 0) / students.length;
console.log(avg); // 84.33
```
### تمرين 6: دمج المصفوفات
ادمج مصفوفتين في واحدة.
**الحل:**
```javascript
const arr1 = [1, 2, 3];
const arr2 = [4, 5, 6];
const merged = [...arr1, ...arr2];
console.log(merged); // [1, 2, 3, 4, 5, 6]
```
### تمرين 7: البحث في مصفوفة كائنات
ابحث عن طالب باسم "محمد".
**الحل:**
```javascript
const students = [
{ name: "أحمد", age: 20 },
{ name: "محمد", age: 22 },
{ name: "علي", age: 21 },
];
const found = students.find((s) => s.name === "محمد");
console.log(found); // { name: "محمد", age: 22 }
```
### تمرين 8: ترتيب المصفوفة
رتب مصفوفة أرقام تصاعدياً وتنازلياً.
**الحل:**
```javascript
const numbers = [5, 2, 8, 1, 9, 3];
// تصاعدي
const asc = [...numbers].sort((a, b) => a - b);
console.log(asc); // [1, 2, 3, 5, 8, 9]
// تنازلي
const desc = [...numbers].sort((a, b) => b - a);
console.log(desc); // [9, 8, 5, 3, 2, 1]
```
## حل المشاكل الشائعة
### 🔴 المشكلة 1: `undefined` عند الوصول
**السبب:** الفهرس خارج نطاق المصفوفة، أو الخاصية غير موجودة.
```javascript
const arr = [1, 2, 3];
console.log(arr[10]); // undefined
const obj = { name: "أحمد" };
console.log(obj.age); // undefined
```
**الحل:** تحقق من الوجود:
```javascript
if (arr[10] !== undefined) { /* ... */ }
if ("age" in obj) { /* ... */ }
```
### 🔴 المشكلة 2: تعديل مصفوفة أثناء المرور عليها
**السبب:** إضافة/حذف عناصر أثناء `forEach` أو `for...of`.
**الحل:** انسخ المصفوفة أولاً:
```javascript
const arr = [1, 2, 3];
[...arr].forEach((item) => {
arr.push(item * 2); // آمن
});
```
### 🔴 المشكلة 3: مقارنة مصفوفات
**السبب:** المصفوفات تُقارن بالمرجع، وليس بالقيمة.
```javascript
console.log([1, 2] === [1, 2]); // false
```
**الحل:** استخدم `JSON.stringify` أو مقارنة عنصراً بعنصر:
```javascript
console.log(JSON.stringify([1, 2]) === JSON.stringify([1, 2])); // true
```
### 🔴 المشكلة 4: `sort` لا يعمل كما تتوقع
**السبب:** `sort` الافتراضي يحول العناصر إلى نصوص.
```javascript
const numbers = [10, 2, 5, 1];
numbers.sort();
console.log(numbers); // [1, 10, 2, 5] ⚠️
```
**الحل:** استخدم دالة مقارنة:
```javascript
numbers.sort((a, b) => a - b);
console.log(numbers); // [1, 2, 5, 10]
```
## جدول الأوامر الأساسية
<table>
<thead>
<tr>
<th>الأمر</th>
<th>الوظيفة</th>
</tr>
</thead>
<tbody>
<tr>
<td><code>const arr = [1, 2, 3];</code></td>
<td>إنشاء مصفوفة</td>
</tr>
<tr>
<td><code>const obj = { key: "value" };</code></td>
<td>إنشاء كائن</td>
</tr>
<tr>
<td><code>arr.push(x)</code></td>
<td>إضافة عنصر</td>
</tr>
<tr>
<td><code>arr.map(fn)</code></td>
<td>تحويل العناصر</td>
</tr>
<tr>
<td><code>arr.filter(fn)</code></td>
<td>تصفية العناصر</td>
</tr>
<tr>
<td><code>arr.reduce(fn, init)</code></td>
<td>تجميع إلى قيمة</td>
</tr>
<tr>
<td><code>obj.key</code></td>
<td>الوصول لخاصية</td>
</tr>
<tr>
<td><code>Object.keys(obj)</code></td>
<td>المفاتيح</td>
</tr>
<tr>
<td><code>Object.values(obj)</code></td>
<td>القيم</td>
</tr>
</tbody>
</table>
## قائمة تحقق نهائية
<table>
<thead>
<tr>
<th>المهمة</th>
<th>الحالة</th>
</tr>
</thead>
<tbody>
<tr>
<td>فهم المصفوفات وكيفية إنشائها</td>
<td>⬜</td>
</tr>
<tr>
<td>استخدام push, pop, shift, unshift</td>
<td>⬜</td>
</tr>
<tr>
<td>استخدام map, filter, reduce</td>
<td>⬜</td>
</tr>
<tr>
<td>فهم الكائنات وكيفية إنشائها</td>
<td>⬜</td>
</tr>
<tr>
<td>الوصول للخصائص وتعديلها</td>
<td>⬜</td>
</tr>
<tr>
<td>استخدام Object.keys, values, entries</td>
<td>⬜</td>
</tr>
<tr>
<td>حل التمارين الثمانية</td>
<td>⬜</td>
</tr>
</tbody>
</table>
## ماذا بعد هذا المقال؟
الآن بعد أن أتقنت المصفوفات والكائنات، أنت جاهز للمقال التالي:
1. **DOM** — التفاعل مع صفحات الويب.
2. **المشاريع العملية** — بناء تطبيقات حقيقية.
3. **Async/Await** — البرمجة غير المتزامنة.
## الخلاصة
في هذا المقال، تعلمت:
- ✅ ما هي المصفوفات وكيفية إنشائها.
- ✅ الوصول للعناصر وتعديلها.
- ✅ الطرق الشائعة: `push`, `pop`, `map`, `filter`, `reduce`...
- ✅ ما هي الكائنات وكيفية إنشائها.
- ✅ الوصول للخصائص وتعديلها.
- ✅ `Object.keys`, `values`, `entries`.
- ✅ دمج المصفوفات والكائنات.
**تذكر:** المصفوفات والكائنات هما العمود الفقري لأي تطبيق JavaScript. أتقنهما جيداً.
**هل أتقنت المصفوفات والكائنات؟ شاركنا في التعليقات!**