web-dev-qa-db-fra.com

Shell Script - Supprimer le premier et le dernier guillemet (") d'une variable

Ci-dessous l'extrait de script Shell issu d'un script plus volumineux. Il supprime les guillemets de la chaîne qui est détenue par une variable. Je le fais en utilisant sed, est-ce efficace? Si non, quel est le moyen efficace?

#!/bin/sh

opt="\"html\\test\\\""
temp=`echo $opt | sed 's/.\(.*\)/\1/' | sed 's/\(.*\)./\1/'`
echo $temp
175
user1263746

Plus simple et plus efficace, utilisez la fonction de suppression du préfixe/suffixe natif de Shell:

temp="${opt%\"}"
temp="${temp#\"}"
echo "$temp"

$ {opt%\"} supprimera le suffixe" (avec une barre oblique inverse pour empêcher l'interprétation du shell)

$ {temp #\"} supprimera le préfixe" (avec une barre oblique inverse pour empêcher l'interprétation du shell)

Un autre avantage est que les guillemets environnants ne seront supprimés que s'il y en a.

En passant, votre solution supprime toujours le premier et le dernier caractère, quels qu’ils soient (bien sûr, vous connaissez vos données, mais il est toujours préférable d’être sûr de ce que vous supprimez).

Utilisation de sed:

echo "$opt" | sed -e 's/^"//' -e 's/"$//'

(version améliorée, comme indiqué par jfgagne, se débarrasser de l'écho)

sed -e 's/^"//' -e 's/"$//' <<<"$opt"

Donc, cela remplace le fait de conduire "avec rien et de tirer" avec rien aussi. Dans la même invocation (inutile de rediffuser et de démarrer un autre sed, utiliser -e vous permet de traiter plusieurs textes).

205
huelbois

Utilisez tr pour supprimer ":

 echo "$opt" | tr -d '"'

Remarque: Cela supprime toutes les doubles guillemets, pas seulement les caractères de début et de fin.

221
wieczorek1990

Cela supprimera toutes les guillemets doubles.

echo "${opt//\"}"
30
Steven Penny

Il existe un moyen simple d’utiliser xargs :

> echo '"quoted"' | xargs
quoted

xargs utilise echo comme commande par défaut si aucune commande n'est fournie et supprime les guillemets de l'entrée, voir p. ex. ici

19
user1587520

Vous pouvez le faire en un seul appel à sed:

$ echo "\"html\\test\\\"" | sed 's/^"\(.*\)"$/\1/'
html\test\
18

Le plus court chemin - essayez:

echo $opt | sed "s/\"//g"

En fait, il supprime tous les "(guillemets) de opt (y aura-t-il vraiment plus de guillemets autres qu'au début et à la fin? Alors, c'est en fait la même chose, et beaucoup plus brève; - ))

15
Dr.Kameleon

Mettre à jour

Réponse simple et élégante de https://stackoverflow.com/a/24358387/116174 :

BAR=$(eval echo $BAR) supprime les guillemets de BAR.

=============================================== ===========

Basé sur la réponse de hueybois, je suis arrivé à cette fonction après de nombreux essais et erreurs:

function stripStartAndEndQuotes {
    cmd="temp=\${$1%\\\"}"
    eval echo $cmd
    temp="${temp#\"}"
    eval echo "$1=$temp"
}

Si vous ne voulez rien imprimer, vous pouvez diriger les évaluations vers /dev/null 2>&1.

Usage:

$ BAR="FOO BAR"
$ echo BAR
"FOO BAR"
$ stripStartAndEndQuotes "BAR"
$ echo BAR
FOO BAR
8
Jonathan Lin

N'est-ce pas la manière la plus discrète sans utiliser sed?

x='"fish"'
printf "   quotes: %s\nno quotes:  %s\n" "$x" "${x//\"/}"

OR

echo $x
echo ${x//\"/}

sortie:

   quotes: "fish"
no quotes:  fish

Je l'ai eu de Source

6
nimig18

La solution la plus simple:

$ s='"abc"'
$ echo $s
"abc"
$ echo "${s:1:-1}"
abc
3
Hiro.Protagonist

Ma version

strip_quotes() {
    while [[ $# -gt 0 ]]; do
        local value=${!1}
        local len=${#value}
        [[ ${value:0:1} == \" && ${value:$len-1:1} == \" ]] && declare -g $1="${value:1:$len-2}"
        shift
    done
}

La fonction accepte les noms de variable et supprime les guillemets à la place. Il ne supprime qu'une paire de citations principales et finales. Il ne vérifie pas si le guillemet de fin est échappé (précédé de \ qui n'est pas lui-même échappé).

D'après mon expérience, les utilitaires de chaîne d'usage général tels que celui-ci (j'en ai une bibliothèque) sont plus efficaces pour manipuler les chaînes directement, en n'utilisant pas de correspondance de modèle et en particulier en ne créant pas de sous-shell, ni en appelant des outils externes tels que sed, awk ou grep.

var1="\"test \\ \" end \""
var2=test
var3=\"test
var4=test\"
echo before:
for i in var{1,2,3,4}; do
    echo $i="${!i}"
done
strip_quotes var{1,2,3,4}
echo
echo after:
for i in var{1,2,3,4}; do
    echo $i="${!i}"
done
1
Gene Pavlovsky