نوع داده تاپل (Tuple) در پایتون
تاپل ها (tuple) دقیقا شبیه به لیست ها هستند، با این تفاوت که در تاپل ها برعکس لیست نمی توان مقادیر عناصر تعریف شده را تغییر داد در صورتی که این کار در لیست ها به سادگی امکان پذیر بود. معمولا از تاپل ها برای تولید دنباله هایی با عناصر ناهمگن استفاده می شود، تفاوت بعدی در نحوه تعریف تاپل ها می باشد، که به آن خواهیم پرداخت.
فهرست مطالب
تعریف تاپل (tuple) در پایتون
یک تاپل با قرارداد عناصر آن داخل پرانتز ( ) به شکلی که عناصر با کاما ( ، ) از هم جدا شده باشند تعریف می شود، لازم به ذکر است استفاده از پرانتز اختیاری است و می توان از آن استفاده نکرد، ولی گذاشتن پرانتز خوانایی برنامه را بالا می برد. نحوه تعریف تاپل به یکی از دو شکل کلی زیر می باشد :
My_tuple = (value1 , value2 , ...)
My_tuple = value1 , value2 , ...
نکته دیگری که وجود دارد نامحدود بودن طول تاپل ها می باشد، تاپل ها نیز مانند لیست ها می توانند طولی نامحدود داشته باشند، برای محاسبه طول یک تاپل از تابع len استفاده می شود، به چند مثال در این زمینه توجه فرمایید:
>>> my_tuple = ()
>>> print(my_tuple)
()
>>> my_tuple = (1 , 2 , 3)
>>> print(my_tuple)
(1, 2, 3)
>>> my_tuple = (1 , 'Pronesh' , 3.14)
>>> print(my_tuple)
(1, 'Pronesh', 3.14)
>>> my_tuple = ('Pronesh' , [8 , 2 , 5] , (1 , 3 , 9))
>>> print(my_tuple)
('Pronesh', [8, 2, 5], (1, 3, 9))
>>> t = (12.5 , 15.9 , 7.45)
>>> new_tuple = my_tuple , t , ('a' , 'b' , 'c')
>>> new_tuple
(('Pronesh', [8, 2, 5], (1, 3, 9)), (12.5, 15.9, 7.45), ('a', 'b', 'c'))
>>> len(new_tuple)
3
از آن جایی که تاپل ها نیز مانند لیست با اندیس ها شماره گذاری می شوند پس تاپل ها نیز مانند لیست می توانند شامل عناصر تکراری باشند.
>>> my_tuple = ('a' , 'b' , 'f' , 'a' , 'a' , 'g')
>>> my_tuple
('a' , 'b' , 'f' , 'a' , 'a' , 'g')
همانطور که قبلا هم گفتیم می توان عناصر تاپل را بدون استفاده از پرانتز نیز تعریف کرد که به این نوع تعریف بسته بندی تاپل (tuple packing) می گویند. به مثالی از این نوع تعریف توجه کنید:
>>> my_tuple = 5 , 5.12 , "Iran"
>>> print(my_tuple)
(5, 5.12, 'Iran')
>>> a , b , c = my_tuple
>>> print(a)
5
>>> print(b)
5.12
>>> print(c)
Iran
ایجاد یک تاپل که شامل فقط یک عنصر باشد کمی با تعریف لیست متفاوت است، از آنجایی که پرانتز در دستورات و سینتکس های مختلف زبان پایتون معانی مختلفی دارد، تعریف یک تاپل تک عنصری با پرانتز گذاری و یا حتی بدون پرانتز گذاری ممکن است با سینتکس تعریف سایر متغییر ها از سمت پایتون اشتباه برداشت شود، برای این منظور در تعریف تاپل های تک عنصری از یک کاما ( , ) در انتهای عنصر استفاده می کنیم تا جلوی اشتباه پایتون را بگیریم. به مثال های زیر برای درک بهتر این موضوع توجه کنید:
>>> my_tuple = ('Pronesh')
>>> type(my_tuple)
>>> my_tuple = 5
>>> type(my_tuple)
>>> my_tuple = ('Pronesh',)
>>> type(my_tuple)
>>> my_tuple = 5,
>>> type(my_tuple)
روش دیگر برای ساخت یک تاپل استفاده کردن از سازنده (cast) است آن در این باره به مثال زیر توجه کنید :
>>> my_tuple = tuple(('Pronesh' , [1 , 2 , 3] , ('a' , 'b' , 'c')))
>>> my_tuple
('Pronesh', [1, 2, 3], ('a', 'b', 'c'))
دسترسی به عناصر تاپل ها
به صورت کلی تاپل ها هم مانند لیست ها به دو روش می توان به عناصر آن ها دسترسی داشت که در تصویر زیر قابل مشاهده است :
همانطور که در تصویر بالا مشاهده می کنید به دو روش می توان به عناصر یک تاپل دسترسی داشت، یکی اندیس گذاری نرمال که از 0 شروع می شود که اندیس 0 به اولین عنصر تاپل اشاره می کند، و این اندیس ها به ترتیب تا اخرین عنصر تاپل یک واحد یک واحد به جلو حرکت می کنند، که در مثال فوق طول تاپل ما 7 است که آخرین عنصر ما اندیس 6 را خواهد داشت.
دومی اندیس گذاری معکوس است می باشد به این شکل که آخرین عنصر تاپل با اندیس 1- شماره گذاری شده و هر چه به سمت ابتدای تاپل حرکت می کنیم اندیس ها یک واحد یک واحد کوچک می شوند به شکلی که اولین عنصر یک تاپل با طول 7 با اندیس 7- شماره گذاری می شود. به مثال های زیر برای درک بهتر دسترسی به عناصر یک تاپل توجه کنید :
my_tuple = ('p' , 'r' , 'o' , 'n' , 'e' , 's' , 'h')
>>> my_tuple[0]
'p'
>>> my_tuple[6]
'h'
>>> my_tuple[7]
Traceback (most recent call last):
File "", line 1, in
IndexError: tuple index out of range
همانطور که در مثال بالا نیز مشاهده کردید دسترسی به اندیس های خارج از رنج و طول یک تاپل باعث بروز خطا خواهد شد، در مثال بالا طول تاپل ما 7 بود که از اندیس 0 تا 6 قابل دسترسی بود، از آنجایی که اندیس 7 در تاپل تعریف شده یک اندیس نامعتبر است پایتون برای دسترسی به این اندیس خطا صادر کرده است.
نکته: اندیس گذاری در تاپل ها با اعداد صحیح انجام میگیرد و اندیس گذاری با اعداد غیر صحیح باعث بروز خطا در دسترسی می گردد به مثال زیر توجه کنید :
my_tuple = ('p' , 'r' , 'o' , 'n' , 'e' , 's' , 'h')
my_tuple[2.0]
Traceback (most recent call last):
File "", line 1, in
TypeError: tuple indices must be integers or slices, not float
در تاپل ها (tuple) می توان با استفاده از نمایه گذاری تو در تو، به عناصر تاپل های (tuple) تو در تو دسترسی داشت به مثال زیر توجه فرمایید :
my_tuple = ('pronesh' , [5 , 6 , 2] , (1 , 2 , 3))
>>> my_tuple[0][2]
'o'
>>> my_tuple[1][1]
6
>>> my_tuple[2][0]
1
همانطور که قبلا هم اشاره شد، روش دیگر، برای دسترسی به عناصر یک تاپل استفاده از اندیس گذاری منفی می باشد برای درک بهتر این موضوع به مثال زیر توجه فرمایید:
>>> my_tuple = ('p' , 'r' , 'o' , 'n' , 'e' , 's' , 'h')
>>> my_tuple[-1]
'h'
>>> my_tuple[-7]
'p'
همچنین می توان عناصر تاپل را به صورت دسته ای به متغییر های مورد نظر انتصاب داد به مثال زیر توجه کنید :
>>> my_tuple = (1 , 2 , 3)
>>> a , b , c = my_tuple
>>> a
1
>>> b
2
>>> c
3
همانطور که در مثال بالا مشاهده کردید متغییر ها را به ترتیب مد نظر با کاما ( ، ) از یکدیگر جدا کرده و برابر با تاپل از قبل تعیین شده قرار دادیم این کار باعث شد اولین عنصر تاپل به اولین متغییر یعنی متغییر a، (ترتیب متغییر ها از چپ به راست است) نسبت داد شود دومین عنصر به متغییر دوم یعنی b و سومین عنصر به متغییر سوم یعنی c نسبت داده شود، سوال اینجاست که اگر تعداد عناصر از تعداد متغییر ها بیشتر باشد و یا بلعکس چه اتفاقی خواهد افتاد. با مثال هایی این موارد را بررسی می کنیم :
>>> my_tuple = (1 , 2 , 3 , 4 , 5 )
>>> a , b , c = my_tuple
Traceback (most recent call last):
File "", line 1, in
ValueError: too many values to unpack (expected 3)
>>> my_tuple = (1 , 2 , 3)
>>> a , b , c , d = my_tuple
Traceback (most recent call last):
File "", line 1, in
ValueError: not enough values to unpack (expected 4, got 3)
همانطور که مشاهده فرمودید در هر دو حالت پایتون از انتساب متغییر بیشتر از تعداد عناصر تاپل و همچنین انتساب متغییر کمتر از تعداد عناصر تاپل خطای کافی نبودن متغییر یا اضافی بودن متغییر صادر کرد، و این موضوع به این معناست که تعداد متغییر انتساب داده شده به یک تاپل برای دریافت نظیر به نظیر عناصر آن باید حتمی برابر با تعداد عناصر تاپل باشد. اما در صورتی که تعداد متغییر های ما کوچکتر تعداد عناصر تاپل باشد می توان با کمک گرفت از عملگر ستاره ( * )، این مشکل را پوشش داد. به مثال زیر توجه کنید :
>>> a , b , *c = my_tuple
>>> my_tuple = (1 , 2 , 3 , 4 , 5 )
>>> a , b , *c = my_tuple
>>> a
1
>>> b
2
>>> c
[3, 4, 5]
همانطور که مشاهده کردید با قرار دادن ستاره ( * ) در ابتدای نام آخرین متغییر، این مشکل را حل کرد، با استفاده از ستاره ( * ) در ابتدای نام متغییر آخر باعث می شوید که پایتون مثل یک لیست با متغییر آخر (ستاره دار) و تمام عناصر باقی مانده در تاپل را به آن اختصاص دهد و دیگر خطای ناکافی بودن متغییر صادر نمی شود.
حال اگر ستاره ( * ) را به متغییری غیر از آخرین متغییر اضافه کنید ، پایتون عناصر تاپل را به شکلی به متغییر ستاره دار نسبت می دهد که عناصر باقی مانده با تعداد متغییر های باقی برابر باشد. با مثال زیر این مفهوم را بهتر درک خواهید کرد:
>>> my_tuple = (1 , 2 , 3 , 4 , 5 )
>>> a , *b , c = my_tuple
>>> a
1
>>> b
[2, 3, 4]
>>> c
5
برش دادن تاپل ها
همانطور که می دانید منظور از برش دادن، جدا کردن بخشی از داده های یک تاپل به شکل دسته ای می باشد که به کمک عملگر کولون ( : ) قابل انجام است :
>>> my_tuple = ('p' , 'r' , 'o' , 'n' , 'e' , 's' , 'h')
>>> my_tuple[0:3]
('p', 'r', 'o')
>>> my_tuple [3:]
('n', 'e', 's', 'h')
>>> my_tuple[:]
('p', 'r', 'o', 'n', 'e', 's', 'h')
>>> my_tuple[3:8]
('n', 'e', 's', 'h')
>>> my_tuple[3:-1]
('n', 'e', 's')
>>> my_tuple[-7:]
('p', 'r', 'o', 'n', 'e', 's', 'h')
تغییر عناصر یک تاپل
همانطور که قبلا هم بیان شد، تاپل ها قابل تغییر نیستند، ولی اگر تاپل به صورت تو در تو تعریف شده باشد، به شکلی که برخی عناصر آن خود عناصری قابل تغییر باشند مانند لیست ها، رشته ها و … می توان عناصر قابل تغییر آن را تغییر داد به مثال های زیر توجه کنید:
>>> my_tuple = (5 , 8 , 2 , [3 , 4])
>>> my_tuple[1] = 9
Traceback (most recent call last):
File "", line 1, in
TypeError: 'tuple' object does not support item assignment
>>> my_tuple[3][0] = 9
>>> my_tuple
(5, 8, 2, [9, 4])
الحاق و تکرار در تاپل ها
برای الحاق دو تاپل می توان از عملگر ( + ) استفاده کرد و برای تکرار عناصر یک تاپل با همان ترتیب موجود در آن و با تعداد تکرار دلخواه می توان از عملگر ( * ) استفاده کرد. نکته قابل توجه این است که حاصل عمل الحاق یا تکرار چند تاپل خود نیز یک تاپل جدید می باشد.
>>> print( (1 , 2 , 3) + (4 , 5 , 6) )
(1, 2, 3, 4, 5, 6)
>>> print(('pronesh',) * 3)
('pronesh', 'pronesh', 'pronesh')
حذف تاپل ها
عناصر یک تاپل تغییر پذیر نیستند، به این معنا که عناصر قابل حذف هم نیستند، اما حذف کامل یک تاپل با کمک دستور del امکان پذیر است :
>>> my_tuple = ('p' , 'r' , 'o' , 'n' , 'e' , 's' , 'h')
>>> del my_tuple[2]
Traceback (most recent call last):
File "", line 1, in
TypeError: 'tuple' object doesn't support item deletion
>>> del my_tuple
>>> my_tuple
Traceback (most recent call last):
File "", line 1, in
NameError: name 'my_tuple' is not defined
همانطور که در مثال بالا مشاهده می کنید حذف یک عنصر از تاپل باعث اعلام خطا توسط پایتون می شود ولی حذف کلی تاپل به راحتی انجام شد به شکلی که فراخوانی نام تاپل حذف شده باعث بروز خطا شد و پایتون اعلام کرد چنین شناسه ای وجود ندارد.
متد های تاپل
متد هایی که باعث اضافه یا حذف شدن عناصر می شوند، برای تاپل ها وجود ندارد، ولی دو متد index برای پیدا کردن اندیس عنصر مد نظر و متد count برای شمارش تعداد تکرار عنصر مد نظر در تاپل قابل استفاده هستند.
>>> my_tuple = ('a' , 'p' , 'p' , 'l' , 'e' ,)
>>> my_tuple.count('p')
2
>>> my_tuple.index('l')
3
تست عضویت در تاپل ها
برای بررسی وجود یا عدم وجود یک عنصر در یک تاپل می توان از کلید in به شکل زیر استفاده کرد:
>>> my_tuple = ('a' , 'p' , 'p' , 'l' , 'e' ,)
>>> print('a' in my_tuple)
True
>>> print('b' in my_tuple)
False
>>> print('g' not in my_tuple)
True
تاپل ها در حلقه های for
از حلقه های for می توان برای ترکیب کردن تکراری تاپل ها استفاده کرد، به مثال زیر توجه کنید :
>>> for name in ('John', 'Kate'): print('Hello' , name)
...
Hello John
Hello Kate
به شکل کلی غیر قابل تغییر بودن عناصر یک تاپل در برخی موارد یک امتیاز محصوب می شود، فرض کنید مقادیری دارید که نمی خواهید در طول اجرای برنامه تغییری کنند، استفاده از تاپل در این خصوص به شما اطمینان میدهد که مقادیر انتصاب داده شده به متغییر در هنگام تعریف دیگر قابل تغییر نی باشد، و نکته دوم، بخاطر ایستا بودن و غیرقابل تغییر بودن تاپل ها، تکرار در آن ها نسبت به لیست ها با سرعت بیشتری انجام می پذیرد.
دیدگاهتان را بنویسید