Como usar operadores de comparação no bash? [duplicar]

Esta pergunta já tem respostas aqui :

Comentários

Resposta

Esses operadores são usados em, por exemplo, (( ... )) e $(( ... )) ( avaliação aritmética e expansão aritmética respectivamente):

if (( arg1 >= num1 )) && (( arg2 <= num2 )); then ... fi 

E também com let. O seguinte é equivalente ao acima:

if let "arg1 >= num1" && let "arg2 <= num2"; then ... fi 

Veja a seção chamada “AVALIAÇÃO ARITMÉTICA” no manual do Bash.

Resposta

Em bash especificamente:

  • ((arg1 >= num1)) (herdado de ksh) faz comparação aritmética. arg1 e num1 aqui se referem às variáveis de shell de mesmo nome. Cada variável é interpretada como uma expansão aritmética e o resultado é substituído. Aqui, se $arg1 for 010 e $num1 for 4+5, o resultado será falso (o comando ((...)) retornará com um status de saída diferente de zero), porque 010 é octal para 8 e 4+5 é 9.
  • (($arg1 >= $num1)): o mesmo que acima, exceto que $arg1 e $num1 são expandidos antes que toda a expressão aritmética seja avaliada. Se $arg1 era (2 e $num1 era 2), o comando anterior teria falhado porque (2 e 2) não são expressões válidas por si mesmas. Mas aqui teria sucesso porque (2 >= 2) seria a expressão aritmética sendo avaliada. Geralmente, em expressões aritméticas, é “melhor deixar o $ de fora. Compare, por exemplo, a=2+2; echo "$((3 * $a))" com a=2+2; echo "$((3 * a))".
  • let "..." (também de ksh). O mesmo que ((...)) exceto que “s analisado como um comando normal, é menos legível, é pouco portátil e você precisa prestar mais atenção nas citações.
  • [ "$arg1" -ge "$num1" ]. Isso é padrão e portátil. Apenas constantes decimais são suportadas. [ 010 -ge 9 ] é o mesmo que [ 10 -ge 9 ].
  • [[ $arg1 -ge $num1 ]]. Também do ksh, mas com grandes diferenças. Desta vez, $arg1 e $num1 são considerados como expressões aritméticas e não apenas constantes decimais. [[ 010 -ge 9 ]] retorna falso novamente.
  • [[ $arg1 < $num1 ]]. Comparação de strings. Isso usa strcoll() para comparar strings, então usando o algoritmo de classificação no local. Observe que enquanto < e > use o algoritmo de classificação, = / == faça a comparação byte a byte, então pode haver pares de strings para os quais tudo de <, > e = / == retorna falso. <= e >= não são suportados.
  • [ "$arg1" "<" "$num1" ]. Fora do padrão. O mesmo que acima, mas usando o comando [. < precisa ser citado para “não ser tomado como um operador de redirecionamento.
  • expr " $arg1" "<=" " $num1" > /dev/null (observe o espaços para forçar a comparação lexical e evitar problemas com strings parecidas com expr operadores) ou awk "BEGIN{exit(!(""ARGV[1] <= ""ARGV[2]))}" "$arg1" "$num1" são os comandos padrão para fazer comparação de strings usando strcoll().

Deixe uma resposta

O seu endereço de email não será publicado. Campos obrigatórios marcados com *