پس از این که دستورات به نشانههاتفکیک گردیدند( بخشی به نام “دستورزبان شل” را ملاحظه کنید)،این نشانهها یا کلمات، تعمیم یافته یا تصمیم گیری میشوند. هشت نوع بسط قابل انجام، وجود دارد، که در بخش بعدی به ترتیبی که اجرا میشوند، در مورد آنها صحبت خواهیم نمود.
پس از انجام تمام بسطها،زدودن نقلقولها انجام میشود.
بسط ابرو مکانیسمی است که توسط آن رشتههای دلخواه میتوانند تولید گردند. الگوهایی که بسط ابرو میشوند به شکل یک مقدمه اختیاری که با یک سری رشتههای جداشده با کاما و محصور شده در یک جفت ابرو ادامه مییابند، هستند، که به دنبال آن یک پیوست اختیاری میآید. مقدمه به هر یک از رشتههای محصور در ابروها پیشوند میشود ، و سپس پیوست به هر یک از رشتههای منتجه الحاق میگردد، بسط از چپ به راست انجام میشود.
بسطهای ابرو میتوانند تودرتو باشند. نتایج حاصل از رشتههای بسط یافته مرتب شده نمیباشند، و ترتیب چپ به راست حفظ میشود:
franky ~>
echosp{el,il,al}l
spell spill spall
بسط ابرو قبل از هر یک از بسطهای دیگر انجام میشود، و هر کاراکتر ویژه در نتجه برای بسطهای دیگر حفظ میگردد. این بسط به طور جدی مبتنی بر متن است. Bash هیچگونه تفسیر دستورزبانی در مفاد بسط یا متن مابین ابروها انجام نمیدهد. برای اجتناب از تداخل با بسط پارامتر، رشته “${” قابل انتخاب برای بسط ابرو مطرح نگردیده است.
یک بسط ابرو با ساختار صحیح، باید شامل ابروهای باز و بسته غیر نقلقولی شده و حداقل یک کاراکتر کامای غیر نقلقولی باشد. هر بسط ابروی نادرست تنظیم شده، دستنخورده رها میشود.
اگر یک کلمه با کاراکتر غیرنقلقولی مد (“~”) شروع شود، تمام کاراکترها تا اولین علامت ممیز(/) غیرنقلقولی( یا تمام کاراکترها در صورت عدم وجود / ) به عنوان مد-پیشوندی در نظر گرفته میشوند. اگر هیچ یک از کاراکترهای مد-پیشوندینقلقولی نشده باشند، با کاراکترهای پس از علامت ~ در مد-پیشوندی به عنوان یک نام لاگین ممکن رفتار میشود. اگر این نام لاگین یک رشته تهی باشد علامت مد با مقدار متغیر HOME
پوسته جایگزین میگردد. اگر متغیرHOME
برقرار نشده باشد، دایرکتوری خانگی کاربر اجرا کننده شل به جای آن جایگزین میشود. در غیر آنصورت مد-پیشوندی با دایرکتوری خانگی مرتبط با نام لاگین معین شده جایگزین میشود.
اگر مد-پیشوندی برابر “~+” باشد، مقدار متغیر PWD
پوسته جایگزین آن میشود. اگر مد-پیشوندی برابر “~-” باشد، مقدار متغیر OLDPWD
پوسته، اگر تنظیم شده باشد، جایگزین آن میشود.
اگر کاراکترهای پس از مد در یک مد-پیشوندی شامل یک عدد N باشد، که به طور انتخابی یک “+” یا یک “-” قبل از آن عدد باشد، مد-پیشوندی با عناصر متناظر از پشته دایرکتوری جایگزین میشود، به طوری که با دستور داخلی dirs فراخوانی شده با کاراکترهای بعد از ~ در یک مد-پیشوندی به عنوان یک شناسه، نمایش داده میشد. اگر یک مد-پیشوندی شامل عددی بدون همراهی “+” یا “-” باشد، “+” در نظر گرفته میشود.
اگر نام لاگین معتبر نباشد، یا بسط مد شکست بخورد، کلمه بدون تغییر رها میشود.
هر تخصیص متغیری فوراً برای مد-پیشوندی غیرنقلقولی دنبال شده با “:” یا “=” بررسی میشود. در این حالتها، بسط مد نیز انجام میشود. در نتیجه، کسی ممکن است از نامهای شامل کاراکتر مد در تنظیم متغیرهای PATH
، MAILPATH
، و CDPATH
استفاده کند، و پوسته مقادیر بسط یافته را جایگزین میکند.
مثال:
franky ~>
exportPATH
=$PATH:~/testdir
~/testdir
به $HOME
/testdir
بسط مییابد، به طوری که اگر $HOME
برابر با /var/home/franky
باشد،دایرکتوری /var/home/franky/testdir
به محتوای متغیر PATH
اضافه خواهد شد.
کاراکتر “$” بسط پارامتر،جایگزینی فرمان، یا بسط حسابی را نشان میدهد . نام یا نماد پارامتری که باید بسط یابد میتواند در ابروها محصور شده باشد، که این مورد اختیاری است، اما به محافظت ازبسط داده شدن بلافاصله متغیر از کاراکترهای دنباله آن، که میتوانند به عنوان بخشی از نام تفسیر گردند، کمک میکند.
وقتی از ابروها استفاده میشود، تطبیق ابروی انتهایی، اولین “}”میباشد، که با \ و درمیان نقلقولها پوشیده نشده، و درمیان بسط حسابی، جایگزینی دستور، و بسط پارامتر نیست.
شکل اصلی بسط پارامتر اینگونه “${PARAMETER}” است. ارزش“PARAMETER” جایگزین میشود. ابروها موقعی لازم هستند که “PARAMETER” یک پارامتر موقعیتی بابیش از یک رقم باشد، یا وقتی که “PARAMETER” با کاراکتری که نباید به عنوان بخشی از نامش تفسیر شود،دنبال شده باشد.
اگر اولین کاراکتر “PARAMETER” یک علامت تعجب باشد، Bash ازارزش متغیر تشکیل شده از بقیه “PARAMETER” به عنوان نام متغیر استفاده میکند، این متغیر بعد بسط خواهد یافت و مقدار آن در بقیه جایگزینی زودتر از ارزش خود “PARAMETER” به کار خواهد رفت. این به عنوان بسط غیر مستقیم شناخته شده است.
شما به طور یقین با بسط مستقیم پارامتر آشنا میباشید، چون همیشه، حتی در سادهترین وضعیتها انجام میشود، از قبیل یکی از موارد بالا یا پایین:
franky ~>
echo$SHELL
/bin/bash
در ادامه یک نمونه از بسط غیر مستقیم:
franky ~>
echo${!N*}
NNTPPORT NNTPSERVER NPX_PLUGIN_PATH
echo $N*
نمیباشد.
ساختار زیر ایجاد نام متغیرهایی که هنوز وجود ندارند را ممکن میسازد:
${
VAR
:=value
}
مثال:
franky ~>
echo$FRANKY
franky ~>
echo${FRANKY:=Franky}
Franky
به هر حال، پارامترهای ویژه ، از جمله پارامترهای موضعی، نمیتوانند به این طریق اختصاص یابند.
ما در آینده در باره کاربرد پرانتزها جهت رفتار متغیرها در فصل 10, بیشتر در مورد متغیرها صحبت خواهیم نمود. همچنین اطلاعات بیشتر را میتوان در صفحههای Bash info یافت.
جایگزینی فرمان، امکان جانشینی خروجی فرمان به جای خودش را فراهم میکند. جایگزینی فرمان موقعی رخ میدهد، که یک دستور به این شکل محصور شود:
$(command)
یا مانند این دیگری با استفاده از backtickها:
`command`
Bash بسط را با اجرای فرمان و تعویض جایگزینی فرمان با خروجی استاندارد دستور، انجام میدهد، و رد پای سطرهای جدید حذف شده را باقی میگذارد. سطرهای جدید تعبیه شده حذف نشدهاند، اماامکان دارد آنها در جریان تفکیک کلمه پاک بشوند.
franky ~>
echo`date`
Thu Feb 6 10:06:20 CET 2003
موقعی که از روش قدیمی نقلقولبرعکس در جایگزینی فرمان استفاده شود، \ غیر از مواردی که با “$”، “`”، یا “\” دنبال شود، معنی واقعی( لفظی ) خود را حفظ میکند. اولین backtick بعدی که با \ پوشش نیافته باشد، جایگزینی فرمان را خاتمه میدهد. وقتی از شکل “$(COMMAND)” استفاده میشود، تمام کاراکترهای بین پرانتزها، دستور را تشکیل میدهند،با هیچ یک به طور ویژه رفتار نمیشود.جایگزینیهای فرمان میتوانند تودرتو باشند. در جایگزینی تودرتو که از شکل نقلقولبرعکس به کارمیبرید، backtickهای داخلی را با \ها پوشش دهید.
اگر جایگزینی در میان نقلقولهای دوگانه قرارداشته باشد، تفکیک کلمه و بسط نام فایل، روی نتایج انجام نمیشود.
بسط حسابی، ارزیابی عبارتهای محاسباتی و جایگزینی نتایج را میسر میسازد. شکل بسط حسابی اینگونه است:
$(( EXPRESSION ))
با عبارت به گونهای رفتار میشود که اگر در یک نقلفول دوگانه میبود، اما با یک نقلقول دوگانه در داخل پرانتزها به طور ویژه رفتار نمیشود. تمام نشانهها در عبارت متحمل بسط پارامتر، جایگزینی فرمان، و رفع نقلقول میشوند. جایگزینی حسابی میتواند تودرتو باشد.
ارزیابی عبارتهای حسابی درمحدوده اعداد صحیح با طول ثابت انجام میشود، اگر چه تقسیم بز صفر محبوس شده و به عنوان یک خطا تشخیص داده میشود. عملگرها تقریباً مانند زبان C هستند. لیست عملگرها به ترتیب کاهش اولویت به این ترتیب است:
جدول 3.4 : عملگرهای حسابی
عملگر | مقصود |
---|---|
VAR++ و VAR-- | افزایش و کاهش یک واحد متغیر |
++VAR و --VAR | پیشافزایش و پیشکاهش یک واحد متغیر |
- and + | مثبت و منفی یکانی |
! و ~ | نفی منطقی و بیتی |
** | توان |
*, / و % | ضرب، تقسیم، باقیمانده |
+ and - | جمع، تفریق |
<< و >> | جابجایی بیتی به چپ و راست |
<=, >=, < and > | عملگرهای مقایسه |
== و != | تساوی و نامتساوی |
& | AND بیتی |
^ | یای انحصاری بیتی |
| | یای بیتی |
&& | AND منطقی |
|| | OR منطقی |
expr ? expr : expr | ارزیابی شرطی |
=, *=, /=, %=, +=, -=, <<=, >>=, &=, ^= و |= | تخصیص مقدار |
, | جداکننده عبارتها |
متغیرهایپوسته میتوانند عملگر باشند، بسط پارامتر قبل از ارزیابی محاسباتی انجام میشود. همچنین متغیرهای پوسته در داخل یک عبارت میتوانند بدون استفاده از ترکیب بسط پارامتر، توسط نام رجوع بشوند. وقتی به متغیر رجوع شود، مقدار متغیر در عبارت حسابی ارزیابی میشود. برای استفاده از متغیر در عبارت لازم نیست صفت عدد صحیح بودن آن تأکید شود.
ثابتهایی که صفر در ابتدای آنها باشد، به عنوان اعداد اکتال تفسیر میشوند. اگر با “0x” یا “0X” شروع شوند به معنی هگزادسیمال است. در غیر اینصورت، اعداد شکل “[BASE'#']N” میگیرند، که در آن “BASE” یک عدد دسیمال بین ۲ تا ۶۴ میباشد و نماینده مبنای محاسبات است، و N عددی در آن مبنا میباشد. اگر “BASE'#'” صرفنظر شده باشد، مبنای ۱۰ به کار میرود. ارقام بزرگتر از ۹ با حروف کوچک، حروف بزرگ، و کاراکتر“@”, و “_”به ترتیب، نمایندگی میشوند. اگر “BASE” کوچکتریا مساوی ۳۶ باشد، حروف کوچک و بزرگ به طور قابل تعویض، میتوانند برای نمایندگی اعداد از ۱۰ تا ۳۵ به کار روند.
عملگرها به ترتیب اولویت ارزیابی میشوند. عبارتهای داخل پرانتزها، اول ارزیابی میشوند.
کاربران Bash تا آنجا که ممکن است، باید جفت براکتها را به کار ببرند:
$[ EXPRESSION ]
هرچند، این ترکیب فقط نتیجه EXPRESSION را حساب میکند و تستها را انجام نمیدهد:
franky ~>
echo$[365*24]
8760
برای نمونههای کاربردی در اسکریپتها، از میان سایرین بخشی به نام “مقایسههای عددی” را ملاحظه کنید.
جایگزینی پردارش در سیستمهایی پشتیبانی میشود که از لوله(pipe()های با نام (FIFOs) یا /dev/fd
یعنی روش نامیدن فایلهای باز، پشتیبانی میکنند. این جایگزینی به شکل
<(LIST)
یا
>(LIST)
میباشد. پردازش LIST
با ورودی یا خروجیاش که متصل به یک FIFO یا فایلهایی در /dev/fd
است، اجرا میشود. نام این فایل به عنواننتیجه بسط، به صورت یک شناسه به دستور جاری داده میشود. اگر از شکل “>(LIST)” استفاده شود، نوشتن در فایل، ورودی برای LIST
را فراهم میکند. اگر شکل “<(LIST)” به کار رود، فایلی که به عنوان یک شناسه داده شده، باید برای به دست آوردن خروجی LIST
خوانده شود. توجه کنید که هیچ فاصلهای نباید بین علامتهای < یا > و پرانتز سمت چپ وجود داشته باشد، در غیر اینصورت به عنوان یک ساختار تغییر مسیر تفسیر میٰگردد.
موقعی که فراهم باشد، جایگزینی پردازش به طور همزمان با بسط پارامتر و متغیر، جایگزینی فرمان، و بسط حسابی، انجام میشود.
اطلاعات بیشتر در بخشی به نام “تغییر مسیر و توصیفگرها” .
پوسته نتایج بسط پارامتر، جایگزینی فرمان، و بسط حسابی، که درنقلقولهای دوگانه واقع نشدهاند را برای تفکیک کلمه بررسی میکند.
شل با هر کاراکتر متغیر IFS$
به عنوان جدا کننده رفتار میکند، و نتایج سایر بسطها را نسبت به این کاراکترها به کلمات تجزیه میکند. اگر IFS
تنظیم نشده باشد، یا مقدار آن دقیقاً “'<space><tab><newline>'” یعنی مقدار پیشفرض، باشد، هر یک از کاراکترهای IFS
برای جداسازی کلمهها به کار میروند. اگر IFS
مقداری غیر از پیشفرض داشته باشد، سپس توالی کاراکترهای فضای سفید “space” و “Tab” ابتدا و انتهای کلمه چشمپوشی میشوند، مشروط به آن که کاراکتر فضای سفید در IFS
موجود باشد( یک کاراکتر فضای سفید IFS
). هر کاراکتر در IFS
که فضای سفید IFS
نیست، همراه با هر کاراکتر فضای سفید مجاور IF
یک فیلد را جدا میکند. با توالی کاراکترهای فضای سفید IFS
نیز همچون یک جداکننده رفتار میشود. اگر مقدار IFS
تهی باشد، تفکیک کلمه انجام نمیشود.
شناسههای تهی صریح یعنی (“""” یا “''”) حفظ میشوند. شناسههای تهی صریح نقلقولی نشده حاصل از بسط پارامترهایی که مقدار ندارند، حذف میشوند. اگر پارامتر بدون مقداری در میان نقلقولهای دوگانه بسط یابد،یک شناسه تهی نتیجه میشود و ابقا میگردد.
بسط و تفکیک کلمه | |
---|---|
اگر بسط انجام نشود، جداسازی انجام نمیشود. |
بعد از تفکیک کلمه، جز اینکه گزینه f-
تنظیم شده باشد( بخشی به نام “اشکازدایی قسمتی اسکریپت” را ملاحظه کنید) ، Bash هر کلمه را برای کاراکترهای“*”، “?”، و “[” مرور میکند. اگر یکی از این کاراکترهادیده شود، آن کلمه به عنوان یک الگو تلقی میشود، وبا لیست مرتب شده الفبایی نام فایلهایی که با الگو تطبیق میکنند، تعویض میشود. اگر هیچ مورد انطباقی یافت نشود و گزینه nullglob
پوسته غیر فعال باشد، کلمه بدون تغییر رها میشود. اگر گزینه nullglob
تنظیم شده باشد و مورد انطباقی پیدا نشود، کلمه حذف میشود. اگر گزینه nocaseglob
پوسته فعال باشد، انطباق بدون در نظر گرفتن حالت کوچک و بزرگ حروف انجام میشود.
وقتی از یک الگو برای تولید نام فایل استفاده میگردد، کاراکتر “.” در ابتدای نام فایل یا بلافاصله بعد از یک / باید به طور وضوح تطبیق یابد، مگر آن که گزینه dotglob
شل برقرار باشد. موقعی که یک نام فایل منطبق میشود، کاراکتر / همیشه باید به طور صریح مطابقت نماید. در سایر حالتها، با کاراکتر “.” به طور خاصی رفتار نمیشود.
متغیر GLOBIGNORE
پوسته میتواند برای محدود نمودن مجموعه نام فایلهای منطبق با الگو، به کار برود. اگر متغیر GLOBIGNORE
تنظیم شده باشد، هر مورد منطبق با الگو،که با یکی از نمونهها در GLOBIGNORE
نیز انطباق داشته باشد، از لیست تطبیقها حذف میشود. نام فایلهای .
و ..
همیشه حذف میشوند، حتی موقعی که متغیر GLOBIGNORE
برقرارگردیده. به هر حال، برقراری گزینه GLOBIGNORE
تأثیر فعال شدن گزینه dotglob
شل را دارد، به طوری که تمام نام فایلهای دیگری که با یک “.” شروع میشوند، تطبیق خواهند نمود. برای به دست آوردن رفتار قبلی چشمپوشی از نام فایلهایی که با یک “.” شروع میشوند، “*.” را یکی از نمونهها در متغیر GLOBIGNORE
قراردهید. وقتی متغیر GLOBIGNORE
برقرار نیست،گزینه dotglob
غیرفعال میباشد.