الإجابة المختصرة هي: يحدث هذا الخطأ عندما تحاول الوصول إلى عنصر خارج نطاق قائمتك. أما الإجابة الطويلة فهي أكثر إثارة للاهتمام. للوصول إلى هذه الإجابة، سنتعلم الكثير عن كيفية عمل القوائم، وكيفية فهرسة الأشياء بالطريقة السيئة والطريقة الجيدة، وأخيرًا كيفية حل الخطأ المذكور أعلاه.
هذه المقالة موجهة للمبتدئين في بايثون الذين لديهم خبرة قليلة في البرمجة. إن فهم هذا الخطأ في وقت مبكر سيوفر لك الكثير من الوقت في المستقبل. إذا كنت تبحث عن بعض المواد التعليمية، فإن مسار أساسيات بايثون الخاص بنا يتضمن 3 دورات تفاعلية مجمعة معًا لمساعدتك على البدء.
فهرسة قوائم بايثون
القوائم هي واحدة من أكثر هياكل البيانات فائدة في بايثون. وتأتي مع مجموعة كاملة من التوابع المفيدة. تشمل هياكل البيانات الأخرى في بايثون الثنائيات والمصفوفات والقواميس والمجموعات، لكننا لن نتطرق إلى تفاصيلها هنا. للحصول على خبرة عملية مع هذه الهياكل، لدينا دورة تدريبية حول هياكل البيانات في بايثون وهي مناسبة للمبتدئين.
يمكن إنشاء القائمة على النحو التالي:
>>> x = [1, 'a', 2.3, [0, 1], 1, 4]
بدلاً من استخدام الأقواس المربعة ([]
) لتعريف قائمتك، يمكنك أيضًا استخدام الدالة المضمنة list()
.
هناك بالفعل بعض الأشياء المثيرة للاهتمام التي يجب ملاحظتها حول المثال أعلاه. أولاً، يمكنك تخزين أي نوع بيانات في قائمة، مثل عدد صحيح أو سلسلة أو رقم فاصلة عائمة أو حتى قائمة أخرى. ثانيًا، لا يلزم أن تكون العناصر فريدة: يظهر العدد الصحيح 1 مرتين في المثال أعلاه.
يتم فهرسة العناصر في القائمة بدءًا من 0. لذلك، للوصول إلى العنصر الأول، قم بما يلي:
>>> print(x[0])
تحتوي قائمتنا على 6 عناصر، يمكنك الحصول عليها باستخدام الدالة المضمنة len()
. للوصول إلى العنصر الأخير في القائمة، يمكنك محاولة القيام بما يلي ببساطة:
>>> print(x[6])
IndexError: list index out of range
هذا يعادل print(x[len(x)])
. نظرًا لأن فهرسة القائمة تبدأ من 0، فإن العنصر الأخير له فهرس len(x)–1
. عندما نحاول الوصول إلى الفهرس len(x)
، نكون خارج نطاق القائمة ونحصل على الخطأ. تبدو الطريقة الأكثر قوة للحصول على العنصر الأخير من القائمة على النحو التالي:
>>> print(x[len(x)-1])
على الرغم من أن هذه الطريقة تعمل، إلا أنها ليست الطريقة الأكثر تشابهًا مع بايثون. هناك طريقة أفضل تستغل ميزة رائعة للقوائم – وهي أنه يمكن فهرستها من نهاية القائمة باستخدام رقم سلبي كمؤشر. يمكن طباعة العنصر الأخير على النحو التالي:
>>> print(x[-1])
4
يمكن الوصول إلى العنصر قبل الأخير باستخدام الفهرس -2، وهكذا. وهذا يعني أن استخدام الفهرس -6 سيعيدك إلى العنصر الأول.
لننتقل إلى خطوة أبعد:
>>> print(x[-7])
IndexError: list index out of range
لاحظ هذا التباين. كان الخطأ الأول هو محاولة الوصول إلى العنصر بعد العنصر الأخير بالمؤشر 6، وكان الخطأ الثاني هو محاولة الوصول إلى العنصر قبل العنصر الأول بالمؤشر -7. ويرجع هذا إلى الفهرسة الأمامية التي تبدأ من 0 (بداية القائمة)، والفهرسة الخلفية التي تبدأ من -1 (نهاية القائمة). ويظهر ذلك بيانيا أدناه:

التكرار عبر القوائم
عندما تعمل مع القوائم، ستحتاج إلى معرفة الحلقات. تتيح لك الحلقة تكرار جميع العناصر في القائمة.
أول نوع من الحلقات التي سنلقي نظرة عليها هو حلقة while
. يجب أن تكون أكثر حذرًا مع حلقات while، لأن الخطأ الصغير سيجعلها تعمل إلى الأبد، مما يتطلب منك إجبار البرنامج على الخروج. مرة أخرى، دعنا نحاول تكرار قائمتنا:
>>> i=0
>>> while i <= len(x):
... print(x[i])
... i+=1
1
a
2.3
[0, 1]
1
4
IndexError: list index out of range
في هذا المثال، نحدد الفهرس الخاص بنا، i
، ليبدأ من الصفر. بعد كل تكرار لحلقة while
، نطبع عنصر القائمة ثم ننتقل إلى الفهرس التالي باستخدام عامل التعيين +=
. (هذه خدعة بسيطة أنيقة، تشبه القيام بـ i=i+1
.)
بالمناسبة، إذا نسيت السطر الأخير، فسوف تحصل على حلقة لا نهائية.
لقد واجهنا خطأ الفهرس لنفس السبب كما في القسم الأول – العنصر الأخير له فهرس len(x)-1. فقط قم بتعديل شرط عبارة while ليعكس هذا، وسوف يعمل بدون مشاكل.
سيتم تنفيذ معظم عمليات التكرار باستخدام حلقة for
، والتي سنوجه انتباهنا إليها الآن. تتمثل الطريقة الأفضل للتكرار عبر العناصر في قائمتنا دون المخاطرة بالوقوع في خطأ الفهرس في الاستفادة من الدالة المضمنة range()
. تتطلب هذه الطريقة ثلاث وسيطات، ولا يتطلب منها سوى وسيطة stop
. جرِّب ما يلي:
>>> for i in range(len(x)):
... print(x[i])
1
a
2.3
[0, 1]
1
4
إن الجمع بين الدالتين المضمنتين range()
وlen()
يتولى أمر القلق بشأن متى يجب التوقف عن فهرسة قائمتنا لتجنب خطأ الفهرس خارج النطاق تمامًا. ومع ذلك، فإن هذه الطريقة مفيدة فقط إذا كنت مهتمًا بمعرفة الفهرس.
على سبيل المثال، ربما تريد طباعة الفهرس والعنصر. في هذه الحالة، كل ما عليك فعله هو تعديل عبارة print()
إلى print(i, x[i])
. حاول القيام بذلك بنفسك لترى النتيجة. بدلاً من ذلك، يمكنك استخدام دالة enumerate()
في Python.
إذا كنت تريد فقط الحصول على العنصر، فهناك طريقة أبسط وأكثر سهولة في الاستخدام. ما عليك سوى التنقل عبر عناصر القائمة مباشرةً:
>>> for element in x:
... print(element)
1
a
2.3
[0, 1]
1
4
def get_value(index):
x = [1, 'a', 2.3, [0, 1], 1, 4]
return x[index]
إذا أدخل المستخدم فهرسًا خارج نطاق القائمة (على سبيل المثال 6)، فسيواجه خطأ فهرس القائمة مرة أخرى. يمكننا تعديل الوظيفة للتحقق من قيمة الإدخال باستخدام عبارة if
:
def get_value(index):
x = [1, 'a', 2.3, [0, 1], 1, 4]
if -len(x) <= index and index <= len(x)-1:
result = x[index]
else:
result = 'Index out of range. Try again.'
return result
يؤدي القيام بذلك إلى منع تعطل برنامجنا إذا كان الفهرس خارج النطاق. يمكنك حتى استخدام فهرس سلبي في الوظيفة أعلاه.
توجد طرق أخرى للتعامل مع الأخطاء في بايثون والتي ستساعدك على تجنب الأخطاء مثل “فهرس القائمة خارج النطاق”. على سبيل المثال، يمكنك تنفيذ كتلة try-except
بدلاً من عبارة if-else
.
لرؤية كتلة try-except
أثناء العمل، دعنا نتعامل مع خطأ الفهرس المحتمل في دالة get_value()
التي كتبناها أعلاه. يبدو منع الخطأ على النحو التالي:
def get_value(index):
x = [1, 'a', 2.3, [0, 1], 1, 4]
try:
result = x[index]
except IndexError:
result = 'Index out of range. Try again.'
return result
كما ترى على الأرجح، فإن الطريقة الثانية أكثر إيجازًا وسهولة في القراءة. كما أنها أقل عرضة للخطأ من التحقق صراحةً من مؤشر الإدخال باستخدام عبارة if-else
.
إتقان خطأ “قائمة الفهرس خارج النطاق” في بايثون
يجب أن تعرف الآن ما يعنيه خطأ الفهرس خارج النطاق في بايثون، ولماذا يظهر، وكيفية منع ظهوره في برامج بايثون الخاصة بك.
الطريقة المفيدة لتصحيح هذا الخطأ وفهم كيفية تشغيل برامجك هي ببساطة طباعة الفهرس ومقارنته بطول القائمة.
قد يحدث هذا الخطأ أيضًا عند تكرار هياكل بيانات أخرى، مثل المصفوفات أو المجموعات أو حتى عند تكرار سلسلة. يختلف استخدام السلاسل قليلاً عن استخدام القوائم.
اكتشاف المزيد من بايثون العربي
اشترك للحصول على أحدث التدوينات المرسلة إلى بريدك الإلكتروني.