Wydaje się, że oba sygnalizują BASH rozpoczęcie kolejnego polecenia po symbolach, ale czy istnieje wyraźna różnica?
command-line
bash
Michael Terry
źródło
źródło
Możesz wypróbować różnicę dla siebie:
ls /invalid/path && echo "hello!"
ponieważ / nieprawidłowa / ścieżka nie istnieje, ls nie może wyświetlić listy katalogów. Nie powiedzie się komunikat o błędzie: „ls: / invalid / path: Brak takiego pliku lub katalogu”. Druga połowa polecenia (echo „Hello!”) Jest nigdy jeszcze stracony , ponieważ pierwsza połowa nie powiodło się.
ls /invalid/path ; echo "hello!"
Ten sam komunikat o błędzie pojawia się jak poprzednio, ale tym razem druga część jest wykonywana !
ls: / invalid / path:
Witaj w takim pliku lub katalogu !
Dlaczego to jest przydatne?
Załóżmy, że chcesz wyodrębnić plik o nazwie archive.tar.gz
Możesz użyć polecenia
tar zxvf archive.tar.gz && rm archive.tar.gz
.Jeśli z jakiegoś powodu rozpakowanie archiwum nie powiedzie się, druga część nie zostanie wykonana! Możesz spróbować jeszcze raz.
Jeśli użyjesz ; w tej samej sytuacji archiwum jest usuwane i nie można spróbować ponownie.
źródło
&&
oznaczaAND
, że drugie polecenie zostanie wykonane tylko wtedy, gdy pierwsze zwróci prawdę (bez błędów).źródło
AND
wykonaniu drugi parametr staje się nieistotny, jeśli pierwszy jest równy,false
a zatem kod bazowy zostaje zoptymalizowany w celu odroczenia oceny drugiego parametru, dopóki nie dowie się, jaki jest pierwszy.&&
jest tylko operatorem binarnym, funkcją. Jedyną „specjalną” rzeczą jest to, że jest to notacja infiksowa (która i tak jest standardem dla większości tego rodzaju operatorów) i opóźnione wykonanie drugiego operandu. Że opóźnia wykonanie rzeczywiście daje mu zdolność do wykorzystania jako coś, co może być postrzegane jako koncepcyjnieif
oświadczenia w tym kontekście , ale nie zabrać z faktu, że to pierwotnie zamierzonego użycia jest w zasięgu warunkowego o rzeczywistejif
oświadczenia. Użycie tutaj jest bardziej „hackowaniem”.a && b || c = (a && b) || c
. Prosta kolejność oceny. Naprawdę nie ma w tym żadnej tajemnicy. Gdybyś napisał je jak typowe funkcje, po prostu wyglądałobyor(and(a, b), c)
. Ta logika jest taka sama zarówno wif
warunkowym, jak i podczas wprowadzania jej bezpośrednio do wiersza poleceń, ponieważ&&
i||
są operatorami , biorą dwa operandy i zwracają inny.Aktualizacja : Dodałem jako skrypt, aby wyróżnić niektóre z możliwych pułapek:
Ponieważ nikt inny nie wspomniał o „||”, zrobię to
Aktualizacja 2 : niektóre ważne przeredagowanie tutaj
&& jest jak „wtedy” wyrażenia „jeśli”, które odpowiada „prawda”
|| NIE jest jak „else” w stwierdzeniu „if”.
|| jest jak „wtedy” wyrażenia „jeśli”, które odpowiada na „fałsz”
Dokładniej, && testuje $? zwraca wartość
poprzednioostatnio wykonanej instrukcji i przekazuje kontrolę do instrukcji lub podpowłoki bezpośrednio po && ... przekazuje kontrolę tylko, jeśli $? jest prawdziwy.|| jest podobny i często widuje się po instrukcji &&, ale testuje ona na fałszywą wartość zwracaną ($?) z
poprzednioostatnio wykonanej instrukcji ... Uwaga! , Nota Bene! Uwaga: jeśli poprzednia instrukcja jest instrukcją &&, która ponownie sprawdza fałsz, gdy spodziewasz się, że jest to prawda, to || zareaguje na fałsz, więc mieszanie obu na tej samej linii może być ryzykowneGłównym punktem, który próbuję zrobić, jest błąd, który popełniłem. tj .:
## [[warunek]] i&A || B
jest nie nie zachowuje się jak C / C ++ stylu trójskładnikowego. tj .:
// (warunek)? Odp .: B
Zobacz poniższy skrypt, aby zobaczyć przykłady „nieoczekiwanych” wyników z „A”
Test podstawowy oraz && i || instrukcja musi znajdować się w tym samym wierszu ...
Uruchom ten skrypt, aby zobaczyć, co może się nie powieść podczas używania && i || Ostatnio wykonywane oświadczenie nie może być jeden oczekujesz ..
[[warunek]] && echo Hello || echo Pożegnanie .... jest zwykle bezpieczne,
ponieważ dobrze uformowane echo zwróci prawdę.
ale co z dostępem do pliku, który nie wychodzi?
źródło
próbować
i
Zobacz różnicę
źródło
Polecenie (funkcja, w przypadku skryptu) po
&&
jest wykonywane w zależności od parametru RETVAL pierwszego polecenia (funkcja, w przypadku skryptu). Zmusza pierwsze polecenie do zwrócenia wartości 0, jeśli zakończy się powodzeniem. Możemy sprawdzić wartość zwracaną, aby wykonać dalsze polecenia.źródło