إذا كنت تريد جمع عناصر List تحقق شرطًا معينًا في Python، فلا تحتاج غالبًا إلى إنشاء قائمة جديدة أو كتابة حلقة طويلة. النمط الأكثر مباشرة هو دمج sum() مع Generator Expression مثل: sum(x for x in numbers if condition). بهذه الطريقة تختار العناصر المطابقة للشرط ثم تجمعها مباشرة.
في بايثون بالمثال 9 سنركز على الجمع الشرطي: جمع الأعداد الزوجية، والموجبة، والقيم الأكبر من حد معين، ثم جمع قيم من list of dictionaries وتجاهل العناصر غير الرقمية عند الحاجة. أما شرح جمع كل عناصر القائمة باستخدام sum() وfor loop فهو مغطى في درس مستقل: بايثون بالمثال 4: حساب مجموع عناصر List في Python بأكثر من طريقة.
{getToc} $title={محتوى المقال}
{alertInfo} الخلاصة السريعة: اكتبsum(expression for item in iterable if condition). الجزء بعدifيحدد العناصر التي تدخل في المجموع، والجزء قبلforيحدد القيمة التي سيتم جمعها.
الصيغة الأساسية لجمع عناصر List حسب شرط
لنبدأ بقائمة أرقام:
numbers = [5, 12, 8, 20, 3]
total = sum(x for x in numbers if x > 10)
print(total)
الناتج:
32
العنصران المطابقان للشرط هما 12 و20، ولذلك يكون المجموع 32.
كيف يعمل sum مع Generator Expression؟
الصيغة العامة هي:
sum(expression for item in iterable if condition)
| الجزء | وظيفته |
|---|---|
expression | القيمة التي ستدخل في عملية الجمع. |
for item in iterable | المرور على عناصر القائمة أو أي iterable. |
if condition | السماح فقط للعناصر التي تحقق الشرط. |
وتوضح وثائق Python أن Generator Expression تنتج iterator، ويمكن حذف أقواسها الخاصة عندما تكون الوسيط الوحيد داخل استدعاء مثل sum(). لذلك نكتب:
total = sum(x for x in numbers if x > 10)
ولا نحتاج إلى إنشاء List مؤقتة مثل [x for x in numbers if x > 10] ما دام هدفنا الوحيد هو تمرير القيم مباشرة إلى sum().
جمع الأعداد الزوجية في List
نستخدم الشرط x % 2 == 0 لاختيار الأعداد الزوجية فقط:
numbers = [1, 2, 3, 4, 5, 6]
even_total = sum(x for x in numbers if x % 2 == 0)
print(even_total)
الناتج هو 12 لأن 2 + 4 + 6 = 12.
جمع الأعداد الموجبة فقط
numbers = [10, -5, 20, 0, -1, 30]
positive_total = sum(x for x in numbers if x > 0)
print(positive_total)
الناتج:
60
جمع القيم الأكبر من حد معين
إذا كان الحد متغيرًا، لا تكتبه داخل الشرط بشكل ثابت:
numbers = [10, 25, 40, 5, 55, 12]
threshold = 20
total = sum(x for x in numbers if x > threshold)
print(total)
الناتج 120 من 25 + 40 + 55.
جمع القيم التي تحقق أكثر من شرط
يمكن دمج أكثر من شرط باستخدام and. المثال التالي يجمع الأعداد الزوجية والموجبة فقط:
numbers = [-4, -1, 2, 5, 8]
total = sum(
x for x in numbers
if x > 0 and x % 2 == 0
)
print(total)
القيم المطابقة هي 2 و8، لذلك الناتج 10.
جمع قيم من list of dictionaries
هذه حالة عملية مهمة. لنفترض أن لدينا منتجات ونريد جمع أسعار المنتجات المتاحة فقط:
products = [
{"name": "Keyboard", "price": 40, "available": True},
{"name": "Mouse", "price": 25, "available": False},
{"name": "Monitor", "price": 180, "available": True},
]
total = sum(
product["price"]
for product in products
if product["available"]
)
print(total)
الناتج 220. لاحظ أن ما نجمعه هنا هو product["price"]، بينما الشرط يفحص product["available"].
ماذا لو كان بعض القواميس لا يحتوي على المفتاح؟
إذا كنت تريد جمع قيمة مفتاح مع السماح بعدم وجوده في بعض العناصر، يمكنك استخدام get() بقيمة افتراضية:
items = [
{"price": 50},
{"name": "Free sample"},
{"price": 30},
]
total = sum(item.get("price", 0) for item in items)
print(total)
الناتج 80. القيمة الافتراضية 0 تمنع KeyError عندما لا يوجد المفتاح price.
تجاهل القيم غير الرقمية أثناء الجمع
إذا كانت القائمة مختلطة الأنواع، فإن تمريرها مباشرة إلى sum() قد يسبب TypeError. يمكنك تصفية عناصر int وfloat أولًا:
values = [10, "Python", 5.5, True, None, 20]
total = sum(
value
for value in values
if isinstance(value, (int, float))
and not isinstance(value, bool)
)
print(total)
الناتج 35.5. استبعدنا bool صراحةً لأن bool نوع فرعي من int في Python، وبالتالي قد تدخل True في الحساب كقيمة 1 إذا استخدمنا isinstance(value, int) وحدها.
{alertWarning}
إذا كانت النصوص تمثل أرقامًا مثل "30" فلا تتجاهلها تلقائيًا إن كانت مهمة؛ حولها بعد التحقق من صلاحيتها. أما هذا المثال فهو للحالة التي تريد فيها تجاهل الأنواع غير الرقمية أصلًا.
Generator Expression أم List Comprehension؟
الطريقتان يمكن أن تعطيَا النتيجة نفسها:
numbers = [1, 2, 3, 4, 5, 6]
a = sum(x for x in numbers if x % 2 == 0)
b = sum([x for x in numbers if x % 2 == 0])
print(a, b)
في الحالة الأولى تمر القيم إلى sum() عبر Generator Expression دون إنشاء List وسيطة كاملة، ولذلك تكون مناسبة جدًا عندما لا تحتاج القائمة المفلترة بعد عملية الجمع.
هل يمكن استخدام filter() بدل Generator Expression؟
نعم:
numbers = [1, 2, 3, 4, 5, 6]
total = sum(filter(lambda x: x % 2 == 0, numbers))
print(total)
لكن في هذا النوع من الأمثلة، sum(x for x in numbers if ...) غالبًا أوضح قراءة لأنه يضع القيمة والشرط في تعبير واحد.
متى أستخدم for loop بدل sum مع شرط؟
استخدم for loop عندما لا يكون المطلوب مجرد جمع، بل تحتاج أثناء المرور إلى أكثر من عملية، مثل تسجيل سبب استبعاد العنصر أو تحديث أكثر من متغير. أما إذا كانت المهمة هي «اختيار عناصر بشرط ثم جمع قيمة منها»، فـsum() مع Generator Expression تكون عادةً أبسط.
| المطلوب | الصيغة المناسبة |
|---|---|
| جمع الأعداد الزوجية | sum(x for x in numbers if x % 2 == 0) |
| جمع الأعداد الموجبة | sum(x for x in numbers if x > 0) |
| جمع القيم الأكبر من حد | sum(x for x in numbers if x > threshold) |
| جمع قيمة من dictionaries حسب شرط | sum(d["price"] for d in data if condition) |
| تنفيذ إجراءات متعددة أثناء المرور | for loop |
أخطاء شائعة
وضع الشرط في المكان الخطأ
الصيغة المباشرة للتصفية هي expression for item in iterable if condition. الشرط يأتي بعد جزء for.
جمع Boolean بدون قصد
القيمتان True وFalse تتصرفان عدديًا كـ1 و0 في بعض العمليات. إذا كنت تنظف قائمة مختلطة وتريد الأرقام الحقيقية فقط، استبعد bool صراحة.
استخدام مفتاح غير موجود في Dictionary
الوصول إلى item["price"] يسبب KeyError إذا كان المفتاح غير موجود. استخدم get() فقط عندما تكون القيمة الافتراضية مثل 0 صحيحة منطقيًا في بياناتك.
أسئلة شائعة
كيف أجمع عناصر List بشرط في Python؟
استخدم sum() مع Generator Expression، مثل sum(x for x in numbers if x > 10).
كيف أجمع الأعداد الزوجية فقط؟
استخدم الشرط x % 2 == 0: sum(x for x in numbers if x % 2 == 0).
ما الفرق بين Generator Expression وList Comprehension داخل sum؟
الـList Comprehension تنشئ List جديدة أولًا، بينما Generator Expression تمرر القيم تدريجيًا إلى sum(). إذا لم تكن تحتاج القائمة الناتجة لاحقًا، فـGenerator Expression مناسبة أكثر.
كيف أجمع قيمة price من list of dictionaries؟
إذا كان المفتاح موجودًا في كل عنصر استخدم sum(item["price"] for item in products). ويمكنك إضافة if في النهاية لتطبيق شرط على المنتجات.
ماذا يحدث إذا لم يطابق أي عنصر الشرط؟
سيكون الـGenerator فارغًا، وsum() تعيد 0 عند استخدام قيمة البداية الافتراضية.
روابط داخلية مفيدة من بايثون العرب
- بايثون بالمثال 4: حساب مجموع عناصر List في Python بأكثر من طريقة
- عمليات Lists في Python: slicing وcopy والقوائم المتداخلة
- شرح if وelse في Python
- استخدام max وmin مع key في Python
مصادر رسمية
الخلاصة
عندما تريد جمع كل عناصر List مباشرة، يكفي sum(numbers) وهذا له درس مستقل. أما عندما تريد جمع عناصر تحقق شرطًا، فالنمط المهم هو sum(expression for item in iterable if condition).
استخدمه لجمع الأعداد الزوجية أو الموجبة أو الأكبر من قيمة، ويمكنك تغيير expression نفسها لجمع حقل مثل price من list of dictionaries. وإذا كانت البيانات مختلطة الأنواع، صفِّ القيم بعناية قبل الجمع بدل تمرير القائمة مباشرة إلى sum().
{alertSuccess} قاعدة الدرس: الشرط يحدد «من يدخل في المجموع»، والـexpression تحدد «ما القيمة التي سيتم جمعها».



