حال متوجه شدهاید که چگونه یک تابع را تعریف کنید و ازان در برنامههای دیگر خود استفاده کنید. حال همچنین موضوعی را فرض کنید اگر بخواهید تعدادی از توابع را در برنامه دیگری که مینویسید استفاده کنید باید چه کرد؟ فکر میکنم همانطور که حدس زدهاید با استفاده از ماژولها این کار امکان پذیر است.
روشهای گوناگونی برای نوشتن ماژولها وجود دارد. اما سادهترین روش است که فایلی افزونهی py.
بسازید که شامل محتویات توابع و متغییرها است.
روش دیگر که برای نوشتن ماژولها میتوانیم استفاده کنیم این است که ماژولها را با زبانبرنامهنویسی مادری خود که در مترجم پایتون نوشته شده است، بنویسیم. برای مثال ماژولها را به برنامهنویسی سی مینویسید و در زمان کامپایل برنامه، پایتون از مترجم استانداری که در پایتون وجود دارد استفاده میکند.
ماژولها را از برنامههای دیگر میتوانید وارد کنید (imported). تا از توابع و خاصیتها انان استفاده کنید. همچنین از کتابخوانههای استاندارد پایتون نیز میتوانیم استفاده کنیم. حال خواهیم دید که چگونه از ماژولهای استاندارد کتابخوانه پایتون استفاده کنیم.
برای مثال (فایلی با نام module_using_sys.py
ذخیره کنید)
{% include "./programs/module_using_sys.py" %}
خروجی:
{% include "./programs/module_using_sys.txt" %}
چگونه و چطوری
در ابتدا ماژولهای sys
را وارد میکنیم این کار با استفاده از دستور import
انجام میشود. اساسا این طوری به پایتون میگویم که میخواهیم از ماژول استفاده کنیم. ماژول sys
حاوی توابعی که مربوط به مترجم پایتون و محیطاش میشود است. بدان معنی که سیستم.
وقتی که پایتون دستور import sys
را اجرا میکند، نگاهی به ماژول sys
هم کرده است. در این مورد این یک ماژول داخلی است و پایتون میداند کجا ان را پیدا کنید.
اگر این یک ماژول کامپایل نشده بود بدان معنی که در پایتون نوشته شده بود، پس پایتون ان را در دارکتوریهای فهرست شده در متغییر sys.path
جستجو خواهد کرد. اگر ماژول پیدا شود سپس دستورات بدنه ماژول اجرا خواهد شد و ماژول در دسترس قرار خواهد گرفت. نکته، مقدار دهی اولیه یکبار انجام میشود وقتی که ماژول را وارد میکنیم.
متغییر argv
در ماژول sys
با استفاده از نقطهی نمادین sys.argv
در دسترس است. پس باید این موضوع را درک کرده باشید این اسم قسمتی از ماژول sys
است. یکی دیگر از مزیتهای این روش این است که نام argv
با متغییرهای که در برنامه با این نام دارید باعث مشکل نمیشود.
متغییر sys.argv
لیستی (لیست در فصول بعدی توضیح داده خواهد شد) از رشتهها است. به طور خاص sys.argv
لیستی از محتوایات ارگومانهای خطفرمان است. این بدان معنی است که دستوراتی را که از ان استفاده میکنید شامل میشود.
اگر از آیدیئی برای اجرا و نوشتن این برنامهها استفاده میکنید، دنبال راهی برای مشخص کردن ارگومانهای خطفرمان در منوی برنامه بکنید.
در اینجا وقتی که ماژولهای پایتون را با استفاده از sys.py
اجرا میکنیم(اینها ارگومان هستند)، ماژولی را اجرا کردیم که از ماژول sys.py
استفاده میکند همراه با دستورات پایتون
و خط فرمانهای ان به دنبال دارد. پایتون ارگومانهای خطفرمان را در متغییر sys.argv
ذخیره میکند.
به یاد داشته باشید که نام اسکریپت اجرا شده همیشه اولین عنصر لیست sys.argv
است. بنابراین از 'sys.py به عنوان'
sys.argv[0]
، sys.argv[1]
، sys.argv[2]
و ارگومانها هم به عنوان sys.argv[3]
به کار میرود. این نکته را هم در نظر داشته باشید که پایتون شمارش را نه از یک بلکه از صفر شروع میکند.
محتویات فایل sys.path
شمامل لیستی از نام دایرکتوریهای که ماژولها از انجا وارد(imported) شدهاند. اگر توجه کنید در خط اول فایل sys.path
خالی است، این رشته خالی نمایانگر دایرکتوریهای فعلی است که بخشی از sys.path
است که همانند متغییر PYTHONPATH
است. این بدان معنی است که میتوانید به طور مستقیم وارد ماژولهای دایرکتوری جاری شوید. در غیر این صورت باید ماژولها خود را در یک از لیستهای sys.path
قرار دهید.
این نکته را در نظر داشته باشید منظور از دایرکتوری جاری همان جایی است که از برنامه اجرا میشود. import os; print(os.getcwd())
اجرا کنید که دایرکتوری جاری برنامهها خود را پیدا کنید.
{#pyc}
ماژول وارکردن یک کار نسبتا گرانبهایی است و پایتون برای این روش ترفندهای برای انجام سریعتر این کار دارد. یکی از این روشها ساختن فایل byte-compiled با پسوند .pyc
است که واسطهی است برای پایتون برای تبدیل به ( اگر به یاد داشته باشید در بخش مقدمه در قسمت پایتون چگونه کار میکند؟) توضیح داده شد.
این فایل .pyc
زمانی بدرد میخورد که بعدا بخواهیم از یک برنامه دیگر ماژولی را وارد کنیم. این کار باعث میشود این امر بسیار سریعتر انجام شود زیرا پردازشهای مربوط به وارد کردن ماژول قبلا انجام شده است. همچین این فایل
بایتتغییریافته(Byte-compiled) وابستگی به پلت فرم ندارد.
نـکـتـه: فایل .pyc
در دایرکتوری جاری که فایل .py
موجود هست ساخته میشود. اگر پایتون اجاز دسترسی برای نوشتن در ان پوشه را نداشته باشد فایل .pyc
ایـــجـــاد نـــمی شـــود.
{#from-import-statement}
اگر به طور مستقیم argv
وارد برنامهی خود کنید(که دیگر هر بار sys
را وارد نکنید). برای این روش میتوانید از دستور from sys import argv
استفاده کنید.
اخــطــار: به طور کلی از دستور from..import
اجـتـنـاب کنید به جای این دستور از دستور import
استفاده کنید. این موضوع جلوگیری از هرگونه مشکل میکند و برنامه خوانا تر می شود.
مثال:
from math import sqrtе
print("Square root of 16 is", sqrt(16))
هر ماژولی نامی دارد و هر نامی خاصیتها یا گزینههای دارد که میتوان ان را پیدا کرد.
این خاصیت برای هدفهای خاص میتواند مفید واقع شود(ماٰژولهای import شده). هماطور که قبلا گفته شده بود ماژولهای که برای بار اول وارد (import)میشوند. محتویات ان ماژول اجرا میشود.
با استفاده از این روش میتوانیم از ماٰژولها استفاده کنیم فرقی نمیکند ان ماژول را وارد کردیم(import) یا ماٰژول خودمان است.
با استفاده از خاصیت __name__
میتوانیم به هدف خود برسیم.
برای مثال (فایلی با نام module_using_name.py
ذخیره کنید)
{% include "./programs/module_using_name.py" %}
خروجی:
{% include "./programs/module_using_name.txt" %}
چگونه و چطوری
هر ماژولی در پایتون برای خود نامی__name__
دارد یا برای ان تعریف شده.
اگر این '__main__'
است این بدان معنی است که ماٰژول توسط کاربر مستقل عمل میکند و اقدامات مناسب را میتوانیم انجام بدهیم.
ایجاد یک ماٰژول شخصی بسیار اسان است. هر روز دارید این کار را انجام میدهید شاید خودتون با خبر نباشید. چون تمامی برنامههای پایتون ماژول است. فقط کافی است که اطمینان حاصل کنید که افزنهای .py
را دارد.
به مثال زیر توجه کنید
برای مثال (فایلی با نامmymodule.py
ذخیره کنید)
{% include "./programs/mymodule.py" %}
بخاطر داشته باشید که ماٰٰژول فرخوان شده باید در همان پوشه باشد یا ادرش ان قید شده باشد.(در یکی از پوشههای sys.path
)
یک ماژول دیگر (فایلی با نام mymodule_demo.py
ذخیره کنید)
{% include "./programs/mymodule_demo.py" %}
خروجی:
{% include "./programs/mymodule_demo.txt" %}
چگونه و چطوری
دقت کردید پایتون برای صدا زدن ماٰژولها ار هم نقطه دوباره استفاده کرده، که مجبور به یادگیری چیز متفرقه نشیم. پایتون به خوبی دوباره از این نشانها استفاده میکند تا یک حس پابیتونی را القا کند.
این یک نسخه از from..import
برای مثال (فایلی با نامmymodule_demo2.py
ذخیره کنید)
{% include "./programs/mymodule_demo2.py" %}
خروجی: mymodule_demo2.py
شبیه خروجی mymodule_demo.py
است.
با فراخوانی mymodule نام __version__
صدا زده شده است. این باعث ایجاد درگیری میشود.بخاطر همین است که توسعه میشود از import
استفاده کنید . گرچه برنامه طولانی تر میشود ولی دچار چنین مشکلی نمیشود.
هچنین میتوانید:
from mymodule import *
این تمامی نامهای عمومی فراخوانی میشود، مثل say_hi
اما بدون __version__
بخاطر اینکه با با دو خط شروع میشود (double underscores)
تکته: با از import-star استفاده شود. *from mymodule import
زین پایتون
یک از اصول پایتون این است که "Explicit is better than Implicit" "اشکار بودن بهتر از نهان است" برای یادگیری بهتر به
import this
مراجعه کنید.
{#dir-function}
تابعی ساخته شده در ()dir
لیست تعریف شده توسط شی را بازمیگرداند. اگر شی یک ماژول باشد، این لیست شامل توابع، کلاسهاومتغییرهای است که در ان ماٰژول تعریف شده است.
این تابع میتواند ارگومان را قبول کند.
اگر ارگومان نامیاست برای ماژول، تابع قابلیت فراخوانی لیست نامهای از ماژول را دارد. اگر ارگومانی وجود نداشته باشد، تابع لیست ماژولهای فعلی را فراخوانی میکند.
مثال:
$ python
>>> import sys
اسامی صفات را در ماژول sys دریافت کنید؛
>>> dir(sys)
['__displayhook__', '__doc__',
'argv', 'builtin_module_names',
'version', 'version_info']
فقط چند نوشته در اینجا نشان داده شده است
نام اسناد برای ماژول فعلی را دریافت کنید
>> dir()
['__builtins__', '__doc__',
'__name__', '__package__']
ایجاد یک متغیر جدید 'a'
>> a = 5
>>> dir()
['__builtins__', '__doc__', '__name__', '__package__', 'a']
حذف / حذف نام
>>> del a
>>> dir()
['__builtins__', '__doc__', '__name__', '__package__']
چطوری و چگونه
در گام اولیه طرز استفاده dir
برروی ماژول فراخوانی شده sys
را دیدیم، همچنین لیستی از ویژگیهای موجود را مشاهده کردیم. در گام بعدی از dir
بدون پارامتر استفاده کردیم. به طور پیش فرض لیست ویژگیهای ماژول فعلی را بازمیگرداند. نکته شامل لیست ماژولهای وارده شده هم میشود.
برای دیدن عمل کرد dir
یک تغییر جدید را به نامa
تعریف کردیم و یک مقدار به ان اختصاص دادیم.سپس dir
را برسی میکنیم میبینیم که یک لیست اضافی در لیست وجود دارد.
با استفاده از دستور del
متغییر را حذف میکنیم و درخروجی دوباره dir
نمایش داده میشود.
نکته دستور del
برای حذف یک تغییر استفاده میشود.پس از استفاده از del a
دیگر نمیتوانید از متغییر a
استفاده کنید. انگاری که وجود نداشته است مثل قبلا.
نکته تابع ()dir
بر روی همه ماژولها کار میکندبرای مثال (dir(str
را اجرا کنید.
همچنین تابع vars()
وجود دارد که میتواند هم صفتها و مقادیر را برگرداند. ولی برای تمامی ماژولها کار نمیکند.
در حال حاضر باید طرز سازماندهی و سلسله مراتب باید درگیر باشید. توابعهاعمومی مهعولا در درون ماژولها قرار میگیرند. حال اگر بخواهید که ماژولها را سازماندهی کنید چه؟ اینجاست که به کمکتات بستهها (Packages) میایند.
بسته همان پوشه است که درون ان فایلی __init__.py
گذاشته میشود و برای پایتون این پوشهخاصی است چون ماژولها در ان قرار دارد.
برای مثال میخواهیم بسته با نام 'world' که در داخل ان 'asia', 'africa', و غیره وجود دارد.
این کاری است که برای سلسله مراتب و ساختار پوشههایتان باید داشته باشید:
- <some folder present in the sys.path>/
- world/
- __init__.py
- asia/
- __init__.py
- india/
- __init__.py
- foo.py
- africa/
- __init__.py
- madagascar/
- __init__.py
- bar.py
بستهها فقط یک توافقی برای سازماندهی سلسله مراتب هستند. نمونهها بسیاری میتوانید در standard library پیدا کنید.
همانطور که دیدیم توابع هم مانند قسمتی از برنامهها هستند که چندین بار در برنامههای مختلف میتوانیم استفاده کنیم. بستهها هم که روشی برای سازماندهی ماژول ها هستند. چیزهای که یاد گرفتیم.
طرز استفاده از ماٰژول و ساخت ماٰژول را اموختیم.
در دروس بعدی با مفهوم جالبی به نام ساختار اشنا خواهیم شد.