تابع all در پایتون — کاربرد به زبان ساده + فیلم آموزشی رایگان
تابع all در پایتون آنچنان قدرتمند است که آن را به کتابخانه داخلی و پیشفرض پایتون اضافه کردهاند. تابع all یکی از کاربردیترین ترفندهای پایتون به حساب میآید و درک نحوه استفاده از این تابع شرطی زنجیرهای میتواند باعث مختصر شدن، انعطافپذیری بیشتر و به اصطلاح «پایتونی شدن» (Pythonic) کدهای برنامه نویسان شود. کاربردها و موارد استفاده ممکن برای تابع all در پایتون محدودیت کمی دارند و بنابراین در این مقاله، برخی از کاربردهای اساسی و تعدادی از موارد پیشرفتهتر به همراه مثال نمایش داده شدهاند. امید است در این مقاله به مخاطبان ثابت شود که چرا همه برنامهنویسان پایتون باید هرچه زودتر نحوه استفاده از تابع all در پایتون را فرا بگیرند.
فیلم آموزشی تابع Any و All در پایتون
تابع all در پایتون چیست؟
تابع all() در پایتون یکی از توابع داخلی و پیشفرض به حساب میآید که تمام یک مجموعه را برای درستی یاTrue بودن مقادیر آن مورد ارزیابی قرار میدهد. میتوان از تابع all در پایتون به صورت سینتکس ایستا استفاده کرد یا اینکه پیادهسازی پویاتری را در ترکیب با ویژگیها و قابلیتهایی مثل «لیستهای مفهومی» (List Comprehension) و Generatorها (مولدها) را به همراه آن به کار گرفت. از تابع all در پایتون میتوان به همراه سایر قابلیتها و ترفندهای پایتون برای ساخت گزارههای شرطی کوتاه، واضح و قدرتمند استفاده کرد.
آموزش سریع تابع all در پایتون
در این بخش سعی شده است آموزش تابع all در پایتون به خلاصهترین شکل ممکن ارائه شود تا اگر زمان کافی برای مطالعه کامل این مقاله وجود ندارد، بتوان درک کلی و ابتدایی از چیستی و نحوه استفاده از آن بدست آورد.
تابع all در پایتون تمام یک مجموعه را به طور کامل برای یافتن شرطهایی وارسی میکند که مقدار آنها برابر با True ارزیابی ميشوند. یعنی اگر ارزش درستی تمام مقادیر یک موجودیت مجموعهوار مثل لیست در پایتون برابر با True باشند، خروجی تابع all همTrueخواهد بود و در غیر این صورت، خروجی تابع all در پایتونFalse است. برای درک بهتر این ترفند پایتونی در ادامه مثالی ساده ارائه شده است:
1# Have a collection of integers
2>>> nums = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
3# Check all items are integers
4>>> all(int(x) for x in nums)
5# That's a bingo
6True
کاربرد ساده و ابتدایی تابع all در پایتون
زبان برنامه نویسی پایتون شامل انواع تکرارگر (Iterable) بسیاری است که اکثر آنها در ادامه فهرست شدهاند:
- لیست در پایتون
- دیکشنری
- مجموعه
- مولد (Generator)
- رشته در پایتون
- سایر موارد
تابع all در پایتون را میتوان برای هر کدام از انواع داده فوق استفاده کرد. تابع all در پایتون را میتوان تقریباً معادل با این مفهوم در نظر گرفت که به ازای تمام مقادیر در یک لیست بررسی شود آیا ارزش درستی هر عضو برابر با True است یا خیر؟ در ادامه چند مورد استفاده ابتدایی از تابع all در پایتون به صورت مثالهایی ساده ارائه شدهاند.
۱. ارزیابی ابتدایی درستی با تابع all در پایتون
در این مورد استفاده ساده و پیشپا افتاده از تابع all در پایتون رفتار اصلی و کلیدی این تابع مشخص میشود. رفتار و عملکرد اصلی تابع all به این صورت است که بررسی میشود آیا ارزش تمام اقلام موجود در یک نوع داده تکرارگرTrueاست یا خیر؟ مثال مربوط به این بخش در ادامه ملاحظه میشود:
1# Create a list
2l = [0, 1, 2, 3, 4, 5]
3all(l)
4>>> False
در مثال فوق، تنها عضوی که باعث میشود نتیجه اجرای تابع all روی لیست l برابر باFalse شود، اولین عضو این لیست است؛ زیرا اولین عضو لیستl مقدار0 دارد که در منطق بولی ارزش آن برابر باFalse است. برای درک بهتر ارزش مقادیر مختلف، در ادامه چند مثال داخل یک قطعه کد ارائه شده است:
1# 1.Check the numerical value of False
2>>> 0 == False
3True
4# 2.Check the numerical value of True
5>>> 1 == True
6True
7# 3.Check for other values of True
8>>> 1 == True and 2 == True and 3 == True and 4 == True and 5 == True
9False
10# 4.Remove the 0 element from list, use all
11>>> all([1, 2, 3, 4, 5])
12True
13# 5.Check an empty list
14>>> all([])
15True
در ادامه توضیحاتی برای هر یک از مثالهای فوق ارائه شده است تا درک آنها سادهتر شود:
- در اولین مثال قطعه کد بالا در خط دوم بررسی شده است که آیا مقدار0 در پایتون برابر باFalse است که خروجیTrueخواهد بود. یعنی پاسخ مثبت است و مقدار صفر در پایتون با False در منطق بولی برابری دارد.
- در مثال دوم که در خط ۵ کدهای بالا آمده، نشان داده شده که ارزش درستی عدد 1 در پایتون برابر باTrue است.
- با اجرای مثال سوم (خط ۸) مشخص میشود که تنها ارزش عدد 1 برابر باTrue است و ارزش درستی سایر اعدادFalse میشود. جالب توجه است که نتیجه این مثال با مثال بعدی تناقض دارد.
- در مثال چهارم (خط ۱۱) با استفاده از تابع all بررسی شده است که آیا مقدار تمام مقادیر یک لیست ارزشTrue دارند یا خیر؟ برخلاف مثال قبلی، خروجی در این مثالTrue است. یعنی با قرار گرفتن چند عدد صحیح بزرگتر از ۲ در یک لیست و اِعمال تابع all روی آنها نتیجه برابر باTrueارزیابی شده؛ این در حالی است که در مثال قبلی حاصلand شرطهایTrue بودن اعداد بزرگتر از 1 برابر با False بدست آمده است.
- در مثال آخر (خط ۱۴) نیز مشاهده میشود که نتیجه ارزیابی یک لیست خالی با تابع all در پایتون نیز برابرTrue است.
مثالهای فوق ممکن است سردرگم کننده به نظر برسند، چون تناقضهایی در آنها دیده میشود. این حس سردرگمی البته چیزی به جز حس شیرین یادگیری چیزهایی جدید نیست. با مراجعه به مستندات پایتون مشخص میشود که:
تابع all در پایتون در صورتی مقدارTrue را بازمیگرداند که ارزش تمام اعضای تکرارگر (Iterable) مربوطه برابر با True باشند یا اینکه آن Iterable هیچ عضوی نداشته و پوچ باشد.
توضیحات فوق که مربوط به مستندات پایتون هستند ممکن است گیج کننده باشد، بنابراین بهتر است به بیان دیگر اینگونه توضیح داده شود که:
خروجی تابع all در پایتون در صورتیTrue خواهد بود که تمام عنصرهای نوع تکرارگر مورد نظر هیچکدامFlase نباشند. به لحاظ منطقی عبارتهایx is not False (ارزش متغیر فرضیx برابر باFlase نیست) و x is True(ارزشx برابر باTrue است) با هم معادل و یکسان هستند؛ اماx is not False در این مورد خاص یعنی در شرح نحوه عملکرد تابع all در پایتون واضحتر و قابلفهمتر است.
با درنظر داشتن توضیحات فوق، اکنون بهتر است اولین مثالی که در این مطلب ارائه شد، بار دیگر بررسی شود:
1# Create a list l = [0, 1, 2, 3, 4, 5]
2>>> all(l)
3False
4# Create another list
5l_2 = [1, 2, 3, 4, 5]
6>>> all(l_2)
7True
اولین عنصر یعنی عنصر صفرم لیست مربوطه در مثال فوق باعث شده است که خروجی نتیجه اجرای تابع all روی این لیست برابر باFalseشود. دلیلش این است که مقدار عدد0 در پشت پرده باFlase برابری دارد. با حذف مقدار صفر در لیست بالا، سایر عنصرها مقادیری غیر صفر دارند که معادل با غیرFlase یا not-Flase هستند.
معمولاً درک کلیت عملکرد هر نوع تابع مبتنی بر منطق دشوار است. مثالهای ارائه شده تا اینجا با هدف بهتر مشخص شدن جزئیات متفاوت تابع all در پایتون ارائه شدند تا بتوان مثالهای پیشرفتهتری که در ادامه آمدهاند را بهتر درک کرد.
معرفی فیلم های آموزش پایتون
در پلتفرم فرادرس تقریباً تمام دورههای مرتبط با آموزش پایتون در یک مجموعه آموزشی گردآوری شدهاند. علاقهمندان به برنامه نویسی پایتون و افرادی که میخواهند برنامه نویس پایتون شوند میتوانند برای شروع یادگیری پایتون از دورههای مقدماتی آن استفاده کنند. همچنین، چندین دوره آموزشی پروژهمحور نیز در این مجموعه برای ادامه یادگیری و تقویت مهارت برنامه نویسی پایتون در دسترس قرار دارند. جدیدترین دوره آموزشی این مجموعه دوره ترفندهای پایتون است که در آن ترفندهای استفاده از تابع all در پایتون هم شرح داده شدهاند. در تصویر فوق تنها برخی از دورههای آموزشی پروژهمحور مجموعه آموزش پایتون قابل ملاحظه هستند.
- برای دسترسی به همه آموزش های پایتون فرادرس + اینجا کلیک کنید.
کاربردهای پیشرفته تابع all در پایتون
بسیاری از کاربردهای تابع all در پایتون پویایی بیشتری دارند. در بیشتر مواقع میتوان با تابع all از سینتکسهای مفهومی برای بررسی تعدادی زیادی از عضویتها به عنوان یک گزاره شرطی برای اجرای منطقهایی دیگر استفاده کرد. به بیان دیگر، میتوان از سینتکس خلاصه و مختصر در پایتون بهرهمند شد. در این خصوص، میتوان مثال زیر را در نظر گرفت:
1from string import printable
2# Check if all letters of a string are in the
3# string.printable variable (ASCII characters)
4if all(x in printable for x in 'hello, world!'):
5 print("All Letters are ASCII!")
6else:
7 print("Non-ASCII letters found!")
8# The result:
9All letters as ASCII!
در مثال فوق با استفاده از تابع all بررسی شده است که آیا تمام حروف در رشته"hello, world!" در متغیرstring.printable قرار دارند یا خیر؟ یعنی بررسی میشود آیا تمام کارکترهای رشته"hello, world!"از نوع کاراکترهای اسکی (ASCII) هستند یا خیر؟
نکته: متغیرstring.printable برابر با رشته زیر است (البته به غیر از برخی از فضاهای سفید):
0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ!"#$%&'()*+,-./:;<=>?@[\]^_`{|}~
مثال فوق مورد استفاده و کاربرد سادهای از تابع all در پایتون را نشان میدهد که ممکن است برنامهنویسان در پروژههای خود با مواردی مشابه با آن مواجه شوند. بررسی برای چندین شرط عضویت روشی قدرتمند برای تصمیمگیری در مورد دادههای پیچیده یا پویا است. حال در ادامه مثالی پیچیدهتر ارائه شده است.
مثال تابع all در پایتون برای ترکیب گزاره ها با یکدیگر
در این بخش مثالی آمده که در آن تابع all در ترکیب با یکی دیگر از توابع داخلی پایتون یعنی تابع any به کار گرفته شده است. در این مثال با استفاده از مجموعه دادههایی ساختگی بررسی خواهد شد که آیا تمام کلیدهای اعضای یک دیکشنری حاوی هر یک از اعضای یک لیست هستند یا خیر؟ در واقع در این مثال ابتدا لیستی (با نامcolors ) حاوی رشتههایی ایجاد میشود که هر یک بیانگر رنگ فرضی خاصی هستند.
یک لیست هم حاوی اعداد ۱، ۲ و ۳ ساخته شده است. سپس یک دیکشنری (data ) با ترکیب تصادفی هر یک از این ۲ لیست ایجاد میشود. کلیدهای این دیکشنری ترکیبهای تصادفی دوتایی از لیستcolors هستند. در پایان با استفاده از تابع all در پایتون بررسی میشود که آیا از تمام اعضای لیست colorsدر تشکیل کلیدهای دیکشنری استفاده شده است یا خیر؟
1# Define a set of values
2colors = ['red', 'blue', 'green']
3numbers = [1, 2, 3]
4# Generate some random data
5>>> data = {
6 choice(colors) + "-" + choice(colors): choice(numbers) * choice(numbers)
7 for x in range(10)
8}
9{'blue-blue': 3, 'blue-red': 2, 'red-blue': 2, 'green-green': 6, 'red-green': 1, 'blue-green': 2}
10# Check that ALL members in 'data' contain ANY member of 'colors'
11>>> all(any(x in y for y in data.keys()) for x in colors)
12True
مثال فوق نهتنها مشخص کننده این مسئله است که چگونه میتوان از تابع all در پایتون به صورت پویا استفاده کرد، بلکه نشان دهنده کاربرد و فایده استفاده از گزارههای مفهومی پایتون نیز هست.
برای یادگیری عمیقتر تابع any در پایتون و مشاهده مثالهای بیشتر برای آن، مطالعه مقاله زیر پیشنهاد میشود:
- مقاله مرتبط: تابع any در پایتون — آموزش کاربردی به زبان ساده
مثال تابع all در پایتون برای استخراج آیتم ها و انتقال آن ها به مجموعه دیگر
از متد all در پایتون میتوان برای استخراج زیرمجموعههایی از مجموعهها استفاده کرد که در آنها نیاز به عضویت شرطی وجود دارد. در ادامه مثال مربوط به این مورد با استفاده از دادههای ساختگی ارائه شده است:
1# Create some random collection of numbers
2num_pairs = [(1, 3), (2, 4), (3, 6, 9), (1, 2, 3, 4), (4, 6, 8)]
3# Extract any pair of numbers where only even numbers are present
4evens = [x for x in num_pairs if all(n % 2 == 0 for n in x)]
5>>> evens
6
7# Results in sub-sets containing
8# only all-even values
9[(2, 4), (4, 6, 8)]
در مثال فوق از تابع all در پایتون برای بررسی جداسازی تاپلهایی در یک لیست استفاده شده است که تمام مقادیر آنها زوج باشند. برای هر تاپلی که حاوی هیچ مقدار غیر زوجی نباشد، سینتکس مفهومی پایتون آن آیتم را انتخاب خواهد کرد و آن را در مجموعه یا همان لیستی جدید به نام evens قرار خواهد داد.
ملاحظات پیشرفته تابع all در پایتون
در زمان تست مجموعههای بزرگ برای عضویت اعضای آنها، برخی مسائل و مشکلاتی مربوط به عملکرد وجود دارد. در مثال زیر از تابع all در پایتون برای بررسی لیستی از ۱۰۰ میلیون صفر و یک تولید شده به صورت تصادفی استفاده شده است و بعد با استفاده از تابع all بررسی میشود که آیا تمام اعضای این لیست از نوع عدد صحیح هستند یا خیر؟ پیش از بررسی این موضوع، در برنامه زیر یک کاراکتر از نوع غیر صحیح، یعنی کاراکتر رشتهای'z' هم به انتهای مجموعه مربوطه اضافه شده است.
1# Create a list 100MMK 1's or 0's, chosen randomly
2import random
3nums = list(random.choice([0, 1]) for x in range(10**8))
4# Add the letter "z" to the end
5nums.append('z')
6# Test that all members are numerical
7import timeit
8>>> timeit.timeit(lambda: all(type(x) == int for x in nums))
9# Total Execution Time
105.397376900000005
در قطعه کد بالا موارد زیر انجام شدهاند:
- ابتدا لیستی حاوی ۱۰۰ میلیون عدد ۱ و ۰ با ترتیب تصادفی ایجاد شده است.
- تنها یک کاراکتر رشتهای یعنی'z' به انتهای این لیست اضافه شده است.
- بررسی میشود که آیا تمام آیتمهای موجود در لیست مقادیری از نوع عدد صحیح هستند یا خیر؟
باید توجه شود که زمان اجرای کلی کدهای فوق در حالتی که کاراکتر 'z' در انتهای دنباله مربوطه آمده، تقریباً برابر با ۵٫۴ ثانیه است. این زمان تخمینی نشان میدهد که تابع all در پایتون قبل از حصول اطمینان از اینکه همه عناصر لیست مربوطه از نوع عدد صحیح هستند، نیاز دارد تا تمام اعضای آن را به صورت تک به تک بررسی کند و روی آنها تکرار انجام دهد.
حالا به فرض اگر کاراکتر'z' در ابتدای لیست قرار داشته باشد، دیگر منطقی نیست که تمام ۱۰۰ میلیون عضو این لیست تکبهتک تا انتها بررسی شوند. اما سازندگان پایتون باهوش هستند و به همین دلیل تابع all را بهگونهای طراحی کردهاند که به محض برخورد با یک مقدار غیرTrue بررسی باقی مقادیر متوقف میشود و همه عنصرها بهطور کامل بررسی نمیشوند. برای نشان دادن این موضوع، مثال فوق دوباره این بار در حالتی اجرا شده است که کاراکتر'z'در ابتدای لیست مربوطه قرار داده میشود:
1# Create a list 100MM 1's or 0's, chosen randomly
2import random
3nums = list(random.choice([0, 1]) for x in range(10**8))
4
5# Add the letter "z" to the start
6nums.insert(0, 'z')
7
8# Test that all members are numerical
9import timeit
10timeit.timeit(lambda: all(type(x) == int for x in nums), number=1)
11
12# A reeaaly small value
132.600000001962144e-06
البته دانستن این نکته درباره تابع all در پایتون چندان ضرورتی ندارد. اما با کسب آگاهی از نحوه توسعه توابع در پایتون و سایر زبانهای برنامه نویسی میتوان درک بهتری از آنها بدست آورد. مخصوصاً در مورد مشکلات مربوط به کیفیت عملکرد (زمان اجرا) این مسئله بسیار اهمیت دارد و میتوان بهتر مشخص کرد که در چه مواقعی بهتر است از چه توابعی استفاده شود.
جمعبندی
تابع all در پایتون یکی از پرکاربردترین ابزارها و ترفندهای پایتون به حساب میآید. طبق تجربه میتوان گفت که امکان بررسی دستهای وضعیت درستی بهطور روزانه بسیار کاربردی و مفید است. سایر زبانهای برنامه نویسی هم به نوعی قابلیتهای مشابهی را ارائه میدهند، اما تعداد کمتری از آنها به صورت از پیش آماده در سینتکس اصلی خود امکاناتی به این شکل و با این سطح از عملکرد مطلوب را ارائه میدهند. در ترکیب با generatorها، کدهای مفهومی و کمی تخیل تابع all میتواند کمک بزرگی به پیادهسازی قابلیتهای مورد نیاز در برنامهها بهگونهای بهینهتر و کارامدتر بکند.