it-swarm.com.de

Entfernen Sie ein festes Präfix / Suffix aus einer Zeichenfolge in Bash

In meinem Skript bash habe ich einen String und sein Präfix/Suffix. Ich muss das Präfix/Suffix aus der ursprünglichen Zeichenfolge entfernen.

Angenommen, ich habe die folgenden Werte:

string="hello-world"
prefix="hell"
suffix="ld"

Wie komme ich zu folgendem Ergebnis?

result="o-wor"
405
$ foo=${string#"$prefix"}
$ foo=${foo%"$suffix"}
$ echo "${foo}"
o-wor
593

Sed verwenden:

$ echo "$string" | sed -e "s/^$prefix//" -e "s/$suffix$//"
o-wor

Innerhalb des Befehls sed stimmt das Zeichen ^ mit dem Text überein, der mit $prefix beginnt, und das abschließende Zeichen $ stimmt mit dem Text überein, der mit $suffix endet.

Adrian Frühwirth macht einige gute Punkte in den Kommentaren unten, aber sed für diesen Zweck kann sehr nützlich sein. Die Tatsache, dass der Inhalt von $ prefix und $ suffix von sed interpretiert wird, kann entweder gut OR schlecht sein. Solange Sie darauf achten, sollten Sie in Ordnung sein. Das Schöne ist, Sie können so etwas tun:

$ prefix='^.*ll'
$ suffix='ld$'
$ echo "$string" | sed -e "s/^$prefix//" -e "s/$suffix$//"
o-wor

das ist vielleicht das, was Sie wollen, und es ist schicker und leistungsfähiger als die Bash-Variablensubstitution. Wenn Sie sich daran erinnern, dass mit großer Kraft große Verantwortung einhergeht (wie Spiderman sagt), sollte es Ihnen gut gehen.

Eine kurze Einführung in sed finden Sie unter http://evc-cit.info/cit052/sed_tutorial.html

Ein Hinweis zur Shell und zur Verwendung von Strings:

Für das angegebene Beispiel würde auch Folgendes funktionieren:

$ echo $string | sed -e s/^$prefix// -e s/$suffix$//

... aber nur weil:

  1. echo ist es egal, wie viele Zeichenfolgen sich in der Argumentliste befinden
  2. In $ prefix und $ suffix sind keine Leerzeichen enthalten

Im Allgemeinen empfiehlt es sich, eine Zeichenfolge in der Befehlszeile in Anführungszeichen zu setzen, da sie dem Befehl auch dann als einzelnes Argument angezeigt wird, wenn sie Leerzeichen enthält. Wir zitieren $ prefix und $ suffix aus demselben Grund: Jeder Editierbefehl an sed wird als ein String übergeben. Wir verwenden doppelte Anführungszeichen, weil sie eine variable Interpolation ermöglichen. Hätten wir einfache Anführungszeichen verwendet, hätte der sed-Befehl ein wörtliches $prefix und $suffix erhalten, was sicherlich nicht das ist, was wir wollten.

Beachten Sie auch, dass ich beim Setzen der Variablen prefix und suffix einfache Anführungszeichen verwende. Wir wollen sicher nicht, dass irgendetwas in den Strings interpretiert wird, also zitieren wir sie einfach, damit keine Interpolation stattfindet. Auch in diesem Beispiel ist es möglicherweise nicht erforderlich, aber es ist eine sehr gute Angewohnheit, sich darauf einzulassen.

76
Chris Kolodin

Kennen Sie die Länge Ihres Präfix und Suffix? In deinem Fall:

result=$(echo $string | cut -c5- | rev | cut -c3- | rev)

Oder allgemeiner:

result=$(echo $string | cut -c$((${#prefix}+1))- | rev | cut -c$((${#suffix}+1))- | rev)

Aber die Lösung von Adrian Frühwirth ist viel cooler! Das wusste ich nicht!

15

Ich benutze grep zum Entfernen von Präfixen aus Pfaden (die von sed nicht gut behandelt werden):

echo "$input" | grep -oP "^$prefix\K.*"

\K entfernt alle Zeichen davor aus der Übereinstimmung.

14
$ string="hello-world"
$ prefix="hell"
$ suffix="ld"

$ #remove "hell" from "hello-world" if "hell" is found at the beginning.
$ prefix_removed_string=${string/#$prefix}

$ #remove "ld" from "o-world" if "ld" is found at the end.
$ suffix_removed_String=${prefix_removed_string/%$suffix}
$ echo $suffix_removed_String
o-wor

Anmerkungen:

# $ Präfix: Das Hinzufügen von # stellt sicher, dass der Teilstring "hell" nur dann entfernt wird, wenn er am Anfang gefunden wird. % $ Suffix: Durch Hinzufügen von% wird sichergestellt, dass die Teilzeichenfolge "ld" nur entfernt wird, wenn sie am Ende gefunden wird.

Ohne diese werden die Teilzeichenfolgen "hell" und "ld" überall entfernt, auch wenn sie in der Mitte gefunden werden.

7
Vijay Vat

Kleine und universelle Lösung:

expr "$string" : "$prefix\(.*\)$suffix"
6
Tosi Do

Verwenden des Operators =~ :

_$ string="hello-world"
$ prefix="hell"
$ suffix="ld"
$ [[ "$string" =~ ^$prefix(.*)$suffix$ ]] && echo "${BASH_REMATCH[1]}"
o-wor
_

@Adrian Frühwirth Antwort verwenden:

function strip {
    local STRING=${1#$"$2"}
    echo ${STRING%$"$2"}
}

benutze es so

HELLO=":hello:"
HELLO=$(strip "$HELLO" ":")
echo $HELLO # hello
5
math2001