web-dev-qa-db-fra.com

Comment vérifier si une variable est définie dans Bash?

Comment savoir si une variable est définie dans Bash?

Par exemple, comment vérifier si l'utilisateur a donné le premier paramètre à une fonction?

function a {
    # if $1 is set ?
}
1341
prosseek

(Généralement) la bonne façon

if [ -z ${var+x} ]; then echo "var is unset"; else echo "var is set to '$var'"; fi

${var+x} est un extension de paramètre qui n'indique rien si var n'est pas défini et remplace la chaîne x sinon.

Citations Digression

Les guillemets peuvent être omis (donc, nous pouvons dire ${var+x} au lieu de "${var+x}") car cette syntaxe et cette utilisation garantissent que cela ne fera que développer quelque chose qui ne nécessite pas de guillemets (puisqu'il est aussi étendu à x (qui ne contient pas de sauts de mots, il n'a donc pas besoin de guillemets), ou de rien (ce qui donne [ -z ], ce qui donne la même valeur (true) à celle de [ -z "" ]).

Cependant, bien que les citations puissent être omises en toute sécurité et que cela ne soit pas immédiatement évident pour tous (ce n'était même pas évident pour le premier auteur de cette explication de citations qui est également un codeur majeur de Bash), Il est parfois préférable d’écrire la solution avec des guillemets comme [ -z "${var+x}" ], au très faible coût possible d’une O(1) pénalité de rapidité. Le premier auteur a également ajouté cela en tant que commentaire à côté du code utilisant cette solution, en donnant l'URL de cette réponse, qui inclut également l'explication de la raison pour laquelle les guillemets peuvent être omis en toute sécurité.

(Souvent) dans le mauvais sens

if [ -z "$var" ]; then echo "var is blank"; else echo "var is set to '$var'"; fi

Cela est souvent faux car il ne fait pas la distinction entre une variable non définie et une variable définie sur la chaîne vide. Autrement dit, si var='', la solution ci-dessus générera "var is blank".

La distinction entre unset et "définir sur la chaîne vide" est essentielle dans les cas où l'utilisateur doit spécifier une extension ou une liste supplémentaire de propriétés, et que ne les spécifiant pas par défaut à une valeur non vide, alors que la spécification de la chaîne vide doit oblige le script à utiliser une extension vide ou une liste de propriétés supplémentaires.

La distinction peut ne pas être essentielle dans tous les scénarios. Dans ces cas, [ -z "$var" ] ira très bien.

2016
Lionel

Pour vérifier la variable chaîne non-null/non-zéro, c’est-à-dire, si défini, utilisez

if [ -n "$1" ]

C'est l'opposé de -z. Je me retrouve à utiliser -n plus que -z.

Vous l'utiliseriez comme:

if [ -n "$1" ]; then
  echo "You supplied the first parameter!"
else
  echo "First parameter not supplied."
fi
793
mbrannig

Voici comment vérifier si un paramètre est non défini ou vide ("Null") ou défini avec une valeur :

+--------------------+----------------------+-----------------+-----------------+
|                    |       parameter      |     parameter   |    parameter    |
|                    |   Set and Not Null   |   Set But Null  |      Unset      |
+--------------------+----------------------+-----------------+-----------------+
| ${parameter:-Word} | substitute parameter | substitute Word | substitute Word |
| ${parameter-Word}  | substitute parameter | substitute null | substitute Word |
| ${parameter:=Word} | substitute parameter | assign Word     | assign Word     |
| ${parameter=Word}  | substitute parameter | substitute null | assign Word     |
| ${parameter:?word} | substitute parameter | error, exit     | error, exit     |
| ${parameter?word}  | substitute parameter | substitute null | error, exit     |
| ${parameter:+Word} | substitute Word      | substitute null | substitute null |
| ${parameter+Word}  | substitute Word      | substitute Word | substitute null |
+--------------------+----------------------+-----------------+-----------------+

Source: POSIX: Expansion des paramètres :

Dans tous les cas indiqués avec "substitute", l'expression est remplacée par la valeur affichée. Dans tous les cas montrés avec "assign", le paramètre se voit attribuer cette valeur, qui remplace également l'expression.

433
Jens

Bien que la plupart des techniques mentionnées ici soient correctes, bash 4.2 prend en charge un test réel de la présence d'une variable ( man bash ), plutôt que de tester la valeur de la variable.

[[ -v foo ]]; echo $?
# 1

foo=bar
[[ -v foo ]]; echo $?
# 0

foo=""
[[ -v foo ]]; echo $?
# 0

Notamment, cette approche ne provoquera pas d'erreur lorsqu'elle est utilisée pour rechercher une variable non définie en mode set -u/set -o nounset, contrairement à de nombreuses autres approches, telles que l'utilisation de [ -z.

203
Russell Harmon

Il y a plusieurs façons de le faire, les suivantes étant l'une d'elles:

if [ -z "$1" ]

Cela réussit si $ 1 est nul ou non défini

174
ennuikiller

Pour voir si une variable est non vide, j'utilise

if [[ $var ]]; then ...       # `$var' expands to a nonempty string

L’opposé teste si une variable est non définie ou vide:

if [[ ! $var ]]; then ...     # `$var' expands to the empty string (set or not)

Pour voir si une variable est définie (vide ou non vide), j'utilise

if [[ ${var+x} ]]; then ...   # `var' exists (empty or nonempty)
if [[ ${1+x} ]]; then ...     # Parameter 1 exists (empty or nonempty)

L'inverse teste si une variable est non définie:

if [[ ! ${var+x} ]]; then ... # `var' is not set at all
if [[ ! ${1+x} ]]; then ...   # We were called with no arguments
62
phkoester

Je trouve toujours la table POSIX dans le autre réponse lente à grok, alors voici mon point de vue dessus:

   +----------------------+------------+-----------------------+-----------------------+
   |   if VARIABLE is:    |    set     |         empty         |        unset          |
   +----------------------+------------+-----------------------+-----------------------+
 - |  ${VARIABLE-default} | $VARIABLE  |          ""           |       "default"       |
 = |  ${VARIABLE=default} | $VARIABLE  |          ""           | $(VARIABLE="default") |
 ? |  ${VARIABLE?default} | $VARIABLE  |          ""           |       exit 127        |
 + |  ${VARIABLE+default} | "default"  |       "default"       |          ""           |
   +----------------------+------------+-----------------------+-----------------------+
:- | ${VARIABLE:-default} | $VARIABLE  |       "default"       |       "default"       |
:= | ${VARIABLE:=default} | $VARIABLE  | $(VARIABLE="default") | $(VARIABLE="default") |
:? | ${VARIABLE:?default} | $VARIABLE  |       exit 127        |       exit 127        |
:+ | ${VARIABLE:+default} | "default"  |          ""           |          ""           |
   +----------------------+------------+-----------------------+-----------------------+

Notez que chaque groupe (avec et sans les deux points précédents) a les mêmes cas set ​​et nset, de sorte que la seule chose qui diffère est la façon dont le vide les cas sont traités.

Avec les deux points précédents, les cas empty et nset ​​sont identiques, je les utiliserais donc dans la mesure du possible (c'est-à-dire, utilisez :=, et pas seulement = , car le cas vide est incohérent).

En-têtes:

  • set ​​signifie que VARIABLE n'est pas vide (VARIABLE="something")
  • vide signifie que VARIABLE est vide/nul (VARIABLE="")
  • nset ​​signifie que VARIABLE n'existe pas (unset VARIABLE)

Valeurs:

  • $VARIABLE signifie que le résultat est la valeur d'origine de la variable.
  • "default" signifie que le résultat est la chaîne de remplacement fournie.
  • "" signifie que le résultat est null (une chaîne vide).
  • exit 127 signifie que le script cesse de s'exécuter avec le code de sortie 127.
  • $(VARIABLE="default") signifie que le résultat est la valeur d'origine de la variable and la chaîne de remplacement fournie est affectée à la variable pour une utilisation ultérieure.
60
deizel

Sur une version moderne de Bash (4.2 ou ultérieure, je pense; je ne sais pas avec certitude), je voudrais essayer ceci:

if [ ! -v SOMEVARIABLE ] #note the lack of a $ sigil
then
    echo "Variable is unset"
Elif [ -z "$SOMEVARIABLE" ]
then
    echo "Variable is set to an empty string"
else
    echo "Variable is set to some string"
fi
31
Seamus Connor
if [ "$1" != "" ]; then
  echo \$1 is set
else
  echo \$1 is not set
fi

Bien que pour les arguments, il est normalement préférable de tester $ #, qui est le nombre d’arguments, à mon avis.

if [ $# -gt 0 ]; then
  echo \$1 is set
else
  echo \$1 is not set
fi
20
Paul Creasey

Vous voulez quitter s'il n'est pas défini

Cela a fonctionné pour moi. Je voulais que mon script se termine avec un message d'erreur si aucun paramètre n'était défini.

#!/usr/bin/env bash

set -o errexit

# Get the value and empty validation check all in one
VER="${1:?You must pass a version of the format 0.0.0 as the only argument}"

Cela retourne avec une erreur quand il est exécuté

peek@peek:~$ ./setver.sh
./setver.sh: line 13: 1: You must pass a version of the format 0.0.0 as the only argument

Vérifier seulement, pas de sortie - Vide et non défini sont non valides

Essayez cette option si vous voulez juste vérifier si la valeur set = VALID ou unset/empty = INVALID.

TSET="good val"
TEMPTY=""
unset TUNSET

if [ "${TSET:-}" ]; then echo "VALID"; else echo "INVALID";fi
# VALID
if [ "${TEMPTY:-}" ]; then echo "VALID"; else echo "INVALID";fi
# INVALID
if [ "${TUNSET:-}" ]; then echo "VALID"; else echo "INVALID";fi
# INVALID

Ou même de courts tests ;-)

[ "${TSET:-}"   ] && echo "VALID" || echo "INVALID"
[ "${TEMPTY:-}" ] && echo "VALID" || echo "INVALID"
[ "${TUNSET:-}" ] && echo "VALID" || echo "INVALID"

Vérifier seulement, pas de sortie - Seulement vide est INVALID

Et c'est la réponse à la question. Utilisez ceci si vous voulez juste vérifier si la valeur set/empty = VALID ou unset = INVALID.

NOTE, le "1" dans "..- 1}" est insignifiant, ça peut être n'importe quoi (comme x)

TSET="good val"
TEMPTY=""
unset TUNSET

if [ "${TSET+1}" ]; then echo "VALID"; else echo "INVALID";fi
# VALID
if [ "${TEMPTY+1}" ]; then echo "VALID"; else echo "INVALID";fi
# VALID
if [ "${TUNSET+1}" ]; then echo "VALID"; else echo "INVALID";fi
# INVALID

Tests courts

[ "${TSET+1}"   ] && echo "VALID" || echo "INVALID"
[ "${TEMPTY+1}" ] && echo "VALID" || echo "INVALID"
[ "${TUNSET+1}" ] && echo "VALID" || echo "INVALID"

Je dédie cette réponse à @ mklement0 (commentaires) qui m'a mis au défi de répondre correctement à la question.

Référence http://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html#tag_18_06_02

16
Jarrod Chesney

Pour vérifier si une variable est définie avec une valeur non vide, utilisez [ -n "$x" ], comme d'autres l'ont déjà indiqué.

La plupart du temps, il est judicieux de traiter une variable qui a une valeur vide de la même manière qu'une variable non définie. Mais vous pouvez distinguer les deux si vous devez: [ -n "${x+set}" ] ("${x+set}" se développe en set si x est défini et à la chaîne vide si x n'est pas défini. ).

Pour vérifier si un paramètre a été passé, testez $#, qui correspond au nombre de paramètres transmis à la fonction (ou au script, lorsqu'il ne fait pas partie d'une fonction) (voir réponse de Paul ) .

14
Gilles

Lisez la section "Extension de paramètres" de la page de manuel bash. L'expansion des paramètres ne fournit pas de test général pour une variable en cours de définition, mais vous pouvez effectuer plusieurs opérations sur un paramètre s'il n'est pas défini.

Par exemple:

function a {
    first_arg=${1-foo}
    # rest of the function
}

définira first_arg égal à $1 s'il est affecté, sinon il utilise la valeur "foo". Si a doit absolument prendre un seul paramètre et qu'il n'existe aucune bonne valeur par défaut, vous pouvez quitter avec un message d'erreur si aucun paramètre n'est donné:

function a {
    : ${1?a must take a single argument}
    # rest of the function
}

(Notez l'utilisation de : en tant que commande null, ce qui développe simplement les valeurs de ses arguments. Nous ne voulons rien faire avec $1 dans cet exemple, quitte si vous ne le définissez pas. )

14
chepner

En bash, vous pouvez utiliser -v à l'intérieur du [[ ]] intégré:

#! /bin/bash -u

if [[ ! -v SOMEVAR ]]; then
    SOMEVAR='hello'
fi

echo $SOMEVAR
13
AlejandroVD

Pour ceux qui cherchent à vérifier si non défini ou vide dans un script avec set -u :

_if [ -z "${var-}" ]; then
   echo "Must provide var environment variable. Exiting...."
   exit 1
fi
_

La vérification normale _[ -z "$var" ]_ échouera avec _var; unbound variable_ si _set -u_ mais _[ -z "${var-}" ]_ se développe pour vider la chaîne si var est non défini sans échec.

12
ecerulm

Remarque

Je donne une réponse fortement axée sur Bash à cause de la balise bash.

Réponse courte

Tant que vous ne traitez que des variables nommées dans Bash, cette fonction doit toujours vous indiquer si la variable a été définie, même s'il s'agit d'un tableau vide.

_is-variable-set() {
    declare -p $1 &>dev/null
}
_

Pourquoi ça marche

Dans Bash (au moins aussi loin que 3.0), si var est une variable déclarée/définie, alors _declare -p var_ génère une commande declare qui affecterait la variable var à son type et sa valeur actuels sont et renvoie le code d'état _0_ (succès). Si var n'est pas déclaré, alors _declare -p var_ renvoie un message d'erreur à stderr et renvoie le code d'état _1_. En utilisant _&>/dev/null_, redirige les sorties régulières stdout et stderr vers _/dev/null_, pour ne jamais être vues, et sans changer le code d'état. Ainsi, la fonction ne renvoie que le code d'état.

Pourquoi les autres méthodes échouent (parfois) dans Bash

  • _[ -n "$var" ]_: Ceci vérifie uniquement si _${var[0]}_ est non vide. (Dans Bash, _$var_ est identique à _${var[0]}_.)
  • _[ -n "${var+x}" ]_: Ceci vérifie uniquement si _${var[0]}_ est défini.
  • _[ "${#var[@]}" != 0 ]_: Ceci vérifie uniquement si au moins un index de _$var_ est défini.

Quand cette méthode échoue dans Bash

Ceci ne fonctionne que pour les variables nommées (y compris _$__) et non pour certaines variables spéciales (_$!_, _$@_, _$#_, _$$_, _$*_, _$?_, _$-_, _$0_, _$1_, _$2_, ..., et tout ce que j'ai peut-être oublié). Comme aucun de ceux-ci n'est un tableau, le style POSIX _[ -n "${var+x}" ]_ fonctionne pour toutes ces variables spéciales. Mais méfiez-vous de l'envelopper dans une fonction car de nombreuses variables spéciales changent les valeurs/l'existence lorsque des fonctions sont appelées.

Note de compatibilité shell

Si votre script contient des tableaux et que vous essayez de le rendre compatible avec autant de shells que possible, envisagez d'utiliser _typeset -p_ au lieu de _declare -p_. J'ai lu que ksh ne supportait que l'ancien, mais je n'ai pas pu tester cela. Je sais que Bash 3.0+ et Zsh 5.5.1 prennent en charge à la fois _typeset -p_ et _declare -p_, ne différant que par le fait que l’un est une alternative à l’autre. Mais je n'ai pas testé les différences au-delà de ces deux mots clés et je n'ai pas testé d'autres coques.

Si vous avez besoin que votre script soit compatible POSIX sh, vous ne pouvez pas utiliser de tableaux. Sans tableaux, _[ -n "{$var+x}" ]_ fonctionne.

Code de comparaison pour différentes méthodes dans Bash

Cette fonction désactive la variable var, evalsur le code transmis, exécute des tests pour déterminer si var est défini par le code evald et affiche enfin les codes d'état résultants pour les différents tests.

Je saute _test -v var_, _[ -v var ]_ et _[[ -v var ]]_ car ils donnent des résultats identiques à ceux du standard POSIX _[ -n "${var+x}" ]_ tout en nécessitant Bash 4.2+. Je saute également _typeset -p_ car il est identique à _declare -p_ dans les shells que j'ai testés (Bash 3.0 à 5.0 et Zsh 5.5.1).

_is-var-set-after() {
    # Set var by passed expression.
    unset var
    eval "$1"

    # Run the tests, in increasing order of accuracy.
    [ -n "$var" ] # (index 0 of) var is nonempty
    nonempty=$?
    [ -n "${var+x}" ] # (index 0 of) var is set, maybe empty
    plus=$?
    [ "${#var[@]}" != 0 ] # var has at least one index set, maybe empty
    count=$?
    declare -p var &>/dev/null # var has been declared (any type)
    declared=$?

    # Show test results.
    printf '%30s: %2s %2s %2s %2s\n' "$1" $nonempty $plus $count $declared
}
_

Code de cas de test

Notez que les résultats des tests peuvent être inattendus, car Bash traite les index non numériques du tableau comme "0" si la variable n'a pas été déclarée comme un tableau associatif. De plus, les tableaux associatifs ne sont valables que dans Bash 4.0+.

_# Header.
printf '%30s: %2s %2s %2s %2s\n' "test" '-n' '+x' '#@' '-p'
# First 5 tests: Equivalent to setting 'var=foo' because index 0 of an
# indexed array is also the nonindexed value, and non-numerical
# indices in an array not declared as associative are the same as
# index 0.
is-var-set-after "var=foo"                        #  0  0  0  0
is-var-set-after "var=(foo)"                      #  0  0  0  0
is-var-set-after "var=([0]=foo)"                  #  0  0  0  0
is-var-set-after "var=([x]=foo)"                  #  0  0  0  0
is-var-set-after "var=([y]=bar [x]=foo)"          #  0  0  0  0
# '[ -n "$var" ]' fails when var is empty.
is-var-set-after "var=''"                         #  1  0  0  0
is-var-set-after "var=([0]='')"                   #  1  0  0  0
# Indices other than 0 are not detected by '[ -n "$var" ]' or by
# '[ -n "${var+x}" ]'.
is-var-set-after "var=([1]='')"                   #  1  1  0  0
is-var-set-after "var=([1]=foo)"                  #  1  1  0  0
is-var-set-after "declare -A var; var=([x]=foo)"  #  1  1  0  0
# Empty arrays are only detected by 'declare -p'.
is-var-set-after "var=()"                         #  1  1  1  0
is-var-set-after "declare -a var"                 #  1  1  1  0
is-var-set-after "declare -A var"                 #  1  1  1  0
# If 'var' is unset, then it even fails the 'declare -p var' test.
is-var-set-after "unset var"                      #  1  1  1  1
_

Test de sortie

Les mnémoniques de test dans la ligne d'en-tête correspondent à _[ -n "$var" ]_, _[ -n "${var+x}" ]_, _[ "${#var[@]}" != 0 ]_ et _declare -p var_, respectivement.

_                         test: -n +x #@ -p
                      var=foo:  0  0  0  0
                    var=(foo):  0  0  0  0
                var=([0]=foo):  0  0  0  0
                var=([x]=foo):  0  0  0  0
        var=([y]=bar [x]=foo):  0  0  0  0
                       var='':  1  0  0  0
                 var=([0]=''):  1  0  0  0
                 var=([1]=''):  1  1  0  0
                var=([1]=foo):  1  1  0  0
declare -A var; var=([x]=foo):  1  1  0  0
                       var=():  1  1  1  0
               declare -a var:  1  1  1  0
               declare -A var:  1  1  1  0
                    unset var:  1  1  1  1
_

Sommaire

  • declare -p var &>/dev/null est (100%?) Fiable pour tester les variables nommées dans Bash depuis au moins 3,0.
  • [ -n "${var+x}" ] est fiable dans les situations conformes à POSIX, mais ne peut pas gérer les tableaux.
  • Il existe d'autres tests pour vérifier si une variable est non vide et pour rechercher les variables déclarées dans d'autres shells. Mais ces tests ne conviennent ni aux scripts Bash ni aux scripts POSIX.
11
Mark Haferkamp

Utiliser [[ -z "$var" ]] est le moyen le plus simple de savoir si une variable a été définie ou non, mais l'option -z ne fait pas la distinction entre une variable non définie et une variable définie sur une chaîne vide:

$ set=''
$ [[ -z "$set" ]] && echo "Set" || echo "Unset" 
Unset
$ [[ -z "$unset" ]] && echo "Set" || echo "Unset"
Unset

Il est préférable de le vérifier en fonction du type de variable: variable env, paramètre ou variable régulière.

Pour une variable env:

[[ $(env | grep "varname=" | wc -l) -eq 1 ]] && echo "Set" || echo "Unset"

Pour un paramètre (par exemple, pour vérifier l'existence du paramètre $5]):

[[ $# -ge 5 ]] && echo "Set" || echo "Unset"

Pour une variable régulière (en utilisant une fonction auxiliaire, pour le faire de manière élégante):

function declare_var {
   declare -p "$1" &> /dev/null
}
declare_var "var_name" && echo "Set" || echo "Unset"

Remarques:

  • $#: vous donne le nombre de paramètres de position.
  • declare -p: vous donne la définition de la variable passée en paramètre. S'il existe, renvoie 0, sinon 1, et affiche un message d'erreur.
  • &> /dev/null: supprime la sortie de declare -p sans affecter son code de retour.
5
Peregring-lk

Les réponses ci-dessus ne fonctionnent pas lorsque l'option Bash set -u est activée. En outre, ils ne sont pas dynamiques. Par exemple, comment tester si la variable portant le nom "dummy" est définie? Essaye ça:

is_var_defined()
{
    if [ $# -ne 1 ]
    then
        echo "Expected exactly one argument: variable name as string, e.g., 'my_var'"
        exit 1
    fi
    # Tricky.  Since Bash option 'set -u' may be enabled, we cannot directly test if a variable
    # is defined with this construct: [ ! -z "$var" ].  Instead, we must use default value
    # substitution with this construct: [ ! -z "${var:-}" ].  Normally, a default value follows the
    # operator ':-', but here we leave it blank for empty (null) string.  Finally, we need to
    # substitute the text from $1 as 'var'.  This is not allowed directly in Bash with this
    # construct: [ ! -z "${$1:-}" ].  We need to use indirection with eval operator.
    # Example: $1="var"
    # Expansion for eval operator: "[ ! -z \${$1:-} ]" -> "[ ! -z \${var:-} ]"
    # Code  execute: [ ! -z ${var:-} ]
    eval "[ ! -z \${$1:-} ]"
    return $?  # Pedantic.
}

Connexes: Dans Bash, comment puis-je tester si une variable est définie en mode "-u"

4
kevinarpe

Tu peux faire:

function a {
        if [ ! -z "$1" ]; then
                echo '$1 is set'
        fi
}
4
codaddict

Ma manière préférée est la suivante:

$var=10
$if ! ${var+false};then echo "is set";else echo "NOT set";fi
is set
$unset var
$if ! ${var+false};then echo "is set";else echo "NOT set";fi
NOT set

Donc, si une variable est définie, elle devient "une négation de la false" résultante (ce qui sera true = "est défini").

Et, s'il n'est pas défini, il deviendra "une négation de la résultante true" (car le résultat vide est évalué à true) (ainsi finira comme étant false = "NON défini ").

2
Aquarius Power

Dans un shell, vous pouvez utiliser l'opérateur -z, qui a la valeur True si la longueur de la chaîne est égale à zéro.

Une ligne simple pour définir le paramètre par défaut MY_VAR s'il n'est pas défini. Sinon, vous pouvez également afficher le message suivant:

[[ -z "$MY_VAR" ]] && MY_VAR="default"
[[ -z "$MY_VAR" ]] && MY_VAR="default" || echo "Variable already set."
1
kenorb

C'est ce que j'utilise tous les jours:

#
# Check if a variable is set
#   param1  name of the variable
#
function is_set()
{
    [[ -n "${1}" ]] && test -n "$(eval "echo "\${${1}+x}"")"
}

Cela fonctionne bien sous Linux et Solaris jusqu'à bash 3.0.

bash-3.00$ myvar="TEST"
bash-3.00$ is_set myvar ; echo $?
0
bash-3.00$ mavar=""
bash-3.00$ is_set myvar ; echo $?
0
bash-3.00$ unset myvar
bash-3.00$ is_set myvar ; echo $?
1
0
fr00tyl00p

Après avoir parcouru toutes les réponses, cela fonctionne également:

if [[ -z $SOME_VAR ]]; then read -p "Enter a value for SOME_VAR: " SOME_VAR; fi
echo "SOME_VAR=$SOME_VAR"

si vous ne mettez pas SOME_VAR à la place de ce que j'ai $SOME_VAR, il le définira à une valeur vide; $ est nécessaire pour que cela fonctionne.

0
Hatem Jaber

J'utilise toujours celui-ci, basé sur le fait qu'il semble facile d'être compris par quiconque voit le code pour la toute première fois:

if [ "$variable" = "" ]
    then
    echo "Variable X is empty"
fi

Et, si vous voulez vérifier si pas vide;

if [ ! "$variable" = "" ]
    then
    echo "Variable X is not empty"
fi

C'est ça.

0
mijnnaam

J'ai trouvé un (beaucoup) meilleur code pour le faire si vous voulez vérifier quoi que ce soit dans $@.

 si [[$ 1 = ""]] 
, alors 
 echo '$ 1 est vide' 
 sinon 
 echo '$ 1 est rempli' 
Fi

Pourquoi tout ça? Tout ce qui se trouve dans $@ existe dans Bash, mais il est vide par défaut. test -z et test -n ne peuvent donc pas vous aider.

Mise à jour: Vous pouvez également compter le nombre de caractères dans un paramètre.

 si [$ {# 1} = 0] 
, alors 
 echo '$ 1 est vide' 
 sinon 
 echo '$ 1 est rempli' 
Fi
0
Zlatan
if [[ ${!xx[@]} ]] ; then echo xx is defined; fi
0
Graham

J'aime les fonctions auxiliaires pour masquer les détails bruts de bash. Dans ce cas, cela ajoute encore plus de cruauté (cachée):

# The first ! negates the result (can't use -n to achieve this)
# the second ! expands the content of varname (can't do ${$varname})
function IsDeclared_Tricky
{
  local varname="$1"
  ! [ -z ${!varname+x} ]
}

Parce que j’avais d’abord eu des bugs dans cette implémentation (inspiré des réponses de Jens et Lionel), j’ai trouvé une solution différente:

# Ask for the properties of the variable - fails if not declared
function IsDeclared()
{
  declare -p $1 &>/dev/null
}

Je trouve cela plus simple, plus simple et plus facile à comprendre/à mémoriser. Le scénario de test montre qu'il est équivalent:

function main()
{
  declare -i xyz
  local foo
  local bar=
  local baz=''

  IsDeclared_Tricky xyz; echo "IsDeclared_Tricky xyz: $?"
  IsDeclared_Tricky foo; echo "IsDeclared_Tricky foo: $?"
  IsDeclared_Tricky bar; echo "IsDeclared_Tricky bar: $?"
  IsDeclared_Tricky baz; echo "IsDeclared_Tricky baz: $?"

  IsDeclared xyz; echo "IsDeclared xyz: $?"
  IsDeclared foo; echo "IsDeclared foo: $?"
  IsDeclared bar; echo "IsDeclared bar: $?"
  IsDeclared baz; echo "IsDeclared baz: $?"
}

main

Le scénario de test montre également que local var fait PAS déclare var (sauf si suivi de '='). Pendant un certain temps, j'ai cru déclarer les variables de cette façon, juste pour découvrir maintenant que je ne faisais qu'exprimer mon intention ... C'est un non-op, je suppose.

IsDeclared_Tricky xyz: 1
IsDeclared_Tricky foo: 1
IsDeclared_Tricky bar: 0
IsDeclared_Tricky baz: 0
IsDéclared xyz: 1
Est déclaré foo: 1
Barre déclarée: 0
IsDéclared baz: 0

BONUS: usecase

J'utilise principalement ce test pour donner (et renvoyer) les paramètres aux fonctions d'une manière un peu "élégante" et sûre (ressemblant presque à une interface ...) :

#auxiliary functions
function die()
{
  echo "Error: $1"; exit 1
}

function assertVariableDeclared()
{
  IsDeclared "$1" || die "variable not declared: $1"
}

function expectVariables()
{
  while (( $# > 0 )); do
    assertVariableDeclared $1; shift
  done
}

# actual example
function exampleFunction()
{
  expectVariables inputStr outputStr
  outputStr="$inputStr world!"
}

function bonus()
{
  local inputStr='Hello'
  local outputStr= # remove this to trigger error
  exampleFunction
  echo $outputStr
}

bonus

Si appelé avec tout requiert des variables déclarées:

Bonjour le monde!

autre:

Erreur: variable non déclarée: outputStr

0
Daniel S
if [[ ${1:+isset} ]]
then echo "It was set and not null." >&2
else echo "It was not set or it was null." >&2
fi

if [[ ${1+isset} ]]
then echo "It was set but might be null." >&2
else echo "It was was not set." >&2
fi
0
solidsnack
[[ $foo ]]

Ou

(( ${#foo} ))

Ou

let ${#foo}

Ou

declare -p foo
0
Steven Penny