الفرق بين المراجعتين لصفحة: «Bash/break and continue»

من موسوعة حسوب
إدخال 1.0، عنوان الصفحة
 
إدخال 2.0 محتوى المادة
سطر 1: سطر 1:
<noinclude>{{DISPLAYTITLE:الأمران Break و Continue}}</noinclude>
<noinclude>{{DISPLAYTITLE:الأمران Break و Continue}}</noinclude>
== أمر Break ==
تُستخدم عبارة <code>Break</code> للخروج من الحلقة التكرارية الحالية قبل موعد خروجها الأصلي، ويحدث هذا في الحالات التي لا تعرف فيها عدد المرات التي يجب أن تنفذها الحلقة، كأن تعتمد على إدخال المستخدم مثلًا.
يوضح المثال التالي حلقة <code>while</code> يمكن مقاطعتها، وهو مثال مُطوَّر من برنامج <code>wisdom.sh</code> من المثال المشروح في [[Bash/while loop|حلقة While في Bash]]:<syntaxhighlight lang="bash">
#!/bin/bash
# هذا البرنامج يطبع أمثالًا ونصائح
# يمكنك الخروج الآن بطريقة أفضل.
FORTUNE=/usr/games/fortune
while true; do
echo "On which topic do you want advice?"
echo "1.  politics"
echo "2.  startrek"
echo "3.  kernelnewbies"
echo "4.  sports"
echo "5.  bofh-excuses"
echo "6.  magic"
echo "7.  love"
echo "8.  literature"
echo "9.  drugs"
echo "10. education"
echo
echo -n "Enter your choice, or 0 for exit: "
read choice
echo
case $choice in
    1)
    $FORTUNE politics
    ;;
    2)
    $FORTUNE startrek
    ;;
    3)
    $FORTUNE kernelnewbies
    ;;
    4)
    echo "Sports are a waste of time, energy and money."
    echo "Go back to your keyboard."
    echo -e "\t\t\t\t -- \"Unhealthy is my middle name\" Soggie."
    ;;
    5)
    $FORTUNE bofh-excuses
    ;;
    6)
    $FORTUNE magic
    ;;
    7)
    $FORTUNE love
    ;;
    8)
    $FORTUNE literature
    ;;
    9)
    $FORTUNE drugs
    ;;
    10)
    $FORTUNE education
    ;;
    0)
    echo "OK, see you!"
    break
    ;;
    *)
    echo "That is not a valid choice, try a number from 0 to 10."
    ;;
esac 
done
</syntaxhighlight>لاحظ أمر <code>break</code> الذي يُنهي الحلَقة فقط -وليس البرنامج-. يمكن رؤية هذا بوضوح عن طريق إضافة أمر <code>echo</code> في نهاية البرنامج، وسيُنفَّذ أمر <code>echo</code> أيضًا عند كتابة مُدخَل يسبب تنفيذ أمر <code>break</code> (حين يكتب المستخدم "<code>0</code>"). كذلك فإن أمر <code>break</code> يسمح -في حالة الحلقات المتداخلة- بتحديد أي الحلقات التي تخرج، انظر صفحات دليل <code>info</code> للمزيد.
== أمر Continue ==
تعيد عبارة <code>continue</code> تكرار حلقة <code>for</code> أو <code>while</code> أو <code>until</code> أو <code>select</code> المُرفقة، وحين تُستخدم في حلقة <code>for</code> فإن المتغير الحاكم -controlling variable- يأخذ قيمة العنصر التالي في القائمة. أما في حالة استخدامها في حلقة <code>while</code> أو <code>until</code> فإن التنفيذ يعود مرة أخرى مع وضع أمر الاختبار <code>TEST-COMMAND</code> في أول الحلقة.
== أمثلة ==
في المثال التالي تُحوَّل حالة أحرف أسماء الملفات إلى الحالة الصغرى، وتعيد عبارة <code>continue</code> تنفيذ الحلقة إن لم تكن ثمة حروف تحتاج إلى تحويل حالتها.
لا تأخذ هذه الأوامر كثيرًا من موارد النظام، ورغم أن مثل تلك المشاكل يمكن حلها باستخدام أمريْ <code>sed</code> و <code>awk</code> على الأرجح، لكن على أي حال من المفيد معرفة هذا الأسلوب في الحل إذ يكون مفيدًا عند تنفيذ مهام كبيرة، ولن يكون ذلك ضروريًا إن أُدخلت الاختبارات في المواضع الصحيحة داخل البرنامج موفِّرةً موارد النظام:<syntaxhighlight lang="bash">
[hsoub@alaraby ~/test] cat tolower.sh
#!/bin/bash
# يحوِّل هذا البرنامج كل أسماء الملفات التي تحتوي حروفًا كبيرة إلى أسماء بحروف صغيرة.
LIST="$(ls)"
for name in "$LIST"; do
if [[ "$name" != *[[:upper:]]* ]]; then
continue
fi
ORIG="$name"
NEW=`echo $name | tr 'A-Z' 'a-z'`
mv "$ORIG" "$NEW"
echo "new name for $ORIG is $NEW"
done
</syntaxhighlight>هذا البرنامج لديه نقطة ضعف واحدة على الأقل، وهي أنه يستبدل الملفات الحالية، ولا يكون أمر <code>noclobber</code> مفيدًا إلا عند حدوث إعادة توجيه. كذلك فإن خيار <code>b-</code> لأمر <code>mv</code> يوفر أمانًا أكثر، لكن ذلك الأمان لا يفيد إلا في حالة استبدال غير مقصود، كما ترى في المثال التالي:<syntaxhighlight lang="bash">
[hsoub@alaraby ~/test] rm *
[hsoub@alaraby ~/test] touch test Test TEST
[hsoub@alaraby ~/test] bash -x tolower.sh
++ ls
+ LIST=test
Test
TEST
+ [[ test != *[[:upper:]]* ]]
+ continue
+ [[ Test != *[[:upper:]]* ]]
+ ORIG=Test
++ echo Test
++ tr A-Z a-z
+ NEW=test
+ mv -b Test test
+ echo 'new name for Test is test'
new name for Test is test
+ [[ TEST != *[[:upper:]]* ]]
+ ORIG=TEST
++ echo TEST
++ tr A-Z a-z
+ NEW=test
+ mv -b TEST test
+ echo 'new name for TEST is test'
new name for TEST is test
[hsoub@alaraby ~/test] ls -a
./  ../  test  test~
</syntaxhighlight>يأتي أمر <code>tr</code> كجزء من حزمة <code>textutils</code>، ويمكنه إجراء جميع أنواع التحويلات على الملفات.
== انظر أيضًا ==
* [[Bash/regular expressions|التعابير النمطية في Bash]].
* [[Bash/examples using grep|أمثلة عن استخدام grep]].
== مصادر ==
<span> </span>
* [http://tldp.org/LDP/Bash-Beginners-Guide/html/sect_09_05.html دليل Bash للمبتدئين، الباب التاسع "المهام التكرارية"، الفصل الخامس "عبارتيْ Break و Continue"].

مراجعة 03:44، 9 أغسطس 2018


أمر Break

تُستخدم عبارة Break للخروج من الحلقة التكرارية الحالية قبل موعد خروجها الأصلي، ويحدث هذا في الحالات التي لا تعرف فيها عدد المرات التي يجب أن تنفذها الحلقة، كأن تعتمد على إدخال المستخدم مثلًا.

يوضح المثال التالي حلقة while يمكن مقاطعتها، وهو مثال مُطوَّر من برنامج wisdom.sh من المثال المشروح في حلقة While في Bash:

#!/bin/bash

# هذا البرنامج يطبع أمثالًا ونصائح
# يمكنك الخروج الآن بطريقة أفضل.

FORTUNE=/usr/games/fortune

while true; do
echo "On which topic do you want advice?"
echo "1.  politics"
echo "2.  startrek"
echo "3.  kernelnewbies"
echo "4.  sports"
echo "5.  bofh-excuses"
echo "6.  magic"
echo "7.  love"
echo "8.  literature"
echo "9.  drugs"
echo "10. education"
echo

echo -n "Enter your choice, or 0 for exit: "
read choice
echo

case $choice in
     1)
     $FORTUNE politics
     ;;
     2)
     $FORTUNE startrek
     ;;
     3)
     $FORTUNE kernelnewbies
     ;;
     4)
     echo "Sports are a waste of time, energy and money."
     echo "Go back to your keyboard."
     echo -e "\t\t\t\t -- \"Unhealthy is my middle name\" Soggie."
     ;;
     5)
     $FORTUNE bofh-excuses
     ;;
     6)
     $FORTUNE magic
     ;;
     7)
     $FORTUNE love
     ;;
     8)
     $FORTUNE literature
     ;;
     9)
     $FORTUNE drugs
     ;;
     10)
     $FORTUNE education
     ;;
     0)
     echo "OK, see you!"
     break
     ;;
     *)
     echo "That is not a valid choice, try a number from 0 to 10."
     ;;
esac  
done

لاحظ أمر break الذي يُنهي الحلَقة فقط -وليس البرنامج-. يمكن رؤية هذا بوضوح عن طريق إضافة أمر echo في نهاية البرنامج، وسيُنفَّذ أمر echo أيضًا عند كتابة مُدخَل يسبب تنفيذ أمر break (حين يكتب المستخدم "0"). كذلك فإن أمر break يسمح -في حالة الحلقات المتداخلة- بتحديد أي الحلقات التي تخرج، انظر صفحات دليل info للمزيد.

أمر Continue

تعيد عبارة continue تكرار حلقة for أو while أو until أو select المُرفقة، وحين تُستخدم في حلقة for فإن المتغير الحاكم -controlling variable- يأخذ قيمة العنصر التالي في القائمة. أما في حالة استخدامها في حلقة while أو until فإن التنفيذ يعود مرة أخرى مع وضع أمر الاختبار TEST-COMMAND في أول الحلقة.

أمثلة

في المثال التالي تُحوَّل حالة أحرف أسماء الملفات إلى الحالة الصغرى، وتعيد عبارة continue تنفيذ الحلقة إن لم تكن ثمة حروف تحتاج إلى تحويل حالتها.

لا تأخذ هذه الأوامر كثيرًا من موارد النظام، ورغم أن مثل تلك المشاكل يمكن حلها باستخدام أمريْ sed و awk على الأرجح، لكن على أي حال من المفيد معرفة هذا الأسلوب في الحل إذ يكون مفيدًا عند تنفيذ مهام كبيرة، ولن يكون ذلك ضروريًا إن أُدخلت الاختبارات في المواضع الصحيحة داخل البرنامج موفِّرةً موارد النظام:

[hsoub@alaraby ~/test] cat tolower.sh
#!/bin/bash

# يحوِّل هذا البرنامج كل أسماء الملفات التي تحتوي حروفًا كبيرة إلى أسماء بحروف صغيرة.

LIST="$(ls)"

for name in "$LIST"; do

if [[ "$name" != *[[:upper:]]* ]]; then
continue
fi

ORIG="$name"
NEW=`echo $name | tr 'A-Z' 'a-z'`

mv "$ORIG" "$NEW"
echo "new name for $ORIG is $NEW"
done

هذا البرنامج لديه نقطة ضعف واحدة على الأقل، وهي أنه يستبدل الملفات الحالية، ولا يكون أمر noclobber مفيدًا إلا عند حدوث إعادة توجيه. كذلك فإن خيار b- لأمر mv يوفر أمانًا أكثر، لكن ذلك الأمان لا يفيد إلا في حالة استبدال غير مقصود، كما ترى في المثال التالي:

[hsoub@alaraby ~/test] rm *

[hsoub@alaraby ~/test] touch test Test TEST

[hsoub@alaraby ~/test] bash -x tolower.sh
++ ls
+ LIST=test
Test
TEST
+ [[ test != *[[:upper:]]* ]]
+ continue
+ [[ Test != *[[:upper:]]* ]]
+ ORIG=Test
++ echo Test
++ tr A-Z a-z
+ NEW=test
+ mv -b Test test
+ echo 'new name for Test is test'
new name for Test is test
+ [[ TEST != *[[:upper:]]* ]]
+ ORIG=TEST
++ echo TEST
++ tr A-Z a-z
+ NEW=test
+ mv -b TEST test
+ echo 'new name for TEST is test'
new name for TEST is test

[hsoub@alaraby ~/test] ls -a
./  ../  test  test~

يأتي أمر tr كجزء من حزمة textutils، ويمكنه إجراء جميع أنواع التحويلات على الملفات.

انظر أيضًا

مصادر