Wie wird das Befehlszeilenargument in Großbuchstaben geschrieben?


125

Ich suchte SO und fand, dass es funktionieren würde, wenn man einen String in Großbuchstaben schreibt

str="Some string"
echo ${str^^}

Ich habe jedoch versucht, ein ähnliches Kommandozeilenargument zu verwenden, was zu folgendem Fehler führte

Versucht

#!/bin/bash
             ## Output
echo ${1^^}  ## line 3: ${1^^}: bad substitution
echo {$1^^}  ## No error, but output was still smaller case i.e. no effect

Wie könnten wir das machen?


8
Es funktioniert für mich ganz gut. Poste dein gesamtes Skript, der Fehler ist wahrscheinlich woanders. Zeigt dein Shebang auf bash?
Manatwork

Antworten:


151

Die von str^^Ihnen verwendete Syntax ist ab Bash 4.0 verfügbar. Vielleicht haben Sie eine ältere Version (oder Sie haben das Skript shexplizit ausgeführt):

Versuche dies:

str="Some string"
printf '%s\n' "$str" | awk '{ print toupper($0) }'

1
Aus MTKs Worten ging hervor, dass die Änderung der Groß- und Kleinschreibung für ihn tatsächlich mit Variablen funktioniert.
Manatwork

1
@manatwork Das ist in der Ausgangsfrage nicht klar angegeben. Die Fehlermeldung für eine fehlerhafte Ersetzung ist dieselbe wie bei älteren Bash-Versionen.
Bernhard

4
Du hast Recht. Ich habe die Version 3.2.25 überprüft. Deine Lösung funktioniert und ich habe es auch versucht tr '[a-z]' [[A-Z]'.
MTK

20
@mtk Das sollte sein tr '[a-z]' '[A-Z]'.
l0b0

2
Ich laufe GNU bash, version 4.3.42(1)-release (x86_64-apple-darwin14.5.0)und erhalte den gleichen Fehler wie OP. Ich glaube daher nicht, dass dies auf bash4.0 und höher verfügbar ist, wie Sie sagen.
Heath Borders

79
echo "lowercase" | tr a-z A-Z

Ausgabe:

LOWERCASE

1
Ich denke , POSIX erfordert nicht die /wie in tr /a-z/ /A-Z/vor meiner edit: das funktioniert nur , weil es ersetzt /durch , /ist aber nutzlos: pubs.opengroup.org/onlinepubs/9699919799/utilities/tr.html Es gibt auch die dunkler und weniger nützlich existiert tr '[:lower:]' '[:upper:]'.
Ciro Santilli

Richtig. tr ist sehr unterschiedlich, aber es funktioniert.
Doug

Umlaute funktionieren damit nicht.
Evgeny

22

Seien Sie vorsichtig mit tr, es sei denn, Sie verwenden nur AZ. Bei anderen Gebietsschemata schlägt sogar '[: lower:]' '[: upper:]' fehl, nur awks toupper und bash (v4 +) funktionieren

$ str="abcåäö"
$ echo "$str"|tr '/a-z/' '/A-Z/'
ABCåäö
$ echo "$str"|LC_ALL=sv_SE tr '[:lower:]' '[:upper:]'
ABCåäö
$ echo "$str"|awk '{print toupper($0)}'
ABCÅÄÖ
$ echo ${str^^} # Bash 4.0 and later
ABCÅÄÖ
$ STR="ABCÅÄÖ"
$ echo ${STR,,}
abcåäö

1
FWIW, tr '[:lower:]' '[:upper:]'arbeitet jetzt für Ihr Beispiel auf OS X mindestens (auch mit LC_ALL=sv_SE)
Ethan

1

Alternativ können Sie auf KSH oder zsh wechseln , die seit Jahrzehnten Fall Umwandlung Unterstützung gehabt haben (lange vor bash‚s ${var^^}in 4,0 hinzugefügt), wenn auch mit einer anderen Syntax:

#! /bin/ksh -
typeset -u upper="$1"
printf '%s\n' "$upper"

(Funktioniert auch mit zsh; beachten Sie, dass in pdksh / mksh nur ASCII-Buchstaben unterstützt werden).

Mit zshkönnen Sie auch das UParametererweiterungsflag verwenden:

#! /bin/zsh -
printf '%s\n' "${(U)1}"

POSIXLY können Sie verwenden:

awk 'BEGIN{print toupper(ARGV[1])}' "$1"

Es gibt auch:

printf '%s\n' "$1" | tr '[:lower:]' '[:upper:]'

In einigen Implementierungen, einschließlich GNU tr, funktioniert dies jedoch nur für Einzelbytezeichen (in UTF-8-Gebietsschemas nur für ASCII-Buchstaben).


0

Wenn immer noch jemand Fehler beim Versuch ${str^^}bekommt, können Sie versuchen, python -coder perles liegt wahrscheinlich daran, dass die Bash-Version niedriger als 4 ist.

Bislang funktioniert bash 4 oder höher jedoch schnell mit der vorhandenen Lösung.

L2U="I will be upper"

Verwendung python -cin Bash

python -c "print('$L2U'.upper())"
I WILL BE UPPER

In ähnlicher Weise kann es auch verwendet werden, um Folgendes zu nutzen:

service="bootup.sh on home"
python -c "print('$service'.capitalize())"
Bootup.sh on home

Verwenden perl

echo $L2U | perl -ne 'print "\U$_"'
I WILL BE UPPER
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.