2013-02-01 14 views
7

Questo script dimostra la definizione di una funzione bash con parentesi versi con parentesi. Le parentesi hanno il piacevole effetto di creare variabili d'ambiente create nella funzione "locale", immagino perché il corpo della funzione viene eseguito come una sottoscheda. L'output è:Definizione del corpo della funzione bash utilizzando parentesi anziché controventi

A=something 
A= 
B=something 
B=something 

La domanda è se questa sintassi è consentita per la definizione di una funzione.

#!/bin/bash 

foo() (
    export A=something 
    echo A=$A 
) 

bar() { 
    export B=something 
    echo B=$B 
} 

foo 
echo A=$A 
bar 
echo B=$B 
+0

indovina sbagliata. Queste variabili sembrano essere locali, perché questo [comando composto] (http://wiki.bash-hackers.org/syntax/basicgrammar#compound_commands) viene eseguito in un gruppo separato (contesto), NON una sottotitola !! – Florian

+0

@Florian Bash e POSIX lo chiamano un "ambiente subshell", forse è quello che intendeva. Ma vero: non un nuovo processo. –

risposta

7

Sì, quella sintassi è consentita. Come descritto nella bash man page, la definizione di una funzione bash è:

[ function ] name() compound-command [redirection] 

Alcuni più descrizione (anche dalla pagina man):

Il corpo della funzione è il comando composto compound-command. Questo comando è in genere un elenco di comandi tra { e }, ma può essere qualsiasi comando elencato in Comandi composti precedente.

() e {} gli elenchi allegati sono comandi composti. L'elenco completo (ancora una volta dalla pagina man, appena modificato verso il basso per un elenco semplice):

Un comando composto è uno dei seguenti:

(list) 
{ list; } 
((expression)) 
[[expression]] 
for name [ in word ] ; do list ; done 
for ((expr1 ; expr2 ; expr3)) ; do list ; done 
select name [ in word ] ; do list ; done 
case word in [ [(] pattern [ | pattern ] ...) list ;; ] ... esac 
if list; then list; [ elif list; then list; ] ... [ else list; ] fi 
while list; do list; done 
until list; do list; done 
+0

Grazie per quello. Noto che questo non funziona: foo() (esportazione A = qualcosa; eco A = $ A) bar() {export B = qualcosa; echo B = $ B} Questo funziona: foo() (esportazione A = qualcosa; eco A = $ A;) bar() {export B = qualcosa; echo B = $ B; } Eppure così: (echo Ciao; echo Bye) – ELO

+1

Scusa, non sono sicuro di aver capito - stai chiedendo qualcosa sul punto e virgola? –

+0

La mente è saltata, grazie! –

1

Entrambi sono validi, e come Carl menzionata qualsiasi comando composto può essere utilizzato anche, ad esempio:

$ f() if [ "$1" = 'a' ]; then echo 'equals a'; fi 
$ f a 
equals a 
$ f b 
$ 

POSIX 7 2.9.5 Definizione della funzione comandohttp://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html#tag_18_09_05:

Il formato di un comando di definizione funzione è la seguente:

fname() composto comando [io-reindirizzamento ...]

[...] Il composto argomento -comando rappresenta un comando composto, come descritto in Comandi composti.

Poi 2.9.4 Comandi compostihttp://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html#tag_18_09_04:

(composto-list) [...] le assegnazioni di variabile e comandi incorporati che influenzano l'ambiente non deve rimanere in vigore dopo la lista finisce.

{compound-list;} Esegui elenco composto nell'ambiente di processo corrente.

La semantica è lo stesso che utilizzare () senza una definizione di funzione: non crea un nuovo processo, ma viene eseguito in quanto POSIX e Bash chiamano un "ambiente di subshell".

Problemi correlati