Jag gör inte väldigt mycket skalskript, så jag blev lite förvånad när jag läste dokumentationen för git submodule och jag såg syntaxen som de använde i den här dokumentationen:
A icke-noll avkastning från kommandot i någon undermodul får bearbetningen att avslutas. Detta kan åsidosättas genom att lägga till
|| :i slutet av kommandot.
Jag var tvungen att leta upp att || : var en förkortning för att tvinga ett kommando att avsluta framgångsrikt. Varje gång jag måste göra ett kommandoutgång , Jag använde || true. Anses || : för att vara mer idiomatisk?
Kommentarer
Svar
true byggdes inte in i Bourne-skalet. : var alltid (det var sättet att skriva in kommentarer innan # infördes).
Det, och därför det är kortare att skriva är förmodligen den främsta anledningen till att folk föredrar : framför true.
Notera en annan skillnad i POSIX-skal (för bash, endast i POSIX-läge): medan true är ett vanligt inbyggt (behöver inte ens byggas in) , : är en special inbyggd. Det har några konsekvenser, varav de flesta är osannolika att ha någon inverkan i detta specifika fall:
-
Om ett
:-kommando misslyckas, inklusive på grund av en misslyckad omdirigering, som får skalet att gå ut. I praktiken kommer det förmodligen inte att göra skillnad om du inte skickar omdirigeringar till:$ sh -c ": > / ; echo HERE" sh: 1: cannot create /: Is a directory $ sh -c "true > /; echo HERE" sh: 1: cannot create /: Is a directory HERE -
i
var=value :,varförblir inställd påvalueefter:returnerar, inte i fallet medtrue:$ var=1; var=2 : ; echo "$var" 2 $ var=1; var=2 true; echo "$var" 1
Observera också att || true fungerar i skal av rc och csh familjer men inte || : (men inte för att avbryta set -e i csh).
|| : är inte samma som :. Det betyder eller kör : annars (det vill säga om föregående pipeline misslyckas).
set -e false
Skulle att skalet skulle gå ut på grund av set -e (aka errexit alternativet) och har utgångsstatus som inte är noll (fel). set -e -effekten avbryts om kommandot som returnerar en utgångsstatus som inte är noll används som villkor som i:
if false; then ... while false; do ... false && : ... false || : ...
false && : avbryter endast set -e. false || : avbryter effekten av set -e och sätter utgångsstatus till 0 så är det mer idiomatiskt att säga att vi vill ignorera en felkod för kommandot. De flesta skulle hävda att || true är mer läsbart (förmedlar avsikten tydligare).
Kommentarer
-
&& :är lysande, finns det några dokument eller ytterligare läsning om detta? Google saknar mig för att försöka hitta den här typen av nyckelord …
Svar
De flesta av dessa svar misslyckas med att ta itu med den vanligaste användningen av :.
För det första är denna diskussion inte relaterad till något skal som inte är Bourne-skal (sh) derivat. Som sagt, alla Bourne-derivatskal ser true och : som samma sak. Tidigare uppmuntrades programmerare att använda : istället för true, eftersom : alltid är en inbyggd medan det tidigare fanns fall där true inte alltid var en inbyggd.
: har två användningsområden. Det är inte en synonym för #, men det har en annan funktion. När du felsöker ditt skript under en set -x tappas rader där # används av tolkaren och ignoreras helt, medan rader med : analyseras och utvärderas. Detta är verkligen användbart vid felsökning eftersom under -x dessa rader visas och deras värde efter utvärdering visas.Det är som att sätta print uttalanden i din kod som bara visas under -x -läge. Var försiktig med värdena efter : eftersom de är riktig kod och biverkningarna kan påverka ditt program.
Kommentarer
- Vad är den andra användningen?
Svar
Generellt, i bash, är kolon : och true är ekvivalent.
Är | | : anses vara mer idiomatisk?
Jag tror att den baseras på -kontext .
Om du vill ha en return value, eller en condition är alltid sant , bör du använda true nyckelord, det kommer att göra din kod tydligare och låta tittarna veta att du vill betona värdet true , dvs.:
while true; do something
eller
<commnad> RETURN_VALUE= $? || true
Och om du vill gör ingenting , eller NOP i skal ska du använda kolon :
if condition then : # DO NOTHING HERE else do something fi
eller
while conditon do : # DO NOTHING HERE done
||:(utan utrymme) också är giltigt i bash. Det gör samma sak som|| :eller|| true.