GNU/Linux >> Znalost Linux >  >> Linux

Přednost logických operátorů Shell &&, ||?

Snažím se pochopit, jak funguje priorita logického operátora v bash. Například bych očekával, že následující příkaz nebude nic opakovat.

true || echo aaa && echo bbb

Na rozdíl od mého očekávání však bbb se vytiskne.

Může mi někdo prosím vysvětlit, jak mohu dát smysl složenému && a || operátory v bash?

Přijatá odpověď:

V mnoha počítačových jazycích jsou operátory se stejnou prioritou asociativní vlevo. To znamená, že při absenci seskupovacích struktur se nejprve provádějí operace zcela vlevo. Bash není výjimkou z tohoto pravidla.

To je důležité, protože v Bash && a || mají stejnou přednost.

Ve vašem příkladu se tedy stane, že operace zcela vlevo (|| ) se provede jako první:

true || echo aaa

Protože true je zjevně pravda, || zkratuje operátor a celé tvrzení je považováno za pravdivé bez nutnosti vyhodnocovat echo aaa jak byste očekávali. Nyní zbývá provést operaci zcela vpravo:

(...) && echo bbb

Vzhledem k tomu, že první operace byla vyhodnocena jako true (tj. měla stav ukončení 0), je to jako byste spouštěli

true && echo bbb

takže && nezkratuje, což je důvod, proč vidíte bbb ozvalo se.

Stejné chování byste získali s

false && echo aaa || echo bbb

Poznámky založené na komentářích

  • Upozorňujeme, že pravidlo levé asociativnosti je pouze následuje, když oba operátory mají stejné přednost. To není případ, kdy tyto operátory používáte ve spojení s klíčovými slovy jako [[...]] nebo ((...)) nebo použijte -o a -a operátory jako argumenty pro test nebo [ příkazy. V takových případech AND (&& nebo -a ) má přednost před NEBO (|| nebo -o ). Děkujeme komentáři Stephana Chazelase za objasnění tohoto bodu.
  • Zdá se, že v jazycích C a C podobných && má vyšší prioritu než || což je pravděpodobně důvod, proč jste očekávali, že se váš původní konstrukt bude chovat jako

    true || (echo aaa && echo bbb). 
    

    To však není případ Bash, ve kterém mají oba operátory stejnou prioritu, a proto Bash analyzuje váš výraz pomocí pravidla asociativity vlevo. Díky Kevinovu komentáři za to, že to přinesl.

  • Mohou také nastat případy, kdy všechny 3 výrazy se vyhodnocují. Pokud první příkaz vrátí nenulový stav ukončení, || nezkratuje a pokračuje ve vykonání druhého příkazu. Pokud se druhý příkaz vrátí s nulovým stavem ukončení, pak && nezkratuje a bude proveden třetí příkaz. Díky komentáři Ignacia Vazqueze-Abramse za to, že to přinesl.

Související:Udělit práva na certifikát aplikaci prostřednictvím shellu?
Linux
  1. Moc (Shell) lidem

  2. Pointa externího příkazu `cd`?

  3. Neočekávané chování skriptu Shell?

  1. Význam $? Ve skriptu Shell?

  2. Jak změnit výchozí prostředí v Linuxu

  3. Jak převést hex na ASCII znaky v prostředí Linuxu?

  1. Přizpůsobení prostředí Bash

  2. Jak získat název aktuální větve git do proměnné v shell skriptu?

  3. Jaké je použití $# v Bash