+1 Dies kann leicht erweitert werden, um beispielsweise ascii hexBytes umzukehren .
Kunstloser Lärm
Ich habe eine verbesserte Antwort hinzugefügt , da meine Bearbeitung nicht akzeptiert wurde (einschließlich einer POSIX-Lösung).
172
Ich weiß, dass Sie "ohne Tools von Drittanbietern" gesagt haben, aber manchmal ist ein Tool einfach zu offensichtlich das richtige und es ist standardmäßig auf den meisten Linux-Systemen installiert:
Aber nicht mit eingebetteten Distributionen wie OpenWRT: - /
bk138
1
Oder rev <<< 12345in Bash, Zsh und Ksh. (Nicht Dash noch Csh.)
Loxaxs
1
Ich höre dich, aber versuche es echo '\xff' |rev. Ich habe nie gesagt, dass echo -edas funktionieren würde, deshalb scheint es ein bisschen hart zu sein, mich über die Kohlen zu harken, wenn es nicht so ist.
MadHatter
Dies funktioniert nicht, wenn die Zeichenfolge eine neue Zeile enthält. revwirkt in jeder Zeile unabhängig und scheint keine Befehlszeilenoptionen zu haben, die dies ändern. Wie das Beispiel von @ Equidamoid zeigt (was übrigens nichts damit zu tun hat echo -e), wird außerdem davon ausgegangen , dass es sich bei der Zeichenfolge um eine ordnungsgemäß codierte Zeichenfolge handelt . Wenn Sie etwas um Bytes umkehren müssen (z. B. wenn Sie nicht mit Binärdaten anstelle von tatsächlichem Text arbeiten), funktioniert diese Lösung nicht. [Hinweis: Um die Formatierung zu korrigieren, habe ich diesen Kommentar gelöscht und erneut veröffentlicht. Entschuldigung für mögliche Phantombenachrichtigungen.]
greatBigDot
12
rev | tail -r(BSD) oder rev | tac(GNU) kehren auch Linien um:
Wenn Sie sowieso auf awk angewiesen sind, warum nicht einfach einmal und nicht in einer Schleife ausführen? awk '{for(i=length($0);i;i--)printf "%s",substr($0,i,1); print ""}'oder sogarawk '{for(i=length($0);i;i--)x=x substr($0,i,1); print x}'
Ghoti
6
Dies kehrt die Zeichenfolge "an Ort und Stelle" um:
a=12345
len=${#a}for ((i=1;i<len;i++)); do a=$a${a: -i*2:1}; done; a=${a:len-1}echo$a
oder die dritte Zeile könnte sein:
for ((i=0;i<len;i++)); do a=${a:i*2:1}$a; done; a=${a:0:len}
oder
for ((i=1;i<len;i++)); do a=${a:0:len-i-1}${a: -i:i+1}${a:len-i-1:1}; done
Für diejenigen ohne rev (empfohlen) gibt es die folgende einfache awk- Lösung, die Felder in der Nullzeichenfolge aufteilt (jedes Zeichen ist ein separates Feld) und umgekehrt druckt:
Der obige awk- Code ist POSIX-kompatibel. Da eine kompatible awk- Implementierung garantiert auf jedem POSIX-kompatiblen Betriebssystem vorhanden ist, sollte die Lösung daher nicht als "Drittanbieter" betrachtet werden. Dieser Code ist wahrscheinlich prägnanter und verständlicher als eine reine POSIX sh (oder bash ) -Lösung.
(; Ich weiß nicht, ob Sie die Nullzeichenfolge für -F als regulären Ausdruck betrachten ...;)
Niemand scheint eine sedLösung veröffentlicht zu haben , daher hier eine, die in Nicht-GNU-Sed funktioniert (daher würde ich sie nicht als "Drittanbieter" betrachten). Es werden zwar einzelne Zeichen mit dem regulären Ausdruck erfasst ., dies ist jedoch der einzige reguläre Ausdruck.
In zwei Schritten:
$ echo 123456 | sed $'s/./&\\\n/g' | sed -ne $'x;H;${x;s/\\n//g;p;}'
654321
Dies verwendet die Ersetzung des Bash-Formats, um Zeilenumbrüche in die Skripte aufzunehmen (da die Frage markiert ist Bash). Es funktioniert, indem zuerst die Eingabezeichenfolge in eine Zeile pro Zeichen getrennt wird und dann jedes Zeichen am Anfang des Haltepuffers eingefügt wird.
x vertauscht den Haltebereich und den Musterbereich und
H H hängt den (aktuellen) Musterraum an den Haltebereich an.
Also platzieren wir dieses Zeichen für jedes Zeichen in den Haltebereich und hängen dann den alten Haltebereich an ihn an, wodurch die Eingabe umgekehrt wird. Der letzte Befehl entfernt die Zeilenumbrüche, um die ursprüngliche Zeichenfolge zu rekonstruieren.
Dies sollte für jede einzelne Zeichenfolge funktionieren, verkettet jedoch mehrzeilige Eingaben zu einer einzelnen Ausgabezeichenfolge.
Antworten:
Einfach:
var="12345" copy=${var} len=${#copy} for((i=$len-1;i>=0;i--)); do rev="$rev${copy:$i:1}"; done echo "var: $var, rev: $rev"
Ausgabe:
quelle
ascii hex
Bytes umzukehren .Ich weiß, dass Sie "ohne Tools von Drittanbietern" gesagt haben, aber manchmal ist ein Tool einfach zu offensichtlich das richtige und es ist standardmäßig auf den meisten Linux-Systemen installiert:
[madhatta@risby tmp]$ echo 12345|rev 54321
quelle
rev <<< 12345
in Bash, Zsh und Ksh. (Nicht Dash noch Csh.)echo '\xff' |rev
. Ich habe nie gesagt, dassecho -e
das funktionieren würde, deshalb scheint es ein bisschen hart zu sein, mich über die Kohlen zu harken, wenn es nicht so ist.rev
wirkt in jeder Zeile unabhängig und scheint keine Befehlszeilenoptionen zu haben, die dies ändern. Wie das Beispiel von @ Equidamoid zeigt (was übrigens nichts damit zu tun hatecho -e
), wird außerdem davon ausgegangen , dass es sich bei der Zeichenfolge um eine ordnungsgemäß codierte Zeichenfolge handelt . Wenn Sie etwas um Bytes umkehren müssen (z. B. wenn Sie nicht mit Binärdaten anstelle von tatsächlichem Text arbeiten), funktioniert diese Lösung nicht. [Hinweis: Um die Formatierung zu korrigieren, habe ich diesen Kommentar gelöscht und erneut veröffentlicht. Entschuldigung für mögliche Phantombenachrichtigungen.]rev | tail -r
(BSD) oderrev | tac
(GNU) kehren auch Linien um:$ rev <<< $'12\n34' | tail -r 43 21 $ rev <<< $'12\n34' | gtac 43 21
Wenn LC_CTYPE C ist, kehrt rev die Bytes der Multibyte-Zeichen um:
$ LC_CTYPE=C rev <<< あの ��め� $ export LC_ALL=C; LC_ALL=en_US.UTF-8 rev <<< あの のあ
quelle
tac
. Beachten Sie, dasstac
die Übergabe eines anderen Trennzeichens als die\n
Verwendung der-s
Option unterstützt wird.Angenommen, eine Variable 'var' hat den Wert '123'.
var="123"
Kehren Sie den String um und speichern Sie ihn in einer neuen Variablen 'rav':
rav=$(echo $var | rev)
Sie werden sehen, dass 'rav' mit echo den Wert '321' hat.
echo $rav
quelle
Eine Bash-Lösung, die sich gegenüber der @ osdyng-Antwort verbessert (meine Bearbeitung wurde nicht akzeptiert):
var="12345" rev="" for(( i=0 ; i<${#var} ; i++ )); do rev="${var:i:1}$rev"; done echo "var: $var, rev: $rev"
Oder eine noch einfachere (Bash-) Schleife:
var=$1 len="${#var}" i=0 rev="" while (( i<len )); do rev="${var:i++:1}$rev"; done echo "var: $var, rev: $rev"
Eine POSIX-Lösung:
var="12345" rev="" i=1 while [ "$i" -le "${#var}" ] do rev="$(echo "$var" | awk -v i="$i" '{print(substr($0,i,1))}')$rev" : $(( i+=1 )) done echo "var: $var, rev: $rev"
Hinweis: Dies funktioniert mit Multi-Byte-Zeichenfolgen. Schnittlösungen funktionieren nur in ASCII-Zeichenfolgen (1 Byte).
quelle
awk '{for(i=length($0);i;i--)printf "%s",substr($0,i,1); print ""}'
oder sogarawk '{for(i=length($0);i;i--)x=x substr($0,i,1); print x}'
Dies kehrt die Zeichenfolge "an Ort und Stelle" um:
a=12345 len=${#a} for ((i=1;i<len;i++)); do a=$a${a: -i*2:1}; done; a=${a:len-1} echo $a
oder die dritte Zeile könnte sein:
for ((i=0;i<len;i++)); do a=${a:i*2:1}$a; done; a=${a:0:len}
oder
for ((i=1;i<len;i++)); do a=${a:0:len-i-1}${a: -i:i+1}${a:len-i-1:1}; done
quelle
Für diejenigen ohne rev (empfohlen) gibt es die folgende einfache awk- Lösung, die Felder in der Nullzeichenfolge aufteilt (jedes Zeichen ist ein separates Feld) und umgekehrt druckt:
awk -F '' '{ for(i=NF; i; i--) printf("%c", $i); print "" }'
Der obige awk- Code ist POSIX-kompatibel. Da eine kompatible awk- Implementierung garantiert auf jedem POSIX-kompatiblen Betriebssystem vorhanden ist, sollte die Lösung daher nicht als "Drittanbieter" betrachtet werden. Dieser Code ist wahrscheinlich prägnanter und verständlicher als eine reine POSIX sh (oder bash ) -Lösung.
(; Ich weiß nicht, ob Sie die Nullzeichenfolge für -F als regulären Ausdruck betrachten ...;)
quelle
Einige einfache Methoden zum Umkehren einer Zeichenfolge
echo '!!!esreveR si sihT' | grep -o . | tac | tr -d '\n' ; echo echo '!!!esreveR si sihT' | fold -w 1 | tac | tr -d '\n' ; echo
In Hex-Werte konvertieren und dann umkehren
echo '!!!esreveR si sihT' | xxd -p | grep -o .. | tac | xxd -r -p ; echo echo '!!!esreveR si sihT' | xxd -p | fold -w 2 | tac | xxd -r -p ; echo
quelle
Wenn
var=12345
:Bash
for((i=0;i<${#var};i++)); do rev="$rev${var:~i:1}"; done
Sch
c=$var; while [ "$c" ]; do rev=$rev${c#"${c%?}"}; c=${c%?}; done
echo "var: $var, rev: $rev"
Starte es:
quelle
Dies kann natürlich verkürzt werden, aber es sollte einfach zu verstehen sein: Das Finale
print
fügt die neue Zeile hinzu.echo 12345 | awk '{for (i = length($0); i > 0; i--) {printf("%s", substr($0, i, 1));} print "";}'
quelle
Niemand scheint eine
sed
Lösung veröffentlicht zu haben , daher hier eine, die in Nicht-GNU-Sed funktioniert (daher würde ich sie nicht als "Drittanbieter" betrachten). Es werden zwar einzelne Zeichen mit dem regulären Ausdruck erfasst.
, dies ist jedoch der einzige reguläre Ausdruck.In zwei Schritten:
$ echo 123456 | sed $'s/./&\\\n/g' | sed -ne $'x;H;${x;s/\\n//g;p;}' 654321
Dies verwendet die Ersetzung des Bash-Formats, um Zeilenumbrüche in die Skripte aufzunehmen (da die Frage markiert ist Bash). Es funktioniert, indem zuerst die Eingabezeichenfolge in eine Zeile pro Zeichen getrennt wird und dann jedes Zeichen am Anfang des Haltepuffers eingefügt wird.
x
vertauscht den Haltebereich und den Musterbereich undH
H hängt den (aktuellen) Musterraum an den Haltebereich an.Also platzieren wir dieses Zeichen für jedes Zeichen in den Haltebereich und hängen dann den alten Haltebereich an ihn an, wodurch die Eingabe umgekehrt wird. Der letzte Befehl entfernt die Zeilenumbrüche, um die ursprüngliche Zeichenfolge zu rekonstruieren.
Dies sollte für jede einzelne Zeichenfolge funktionieren, verkettet jedoch mehrzeilige Eingaben zu einer einzelnen Ausgabezeichenfolge.
quelle
Hier ist eine weitere einfachere
awk
Lösung:awk 'BEGIN{FS=""} {for (i=NF; i>0; i--) s=s $i; print s}' <<< '123456'
quelle
Wort lesen
reve=`echo "$word" | awk '{for(i=length($0); i>0;i--) printf (substr($0,i,1));}'` echo "$reve"
quelle