Hvad er kommandosubstitution i en skal? [duplikat]

Dette spørgsmål har allerede svar her :

Kommentarer

  • OK, alle skal slappe af og stoppe med at beskylde hinanden for trolling. Hvis du ikke ' ikke kan lide et spørgsmål, skal du nedstemme eller ignorere det og gå væk . Hvis du føler at du ' bliver angrebet i kommentarer, skal du ikke engagere dig, men markere og gå væk .
  • Også relateret: Hvad ' er forskellen mellem $ (stuff) og `stuff ?
  • Visning af output af en kommando ved hjælp af kommandosubstitution og echo er et dårligt eksempel på kommandosubstitution, fordi 1) output ville have været vist alligevel, 2) printf er sikrere at bruge til variable data. Eksemplet kunne lige så godt skrives date | sed 's/^/Today is /'
  • @Kusalananda Jeg kan se dit pointe at udskrive det med det samme (med printf ) er ubrugelig. Jeg ændrede formuleringen lidt, fra straks til sometime later, er det mere tiltalende?
  • Eksemplet kan være thedate=$(date), efterfulgt af printf 'The date is %s\n' "$thedate".

Svar

" Kommandosubstitution " er navnet på funktionen af shell-sproget, der giver dig mulighed for at udføre en kommando og få output fra den kommando erstattet ( erstatning) teksten for kommandoen.

Der er ingen anden funktion i shell-sproget, der giver dig mulighed for at gøre det.

En kommandosubstitution, dvs. hele $(...) udtryk rstattes af dets output, som er den primære anvendelse af kommandosubstitutioner.

Den kommando, som kommandosubstitutionen udfører, udføres i en subshell, hvilket betyder, at det har sit eget miljø, der ikke påvirker den overordnede shells miljø.

Ikke alle subshell-henrettelser er kommandosubstitutioner end ugh (se flere eksempler i slutningen).

Eksempel, der viser, at en kommandosubstitution udføres i en subshell:

$ s=123 $ echo "hello $( s=world; echo "$s" )" hello world $ echo "$s" 123 

Her er variabel s er indstillet til strengen 123. På den næste linje påkaldes echo på en streng, der indeholder resultatet af en kommandosubstitution. Kommandosubstitutionen indstiller s til strengen world og gentager denne streng. Strengen world er output for kommandoen i kommandosubstitutionen og hvis dette blev kørt under set -x, ville vi se, at den anden linje ovenfor ville være udvidet til echo "hello world", som producerer hello world på terminalen:

$ set -x $ echo "hello $( s=world; echo "$s" )" ++ s=world ++ echo world + echo "hello world" hello world 

(bash tilføjer et ekstra niveau af + til hvert niveau af en kommandosubstitutionsunderskal i sporingsoutputtet, andre skaller gør muligvis ikke dette)

Endelig viser vi, at kommandoen inde i kommandosubstitutionen blev kørt i sin egen subshell, fordi den ikke påvirkede værdien af s i den kaldende skal (værdien af s er stadig 123, ikke world).

Der er andre situationer, hvor kommandoer udføres i subshells, såsom i

echo "hello" | read message 

I bash, medmindre du indstiller lastpipe -indstillingen (kun i ikke-interaktive forekomster), udføres read i en subshell, hvilket betyder at $message ikke ændres i den overordnede shell, dvs. at echo "$message" efter ovenstående kommando vil ekko en tom streng (eller hvilken som helst værdi $message var før).

En proceserstatning i bash udføres også i en subshell:

cat < <( echo "hello world" ) 

Også dette adskiller sig fra en kommandosubstitution.

Kommentarer

  • For bash 4.2 op, hvis shopt lastpipe er indstillet, jobkontrol ikke er aktiv, og rørledningen ikke har baggrund, kører den sidste kommando ikke i en subshell.
  • Du siger, “Der er ingen anden funktion i shell-sproget, der giver dig mulighed for at gøre det.” Nå, med risiko for at klippe hår, kan du gøre cmd₁ > myfile / read -r var < myfile / cmd₂ "$var" . Hvis det er nødvendigt, kan du udvide det til at håndtere data med flere linjer.
  • @ G-Man Ja, og du kan også skrive et nyt shell-script til en fil og udføre det.Der er ingen anden funktion, der giver mulighed for at erstatte et stykke tekst med output fra en kommando.

Svar

a=$(command) 

gemmer resultatværdien af command i variablen.

Der er virkelig ikke mere.

Som en sidebemærkning tror jeg:

a=`command` 

er udfaset og har samme betydning som ovenfor.

Kommentarer

  • resultat her er standardoutputtet af kommandoen fjernet fra al dens efterfølgende nye linje tegn (og nogle variationer mellem skaller, hvis output ikke er tekst). Bemærk, at `...` er Bourne af csh-syntaks, mens $(...) er Korn / POSIX-syntaksen (med `...` understøttes stadig for bagudkompatibilitet)
  • @St é phaneChazelas Tak for værdifulde oplysninger, og du er velkommen til at redigere svaret, så det inkluderer det.

Skriv et svar

Din e-mailadresse vil ikke blive publiceret. Krævede felter er markeret med *