2010-12-08 31 views
5

J'ai un script bash similaire à ce qui suit:Comment utiliser la même variable bash entre un shell parent et l'enfant shell


function test 
{ 
    running=$(($running - 1)) 
} 

running=0 
test & 
echo $running 

 

Parce que la fonction de test est exécuté dans un shell sous il ne modifie pas la variable en cours d'exécution et je reçois 0 écho à l'écran. J'ai besoin du sous-shell pour pouvoir changer les variables des shells parents, comment cela peut-il être fait? J'ai essayé l'exportation mais en vain.

EDIT Merci pour toutes les réponses utiles, La raison pour laquelle je veux exécuter cette fonction en arrière-plan est de permettre l'exécution simultanée de plusieurs fonctions. J'ai besoin de pouvoir rappeler le script parent pour le dire quand toutes les fonctions sont terminées. J'avais utilisé des pids pour le faire mais je n'aime pas avoir à vérifier si plusieurs processus sont en permanence en boucle.

+3

En général, cela ne peut pas être fait. Pourquoi exécutez-vous la fonction dans un sous-shell? Et en arrière-plan? Si vous nous dites ce que vous essayez de faire, nous pourrions peut-être vous aider davantage. – thkala

+0

En fait, vous exportez "down", mais pas "up". Dans ce cas, supprimer '&' vous aidera, mais je crois que vous devez vraiment l'exécuter en arrière-plan, si vous mettez cela. – khachik

+0

'((running--))' ou '((--running))' –

Répondre

2

Vous ne pouvez pas vraiment. Chaque shell a une copie de l'environnement.

voir Can a shell script set environment variables of the calling shell?

Mais pour ce que vous faites dans votre exemple, essayez ce que votre script:

 
#!/bin/bash 

function testSO 
{  
    running=$(($running - 1)); 
    return $running; 
} 

et invoquez comme:

 
running=$(testSO) 

Si vous voulez seulement retourne effectivement une valeur, puis renvoie simplement la valeur de la fonction.

+0

c'est la même chose que de lancer 'testSO' au premier plan, mais ce n'était pas le OP veut, je pense. – khachik

+2

Vous confondez deux manières différentes de "renvoyer" des informations à partir d'une fonction: le renvoyer comme un statut (ce que fait 'return'), et l'envoyant à stdout (qui est ce que' $ (...) 'capture). Vous devez utiliser 'echo $ running' et' running = $ (testSO) 'ou' return $ running' et 'testSO; running = $? 'pas un mélange des deux. Etant donné que "running" ne semble pas être un indicateur de statut (c'est-à-dire que non zéro indique une erreur), j'irais dans la première approche. –

+0

Merci pour la clarification. Je ne suis pas un wiz avec des sous-couches, donc j'apprécie d'apprendre plus. –

0

Utilisez des alias à la place des fonctions. Ou écrivez un script avec le corps de la fonction et exécutez-le avec source.

Les deux solutions évitent de créer une sous-coque.