پیش نیاز های مقاله
توجه: ویدیو قرار داده شده فقط بخش اول از آموزش حلقه for در پایتون است. اگر قصد یادگیری بیشتر در مورد حلقه for و کلی مباحث دیگه در پایتون دارید، متونید دوره آموزش پایتون رو به صورت رایگان ببینید.
اولین نکته ای که باید بدونید اینه که حلقه ها (چه for چه while) بحث اختصاصی مروبط فقط به زبان پایتون نیستن.
اگر شما زبان های برنامه نویسی دیگه رو هم نگاه کنید دقیقا با بحث حلقه ها بر میخورید، فقط با سینتکس و نوشتاری متفاوت وگرنه مفهمومی دقیقا یک کار رو دارن انجام میدن.
کاربرد و دلیل استفاده از حلقه ها
فک کنید شما یک سایت آموزشی دارید و مثلا میخواید روز دانش آموز رو به همه کاربر هاتون تبریک بگید، ولی میخواید توی هر پیام اسم و فامیل کاربر رو هم توی متن پیام بفرستید.
خب اگر با دید برنامه نویسی بهش نگاه کنیم (به شکلی ساده) سریع متوجه دوتا نیاز میشیم:
- اول اینکه من چطور برای چندین هزار کاربری که دارم پیام ارسال کنم، یعنی تک به تک متن رو ارسال کنم؟!
- چون نیازه داخل هر پیام اسم و فامیل کاربر بیاد پس نمیشه یک متن کپی پیست بشه و برای همه ارسال بشه
خب اینجا اولین جایی هستش که شما نیاز به حلقه ها رو شدید احساس میکنید.
فلسفه پشت حلقه ها از این قراره:
ما یکسری دستور تکراری داریم که نیازه روی مجموعه ای از ایتم ها اعمالش کنیم (مثل ایتم های کاربر های سایت توی مثال بالا).
بر اساس خلاقیت هم میتونید پارامتر های داینامیک بزارید که برای هر ایتم مقادیری اختصاصی اون ایتم اعمال بشن (مثل همون اسم و فامیل ارسالی کاربر که متغیر هستش توی هر پیام).
حلقه for در پایتون چیست؟
حلقه for در python دستوری است که روی اعضای یک مجموعه حرکت میکنه و برای هر عضو از اون مجموعه بخشی از کد رو اجرا میکنه. این مجموعه میتونه لیست، رشته، دیکشنری، تاپل، range و.. باشه.
پس روی هر نوع داده ای میشه در پایتون حلقه for زد؟ واقعیت اینه که نه.
مثالی از سینتکس کلی حلقه for:
for item in iterable:
# کدی که برای هر آیتم اجرا می شود
print(item)اجزای ساختاری حلقه for:
- کلمه for شروع حلقه رو اعلام میکنه و یک کلمه رزرو شده در پایتون است.
- کلمه item مقدار ثابتی نداره، در واقع در هر دور از پیمایش مقدارش بر اساس ترتیب مجموعه عوض میشه.
نکته: بهتره که این اسم رو معنا دار انتخاب کنید، مثلا student برای لیست دانش آموزان. - کلمه in داره به پایتون میگه قراره روی چی پیمایش انجام بدی
- اون بخش Iterable هم باید جایگاه مجموعه قابل پیمایش شما باشه (مثل لیست، رشته، دیکشنری، تاپل، range و..) پایین تر Iterable کامل گفته شده.
- علامت (:) یا Colon یا دو نقطه: اگر در انتهای خط تعریف حلقه گذاشته نشود باعث SyntaxError ارور میشه.
- تورفتگی (Indentation) : این بخشی است که به مفسر پایتون میفهماند که چه کدهایی تحت نظر این حلقه هستن، شما با قرار دادن space یا فاصله به پایتون میگویید این کد ها تحت تاثیر این حلقه هستن که بر اساس استاندارد PEP8بهتر است 4 فاصله بگذارید.
توجه: اگر برای Indentation کمتر/بیشتر از 4 فاصله بگذارید ارور نمیگیرید، بلکه تنها ممکن از Syntax Warning بگیرید که بیشتر یک هشدار است تا یک ارور ولی از حالت استاندارد خارج شده اید.
اگر میخواید به استاندارد PEP8 مسلط تر بشید میتونید مقاله PEP8 چیست رو مطالعه کنید.
حلقه for قدم به قدم چطور داره اجرا میشه؟
کد زیر وظیفه جمع کردن چند عدد و محاسبه جمع کل هستش، حالا دور به دور ببینیم چی میشه:
numbers = [5, 10, 15]
total = 0
for n in numbers:
total = total + n
print(total) # 30| دوره حلقه | مقدار n | مقدار total بعد از یک دور |
|---|---|---|
| دور اول | 5 | 5 |
| دور دوم | 10 | 15 |
| دور سوم | 15 | 30 |
در دور سوم چون دیگه ایتمی در لیست باقی نمونده حلقه تموم میشه و بعد به دستور print میرسه و مقدار 30 چاپ میشه.
توجه:
# ورژن بلند
total = total + n
# ورژن کوتاه شد
total += nمنظور از Iterable Object در پایتون چیه؟ و چه فرقی با Iterate داره؟
به هر مجموعه ای در پایتون که بتونیم روی اون حلقه for اجرا کنیم بدون اینکه ارور object is not iterable رو بگیریم یعنی اون داده قابل پیمایش یا Iterableهستش.
پس به صورت کلی ابجکت های Iterable میشه روشون پیمایش کرد و حلقه for اجرا کرد.
ما به این عمل پیمایش که انجام میشه و روی ایتم های یک مجموعه حرکت میکنیم Iterate میگیم.
حلقه for else در پایتون چیست؟
یک ویژگی کمتر شناخته شده از حلقه for اینه که میتونه بخش else هم داشته باشه.
قانون ساده ای داره:
بخش else فقط وقتی اجرا میشود که حلقه بدون اینکه به دستور break بخوره تموم بشه، ساده ترش اینه بخش else همیشه بعد از تمام شدن حلقه اجرا میشود مگر اینکه حلقه به دستور break بر بخورد.
کار دستور break در حلقه ها:
دستور break در هر مرحله ای هم که باشه اگر حلقه بهش بر بخوره، حلقه پیمایشش تموم میشه و حلقه شکسته میشه و به پایان میرسه.
مثال:
numbers = [10, 20, 30, 40, 50]
for number in numbers:
if number == 30:
print("عدد پیدا شد!")
break
else:
print("عدد پیدا نشد!")در این حلقه چون در لیست عدد 30 وجود داره در پیمایش چون دستور break اجرا میشه هیچوقت بخش else اجرا نمیشه.
حالا اگر نزاریم دستور break اجرا بشه:
عدد 30 رو از لیست حذف کردیم
numbers = [10, 20, 40, 50]
for number in numbers:
if number == 30:
print("عدد پیدا شد!")
break
else:
print("عدد پیدا نشد!")اینجا دیگه در حین پیمایش به دستور break اجرا نمیشه پس بعد از اتمام حلقه بخش else اجرا میشه.
پیمایش لیست، رشته و دیکشنری با حلقه for
1. حلقه for روی لیست (List)
با اطمینان میشه گفت که رایج ترین کاربرد حلقه for در پایتون، پیمایش لیست (List) است.
مثال کاربردی
محاسبه تعداد قبولی ها یک کلاس بر اساس لیست نمرات کلاس:
scores = [18, 9, 15, 11, 7, 20]
passed = 0
for score in scores:
if score >= 10:
passed += 1
print("تعداد قبولی ها:", passed)خروجی:
تعداد قبولی ها: 4چه اتفاقی افتاد:
یک لیست 6 تایی از نمرات کلاس داشتیم ولی میخواستیم بفهمیم چند نفر بالای 10 شدن (نمره قبولی)، پس حلقه for رو با if ترکیب کردیم.
متغیر score که داره لیست رو پیمایش میکنه (در واقع در هر دور، نمره یک شخص رو درون خودش داره)، پس در هر دور حلقه شرط score بزرگتر مساوی 10 چک میشه و هر باری که نمره 10 یا بالاتر از 10 باشه یک عدد به متغیر passed اضافه میکنه.
پس بعد از اتمام حلقه متغیر passed داره تعداد ایتم هایی که بالاتر و مساوی 10 بودن رو درون خودش نگه میداره (همون تعداد قبولی ها).
2. حلقه for روی رشته (String)
رشته ها Iterable یا قابل پیمایش هستن (بر خلاف باور اولیه خیلی ها)، وقتی روی یک رشته حلقه زده میشه هر کارکتر درون رشته تبدیل به یک واحد در چرخه ی حلقه میشود.
نکته: فاصله و یا اسپیش هم یک ایتم حساب میشود و باعث یک دور چرخه کامل حلقه میشود.
مثال:
word = "GeekBaz"
for letter in word:
print(letter, end=" ")خروجی:
G e e k B a zتوجه: ارگومان end=" " که به print داده شد در واقع میگه بعد از هر چاپ به جای اینکه به خط بعد برود فقط بعد از چاپ یک فاصله بگذارد.
نکته: دلیل اینکه بعد از هر چاپی که با دستور print صورت میگیرد، چاپ بعدی در خط جدید صورت میگیرد این است که مقدار ارگومان end به صورت پیشفرض "\n" است.
3. حلقه for روی دیکشنری (Dict)
دیکشنری ها در پایتون Iterable هستن و قابلیت پیمایش دارند، ولی ساختار key value اون ها گول زننده است.
نکته طلایی که در رسیدن به درک درست از دیکشنری ها کمکتون میکنه:
هر جا که در پایتون دیکشنری ها (Dict) رو مستقیما به صورت Iterable استفاده کنیم، عمل iteration یا پیمایش به صورت پیش فرض روی کلیدها یا Keys دیکشنری ها انجام میشه.
مثال:
person = {
"name": "Saeed Amini",
"brand": "GeekBaz",
"age": 25
}
for item in person:
print(item)خروجی:
name brand ageتوضیح حلقه بالا:
ما وقتی که Person به حلقه for دادیم (که همون دادن یک دیکشنری به عنوان Iterable ) مشخص نکردیم که روی کلید ها حلقه زده بشه یا روی value ها.
پس بر اساس نکته بالا به صورت پیشفرض دیکشنری ها مقدار کلید ها رو برمیگردونن.
اگر بخوایم از رفتار پیشفرض دوری کنیم و دقیق مشخص کنیم روی کلید یا مقدار حلقه زده بشه باید با متدها .keys() .values() مشخصش کنیم.
با .keys():
person = {
"name": "Saeed Amini",
"brand": "GeekBaz",
"age": 25
}
for item in person.keys():
print(item)خروجی:
name brand age
با .values()
person = {
"name": "Saeed Amini",
"brand": "GeekBaz",
"age": 25
}
for item in person.values():
print(item)خروجی:
Saeed Amini GeekBaz 25
یه وقت هایی هست که ما توی هر پیمایش به صورت همزمان نیاز دارم که هم کلید رو داشته باشیم و هم مقدار رو، پس با استفاده از متد .items یک تاپل میگیریم که ساختاری به شکل (key, value) داره و دیگه میتونید بر اساس منطقی که در حلقه مینویسید ازش استفاده کنید:
person = {
"name": "Saeed Amini",
"brand": "GeekBaz",
"age": 25
}
for item in person.items():
print(item)خروجی:
('name', 'Saeed Amini') ('brand', 'GeekBaz') ('age', 25)حلقه تو در تو در پایتون (Nested Loop)
وقتی که یک حلقه داخل یک حلقه دیگه قرار بگیره، بهش حلقه تو در تو میگن. به ازای هر دور حلقه بیرونی، ممکن است حلقه درونی کامل اجرا شود یا ممکن است اصلا اجرا نشود، کاملا بستگی به منطق کد شما دارد، بیاد با مثال حرفم رو بگم:
توجه: برای درک بهتر این بخش پیشنهادم میکنم ویدیوی آموزش تابع range در پایتون رو ببینید.
for i in range(5):
print("بیرونی:", i)
if i % 2 == 0:
for j in range(3):
print(" داخلی:", j)خروجی:
بیرونی: 0
داخلی: 0
داخلی: 1
داخلی: 2
بیرونی: 1
بیرونی: 2
داخلی: 0
داخلی: 1
داخلی: 2
بیرونی: 3
بیرونی: 4
داخلی: 0
داخلی: 1
داخلی: 2توضیح:
اینجا با هر بار اجرا شدن حلقه بیرونی، کد های مربوط به اون حلقه اجرا میشن، ولی حلقه درونی با شرط زوج بودن i اجرا میشه (if i % 2 == 0)، پس وقتی به حلقه دوم میرسیم قطعا مقدار j زوج خواهد بود: for j in range(3) .
اخطار:
اگر به منطق حلقه ها دقت نکنید اگر حلقه بیرونی 100 بار تکرار شود و حلقه درونی هم 100 بار، کد داخلی 10 هزار برا اجرا میشود و در داده های بزرگ، سرعت برنامه رو پایین میاره.
حالا فک کنید هر حلقه بیشتر از 100 بار باشه و بعد حساب کنید چقدر میتونه اسیب زا بشه اگر کنترل نشه.
علامت _ در حلقه for یعنی چه؟
وقتی در یک حلقه فقط تکرار براتون مهمه و به تک تک ایتم هایی که از اون حلقه میکشید بیرون نیاز ندارید ولی میخواید این رو توی سینتکس هم نشون بدید که برنامه نویس دیگه ای کدتون رو خوند سریع متوجه بشه که اصلا برای این بخش به ایتم ها نیازی نبوده بلکه هدف تکرار کد بوده، از _ استفاده میکنید.
for _ in range(3):
print("سلام!")
خلاصه
دستور for که میشه گفت یکی از مهم ترین مفاهیم و پرکاربردترین در زبان های برنامه نویسی و همچنین پایتون هستش رو به صورت مقدماتی در حد آشنایی در این مقاله آشنا شدیم.
اگر میخواید کامل تر حلقه ها رو با مثال و مینی پروژه یاد بگیرید، پیشنهاد میکنم دوره رایگان آموزش پایتون رو حتما ببینید.
| مفهوم | کاربرد | نمونه کد |
|---|---|---|
| حلقه for ساده | پیمایش آیتم های یک مجموعه | for item in items: |
| دستور break | توقف کامل حلقه | if found: break |
| ساختار for else | اجرا فقط وقتی حلقه بدون break تمام شود | else: هم تراز با for |
| حلقه تو در تو | کار با داده های جدولی و دو بعدی و... | یک for داخل بدنه for دیگر |
| علامت _ در حلقه ها | کمک به درک کسانی که کد شما رو میخونن | for _ in range(3) |