Kommando substitution
Inom datorer är kommandosubstitution en möjlighet som gör att ett kommando kan köras och dess utdata klistras tillbaka på kommandoraden som argument till ett annat kommando . Kommandosubstitution dök först upp i Bourne-skalet , introducerat med version 7 Unix 1979, och har förblivit ett kännetecken för alla senare Unix-skal . Funktionen har sedan dess antagits i andra programmeringsspråk också, inklusive Perl , PHP , Ruby och Microsofts Powershell under Windows . Det visas också i Microsofts CMD.EXE i FOR
-kommandot och ( )
-kommandot.
Syntax och semantik
Skal implementerar vanligtvis kommandosubstitution genom att skapa en underordnad process för att köra det första kommandot med dess standardutdata tillbaka till skalet, som läser den utdatan och analyserar den till ord separerade med blanksteg . Eftersom skalet inte kan veta att det har all utdata från barnet tills röret stängs eller barnet dör, väntar det tills dess innan det startar en annan barnprocess för att köra det andra kommandot.
Det här C- skalexemplet visar hur man kan söka efter alla C -filer som innehåller strängen malloc
med hjälp av fgrep
och sedan redigera alla som hittas med vi
-redigeraren. Den syntaktiska notationen som visas här, `
... `
, med citationstecken som avgränsare , är den ursprungliga stilen och stöds av alla vanliga Unix-skal.
#!/bin/csh vi ` fgrep -l malloc *.c `
Invändningar har framförts mot både syntaxen , hur den skrivs och semantiken , hur den fungerar.
Även om det är lätt att skriva, en viktig faktor för en interaktiv kommandoprocessor, har syntaxen kritiserats för att vara besvärlig att kapsla, att placera en kommandosubstitution i en annan, eftersom både vänster och höger avgränsare är desamma. KornShell (ksh) löste detta med en alternativ notation, $(
... )
, som lånade från den notationsstil som används för variabel substitution . Idag stöder de flesta UNIX-skal denna syntax. Microsofts PowerShell använder också denna notation, med samma semantik.
#!/bin/bash vi $( fgrep -l malloc *.c )
Semantiken, som bryter ut utdata till ord vid blanksteg, har också kritiserats. Det fungerade bra på tidiga Unix- system där filnamn aldrig innehöll mellanslag men det fungerar inte alls bra på moderna Windows- och Linux- system där filnamn säkert kan innehålla mellanslag. I något av dessa tidigare exempel, om något av filnamnen som matchas av *.c
jokertecknet innehåller ett mellanslag, kommer det filnamnet att delas upp i två separata argument till vi
, helt klart inte vad som var avsett. Hamilton C-skal löste detta med ett dubbelt bakåtcitat, ``
... ``
, som analyserar till ord endast vid radbrytningar.
Det här är ett exempel på kommandoersättning med operatorn ()
i PowerShell :
$MyVariable = ( ls ) echo $MyVariable
Uttryckssubstitution
En relaterad facilitet, uttrycksersättning, finns i språken Common Lisp och Scheme , anropade genom att använda komma-at-operatorn i ett uttryck markerat med bakåtcitat (eller "kvasicitat") operatorn, och i ABC , genom att använda ett uttryck som omges mellan bakåtcitat i en textvisning ( sträng bokstavlig ). Till exempel, ABC-kommandot WRITE '2 + 2 = `2+2`'
producerar utdata 2 + 2 = 4
.