2008-10-08 20 views

Répondre

11

bash

Shortest fix:

if [[ "$var1" = "mtu "* ]] 

Bash de [[ ]] ne sont pas remplacées glob, contrairement [ ] (qui doit, pour des raisons historiques).


bash --posix

Oh, j'ai posté trop vite. Bourne shell, pas Bash ...

if [ "${var1:0:4}" == "mtu " ] 

${var1:0:4} signifie que les quatre premiers caractères de $var1.


/bin/sh

Ah, désolé. L'émulation POSIX de Bash ne va pas assez loin; un véritable shell Bourne original n'a pas ${var1:0:4}. Vous aurez besoin de quelque chose comme la solution de mstrobl.

if [ "$(echo "$var1" | cut -c0-4)" == "mtu " ] 
+0

'$ {var1: 0: 4}' - d'où avez-vous obtenu cette syntaxe? Ce n'est certainement pas POSIX. –

+1

Ma version de cut dit que les positions sont numérotées à partir de 1. '' cut -c 1-4'' ou '' cut -c -4'' renvoie la valeur correcte ici. – jotr

18

Utilisez les outils Unix. Le programme cut raccourcira heureusement une chaîne.

if [ "$(echo $var1 | cut -c 4)" = "mtu " ]; 

... devrait faire ce que vous voulez.

+1

oui, mais un peu lourd –

+0

Je crois que puisque vous comparez deux chaînes ici, il devrait être "=" ou "==", pas "-eq". – William

+0

'' cut -c 4'' coupe le quatrième caractère: '' cut -c -4'' coupe les quatre premiers caractères. – jotr

0

Ou, comme un exemple de l'opérateur = ~:

if [[ "$var1" =~ "mtu *" ]] 
+0

Quel genre de coquille est-ce? – ADEpt

+0

Bash 3.1 et supérieur a [[a = ~. *]]. Mais * à l'intérieur des guillemets est faux pour 3.2 et plus sans shopt -s compat31. – ephemient

+0

Ce n'est pas POSIX. –

6

Vous pouvez appeler expr pour correspondre à des chaînes contre des expressions régulières à partir de scripts shell Bourne. Le semble ci-dessous pour travailler:

#!/bin/sh 

var1="mtu eth0" 

if [ "`expr \"$var1\" : \"mtu .*\"`" != "0" ];then 
    echo "match" 
fi 
3

Je ferais ce qui suit:

# Removes anything but first word from "var1" 
if [ "${var1%% *}" = "mtu" ] ; then ... fi 

Ou:

# Tries to remove the first word if it is "mtu", checks if we removed anything 
if [ "${var1#mtu }" != "$var1" ] ; then ... fi 
1

J'aime utiliser la déclaration de cas pour comparer des chaînes.

Un exemple trivial est

case "$input" 
in 
    "$variable1") echo "matched the first value" 
    ;; 
    "$variable2") echo "matched the second value" 
    ;; 
    *[a-z]*) echo "input has letters" 
    ;; 
    '')  echo "input is null!" 
    ;; 
    *[0-9]*) echo "matched numbers (but I don't have letters, otherwise the letter test would have been hit first!)" 
    ;; 
    *) echo "Some wacky stuff in the input!" 
esac 

J'ai fait des choses folles comme

case "$(cat file)" 
in 
    "$(cat other_file)") echo "file and other_file are the same" 
     ;; 
    *) echo "file and other_file are different" 
esac 

Et cela fonctionne aussi, avec certaines limites, telles que les fichiers ne peuvent pas être plus d'un couple mégaoctets et le shell ne voit tout simplement pas de valeurs nulles, donc si un fichier est plein de zéros et l'autre n'en a pas, (et aucun n'a d'autre chose), ce test ne verra aucune différence entre les deux. Je n'utilise pas la comparaison de fichiers comme un exemple sérieux, seulement un exemple de la façon dont l'instruction case est capable de faire une correspondance de chaîne beaucoup plus flexible que celle disponible avec test ou expr ou d'autres expressions shell similaires.

1

Dans Bourne shell, si je veux vérifier si une chaîne contient une autre chaîne:

if [ `echo ${String} | grep -c ${Substr} ` -eq 1 ] ; then 

Entourez echo ${String} | grep -c ${Substr} avec deux ` accents graves:

Pour vérifier si la sous-chaîne est au début ou à la fin:

if [ `echo ${String} | grep -c "^${Substr}"` -eq 1 ] ; then 
... 
if [ `echo ${String} | grep -c "${Substr}$"` -eq 1 ] ; then