Catatan: YMMV yang satu ini. Tidak bekerja untuk saya (GNU bash versi 4.2.46 dan 4.0.33 (dan perilaku yang sama 2.05b.0 tetapi nocasematch tidak diterapkan)) bahkan dengan menggunakan shopt -u nocasematch;. Tidak mengonfirmasi bahwa nocasematch menyebabkan [["fooBaR" == "FOObar"]] cocok dengan OK TAPI di dalam case aneh [bz] tidak cocok dengan [AZ]. Bash bingung oleh double-negative ("unsetting nocasematch")! :-)
Apakah saya kehilangan sesuatu, atau apakah contoh terakhir Anda (di Bash) benar-benar melakukan sesuatu yang sama sekali berbeda? Ini berfungsi untuk "ABX", tetapi jika Anda membuat word="Hi All"seperti contoh-contoh lain, ia kembali ha, tidak hi all. Ini hanya berfungsi untuk huruf kapital dan melompati huruf yang sudah lebih kecil.
jangosteve
26
Perhatikan bahwa hanya trdan awkcontoh yang ditentukan dalam standar POSIX.
Richard Hansen
178
tr '[:upper:]' '[:lower:]'akan menggunakan lokal saat ini untuk menentukan setara huruf besar / kecil, jadi itu akan berfungsi dengan lokal yang menggunakan huruf dengan tanda diakritik.
Richard Hansen
10
Bagaimana cara mendapatkan output ke variabel baru? Yaitu saya ingin string yang lebih kecil menjadi variabel baru?
Adam Parkin
60
@Adam:b="$(echo $a | tr '[A-Z]' '[a-z]')"
Tino
435
Dalam Bash 4:
Untuk huruf kecil
$ string="A FEW WORDS"
$ echo "${string,}"
a FEW WORDS
$ echo "${string,,}"
a few words
$ echo "${string,,[AEIUO]}"
a FeWWoRDS
$ string="A Few Words"
$ declare -l string
$ string=$string; echo "$string"
a few words
Ke huruf besar
$ string="a few words"
$ echo "${string^}"
A few words
$ echo "${string^^}"
A FEW WORDS
$ echo "${string^^[aeiou]}"
A fEw wOrds
$ string="A Few Words"
$ declare -u string
$ string=$string; echo "$string"
A FEW WORDS
Toggle (tidak berdokumen, tetapi dapat dikonfigurasi opsional saat waktu kompilasi)
$ string="A Few Words"
$ echo "${string~~}"
a fEW wORDS
$ string="A FEW WORDS"
$ echo "${string~}"
a FEW WORDS
$ string="a few words"
$ echo "${string~}"
A few words
Kapitalisasi (tidak terdokumentasi, tetapi dapat dikonfigurasi secara opsional pada waktu kompilasi)
$ string="a few words"
$ declare -c string
$ string=$string
$ echo "$string"
A few words
Judul kasus:
$ string="a few words"
$ string=($string)
$ string="${string[@]^}"
$ echo "$string"
A FewWords
$ declare -c string
$ string=(a few words)
$ echo "${string[@]}"
A FewWords
$ string="a FeW WOrdS"
$ string=${string,,}
$ string=${string~}
$ echo "$string"
A few words
Untuk mematikan declareatribut, gunakan +. Sebagai contoh declare +c string,. Ini memengaruhi penugasan selanjutnya dan bukan nilai saat ini.
The declarepilihan mengubah atribut dari variabel, tetapi bukan isi. Penugasan kembali dalam contoh saya memperbarui konten untuk menunjukkan perubahan.
Edit:
Menambahkan "beralih karakter pertama dengan kata" ( ${var~}) seperti yang disarankan oleh ghostdog74 .
Sunting: Perilaku tilde yang diperbaiki agar sesuai dengan Bash 4.3.
Cukup aneh, "^^" dan ",," operator tidak bekerja pada karakter non-ASCII tetapi "~~" tidak ... Jadi string="łódź"; echo ${string~~}akan mengembalikan "ŁÓDŹ", tetapi echo ${string^^}mengembalikan "łóDź". Bahkan di LC_ALL=pl_PL.utf-8. Itu menggunakan bash 4.2.24.
Hubert Kario
2
@ HubertKario: Aneh. Ini sama bagi saya di Bash 4.0.33 dengan string yang sama en_US.UTF-8. Ini bug dan saya sudah melaporkannya.
Dijeda sampai pemberitahuan lebih lanjut.
1
@ HubertKario: Coba echo "$string" | tr '[:lower:]' '[:upper:]'. Mungkin akan menunjukkan kegagalan yang sama. Jadi masalahnya setidaknya sebagian bukan milik Bash.
Dijeda sampai pemberitahuan lebih lanjut.
1
@ DennisWilliamson: Ya, saya sudah memperhatikan itu juga (lihat komentar untuk jawaban Shuvalov). Saya hanya akan mengatakan, "barang ini hanya untuk ASCII", tetapi kemudian operator "~~" yang berfungsi, jadi tidak seperti kode dan tabel terjemahan belum ada di sana ...
Hubert Kario
4
@HubertKario: Pemelihara Bash telah mengakui bug dan menyatakan bahwa bug tersebut akan diperbaiki pada rilis berikutnya.
@RichardHansen: trtidak berfungsi untuk saya untuk karakter non-ACII. Saya memiliki set lokal yang benar dan file lokal yang dihasilkan. Ada yang tahu apa yang bisa saya lakukan salah?
Hubert Kario
FYI: Ini berfungsi pada Windows / Msys. Beberapa saran lain tidak.
+1 a="$(tr [A-Z] [a-z] <<< "$a")"terlihat paling mudah bagi saya. Saya masih pemula ...
Sandeepan Nath
2
Saya sangat merekomendasikan sedsolusinya; Saya telah bekerja di lingkungan yang karena alasan tertentu tidak ada trtetapi saya belum menemukan sistem tanpa sed, ditambah banyak waktu saya ingin melakukan ini, saya hanya melakukan sesuatu yang lain sedsehingga dapat membuat rantai perintah bersama menjadi satu pernyataan (panjang).
Haravikk
2
Ekspresi braket harus dikutip. Dalam tr [A-Z] [a-z] A, shell dapat melakukan ekspansi nama file jika ada nama file yang terdiri dari satu huruf atau nullgob diatur. tr "[A-Z]" "[a-z]" Aakan berperilaku baik.
Dennis
2
@ CamiloMartin ini adalah sistem BusyBox tempat saya mengalami masalah itu, khususnya Synology NASes, tetapi saya juga pernah menemukannya di beberapa sistem lain. Saya telah melakukan banyak skrip shell lintas-platform akhir-akhir ini, dan dengan persyaratan bahwa tidak ada tambahan yang diinstal itu membuat semuanya sangat rumit! Namun saya belum menemukan sistem tanpased
Haravikk
2
Catatan yang tr [A-Z] [a-z]salah di hampir semua lokal. misalnya, di en-USlokal, A-Zsebenarnya adalah intervalnya AaBbCcDdEeFfGgHh...XxYyZ.
fuz
44
Saya tahu ini adalah posting lawas tetapi saya membuat jawaban ini untuk situs lain jadi saya pikir saya akan mempostingnya di sini:
UPPER -> lower : use python:
b=`echo "print '$a'.lower()" | python`
Atau Ruby:
b=`echo "print '$a'.downcase" | ruby`
Atau Perl (mungkin favorit saya):
b=`perl -e "print lc('$a');"`
Atau PHP:
b=`php -r "print strtolower('$a');"`
Atau Awk:
b=`echo "$a" | awk '{ print tolower($1) }'`
Atau Sed:
b=`echo "$a" | sed 's/./\L&/g'`
Atau Bash 4:
b=${a,,}
Atau NodeJS jika Anda memilikinya (dan sedikit gila ...):
@ YESUS keduanya bekerja untuk saya atas -> bawah dan bawah-> atas. Saya menggunakan sed 4.2.2 dan Bash 4.3.42 (1) pada 64bit Debian Stretch.
nettux
1
Hai, @ nettux443 ... Saya baru saja mencoba operasi bash lagi dan masih gagal bagi saya dengan pesan kesalahan "substitusi buruk". Saya menggunakan OSX menggunakan bash homebrew: GNU bash, versi 4.3.42 (1) -release (x86_64-apple-darwin14.5.0)
JESii
5
Jangan gunakan! Semua contoh yang menghasilkan skrip sangat rapuh; jika nilai aberisi satu kutipan, Anda tidak hanya merusak perilaku, tetapi juga masalah keamanan yang serius.
tripleee
Saya paling suka solusi sed, karena sed selalu ada di mana-mana.
Dudi Boy
Saya lebih suka menggunakan solusi dd. Harap dicatat bahwa Anda harus menjadi root untuk membuatnya berfungsi
Saya ingin menerima pujian untuk perintah yang ingin saya bagikan tetapi kenyataannya adalah saya mendapatkannya untuk saya gunakan sendiri dari http://commandlinefu.com . Ini memiliki keuntungan bahwa jika Anda cdke direktori mana pun di dalam folder home Anda sendiri, itu akan mengubah semua file dan folder menjadi huruf kecil secara rekursi, silakan gunakan dengan hati-hati. Ini adalah perbaikan baris perintah yang brilian dan sangat berguna untuk banyak album yang telah Anda simpan di drive Anda.
Anda bisa menentukan direktori sebagai pengganti titik (.) Setelah menemukan yang menunjukkan direktori saat ini atau path lengkap.
Saya harap solusi ini terbukti bermanfaat. Satu hal yang tidak dilakukan perintah ini adalah mengganti spasi dengan garis bawah - oh mungkin lain kali.
Ini tidak berhasil bagi saya untuk alasan apa pun, meskipun terlihat baik-baik saja. Saya mendapatkan ini berfungsi sebagai alternatif: menemukan. -exec / bin / bash -c 'mv {} `tr [AZ] [az] <<< {}`' \;
John Rix
Ini perlu prenamedari perl: dpkg -S "$(readlink -e /usr/bin/rename)"memberiperl: /usr/bin/prename
Tino
4
Banyak jawaban menggunakan program eksternal, yang sebenarnya tidak digunakan Bash.
Jika Anda tahu Anda akan memiliki Bash4 tersedia, Anda harus benar-benar hanya menggunakan ${VAR,,}notasi (mudah dan keren). Untuk Bash sebelum 4 (My Mac masih menggunakan Bash 3.2 misalnya). Saya menggunakan versi koreksi dari jawaban ghostdog74 untuk membuat versi yang lebih portabel.
Anda dapat menelepon lowercase 'my STRING'dan mendapatkan versi huruf kecil. Saya membaca komentar tentang mengatur hasilnya ke var, tetapi itu tidak benar-benar portabel Bash, karena kita tidak dapat mengembalikan string. Mencetaknya adalah solusi terbaik. Mudah ditangkap dengan sesuatu seperti var="$(lowercase $str)".
Bagaimana ini bekerja?
Cara kerjanya adalah dengan mendapatkan representasi integer ASCII dari masing-masing karakter dengan printfdan kemudian adding 32jika upper-to->lower, atau subtracting 32jika lower-to->upper. Kemudian gunakan printflagi untuk mengubah nomor kembali menjadi char. Dari 'A' -to-> 'a'kami memiliki perbedaan 32 karakter.
Menggunakan printfuntuk menjelaskan:
$ printf "%d\n""'a"97
$ printf "%d\n""'A"65
97 - 65 = 32
Dan ini adalah versi yang berfungsi dengan contoh.
Harap perhatikan komentar dalam kode, karena mereka menjelaskan banyak hal:
#!/bin/bash# lowerupper.sh# Prints the lowercase version of a char
lowercaseChar(){case"$1"in[A-Z])
n=$(printf "%d""'$1")
n=$((n+32))
printf \\$(printf "%o""$n");;*)
printf "%s""$1";;esac}# Prints the lowercase version of a sequence of strings
lowercase(){
word="$@"for((i=0;i<${#word};i++));do
ch="${word:$i:1}"
lowercaseChar "$ch"done}# Prints the uppercase version of a char
uppercaseChar(){case"$1"in[a-z])
n=$(printf "%d""'$1")
n=$((n-32))
printf \\$(printf "%o""$n");;*)
printf "%s""$1";;esac}# Prints the uppercase version of a sequence of strings
uppercase(){
word="$@"for((i=0;i<${#word};i++));do
ch="${word:$i:1}"
uppercaseChar "$ch"done}# The functions will not add a new line, so use echo or# append it if you want a new line after printing# Printing stuff directly
lowercase "I AM the Walrus!"$'\n'
uppercase "I AM the Walrus!"$'\n'
echo "----------"# Printing a var
str="A StRing WITH mixed sTUFF!"
lowercase "$str"$'\n'
uppercase "$str"$'\n'
echo "----------"# Not quoting the var should also work, # since we use "$@" inside the functions
lowercase $str$'\n'
uppercase $str$'\n'
echo "----------"# Assigning to a var
myLowerVar="$(lowercase $str)"
myUpperVar="$(uppercase $str)"
echo "myLowerVar: $myLowerVar"
echo "myUpperVar: $myUpperVar"
echo "----------"# You can even do stuff likeif[['option 2'="$(lowercase 'OPTION 2')"]];then
echo "Fine! All the same!"else
echo "Ops! Not the same!"fi
exit 0
Dan hasilnya setelah menjalankan ini:
$ ./lowerupper.sh
i am the walrus!
I AM THE WALRUS!----------
a string with mixed stuff!
A STRING WITH MIXED STUFF!----------
a string with mixed stuff!
A STRING WITH MIXED STUFF!----------
myLowerVar: a string with mixed stuff!
myUpperVar: A STRING WITH MIXED STUFF!----------Fine!All the same!
Ini seharusnya hanya berfungsi untuk karakter ASCII .
Bagi saya itu baik-baik saja, karena saya tahu saya hanya akan memberikan karakter ASCII.
Saya menggunakan ini untuk beberapa opsi CLI case-insensitive, misalnya.
Jika menggunakan v4, ini dibakar . Jika tidak, berikut ini adalah solusi sederhana dan dapat diterapkan secara luas . Jawaban lain (dan komentar) pada utas ini cukup membantu dalam membuat kode di bawah ini.
# Like echo, but converts to lowercase
echolcase (){
tr [:upper:][:lower:]<<<"${*}"}# Takes one arg by reference (var name) and makes it lowercase
lcase (){eval"${1}"=\'$(echo ${!1//\'/"'\''"}| tr [:upper:][:lower:])\'
}
Catatan:
Melakukan: a="Hi All"lalu: lcase aakan melakukan hal yang sama seperti:a=$( echolcase "Hi All" )
Dalam fungsi lcase, menggunakan ${!1//\'/"'\''"}alih-alih ${!1}memungkinkan ini berfungsi bahkan ketika string memiliki tanda kutip.
Tidak buruk! Untuk analisis kinerja pendekatan ini, lihat jawaban saya untuk metrik.
Dejay Clayton
3
Terlepas dari berapa usia pertanyaan ini dan mirip dengan jawaban ini oleh technosaurus . Saya kesulitan menemukan solusi yang portabel di sebagian besar platform (Itu Saya Gunakan) serta versi bash yang lebih lama. Saya juga merasa frustrasi dengan array, fungsi dan penggunaan cetakan, gema dan file sementara untuk mengambil variabel sepele. Ini bekerja dengan sangat baik untuk saya sejauh ini saya pikir saya akan berbagi. Lingkungan pengujian utama saya adalah:
GNU bash, versi 4.1.2 (1) -release (x86_64-redhat-linux-gnu)
GNU bash, versi 3.2.57 (1) -release (sparc-sun-solaris2.10)
lcs="abcdefghijklmnopqrstuvwxyz"
ucs="ABCDEFGHIJKLMNOPQRSTUVWXYZ"
input="Change Me To All Capitals"for(( i=0; i<"${#input}"; i++));do:for(( j=0; j<"${#lcs}"; j++));do:if[["${input:$i:1}"=="${lcs:$j:1}"]];then
input="${input/${input:$i:1}/${ucs:$j:1}}"fidonedone
Gaya C sederhana untuk loop untuk beralih melalui string. Untuk baris di bawah ini jika Anda belum melihat yang seperti ini sebelumnya
ini adalah tempat saya belajar ini . Dalam kasus ini, baris akan memeriksa apakah char $ {input: $ i: 1} (huruf kecil) ada di input dan jika demikian menggantinya dengan char $ {ucs: $ j: 1} (huruf besar) dan menyimpannya kembali ke input.
Ini sangat tidak efisien, mengulang 650 kali dalam contoh Anda di atas, dan mengambil 35 detik untuk mengeksekusi 1.000 doa pada mesin saya. Untuk alternatif yang mengulang hanya 11 kali dan membutuhkan waktu kurang dari 5 detik untuk mengeksekusi 1.000 doa, lihat jawaban alternatif saya.
Dejay Clayton
1
Terima kasih, meskipun itu harus jelas hanya dengan melihatnya. Mungkin kesalahan halaman berasal dari ukuran input dan jumlah iterasi yang Anda jalankan. Meskipun demikian saya suka solusi Anda.
JaredTS486
3
Ini adalah variasi yang jauh lebih cepat dari pendekatan JaredTS486 yang menggunakan kemampuan Bash asli (termasuk versi Bash <4.0) untuk mengoptimalkan pendekatannya.
Saya telah menghitung 1.000 iterasi pendekatan ini untuk string kecil (25 karakter) dan string lebih besar (445 karakter), baik untuk konversi huruf kecil dan besar. Karena string tes sebagian besar adalah huruf kecil, konversi ke huruf kecil umumnya lebih cepat daripada huruf besar.
Saya telah membandingkan pendekatan saya dengan beberapa jawaban lain di halaman ini yang kompatibel dengan Bash 3.2. Pendekatan saya jauh lebih berkinerja daripada kebanyakan pendekatan yang didokumentasikan di sini, dan bahkan lebih cepat daripada trdalam beberapa kasus.
Berikut adalah hasil waktu untuk 1.000 iterasi 25 karakter:
0,46 untuk pendekatan saya ke huruf kecil; 0,96 untuk huruf besar
75-an untuk pendekatan ghostdog74 untuk huruf kecil; 669 untuk huruf besar. Sangat menarik untuk dicatat seberapa dramatis perbedaan kinerja antara tes dengan pertandingan yang dominan vs tes dengan kesalahan yang dominan
660 untuk pendekatan JaredTS486 untuk huruf kecil; 660 untuk huruf besar. Sangat menarik untuk dicatat bahwa pendekatan ini menghasilkan kesalahan halaman terus menerus (pertukaran memori) di Bash
Pendekatannya sederhana: sementara string input memiliki huruf besar yang tersisa, temukan yang berikutnya, dan ganti semua instance dari huruf itu dengan varian huruf kecilnya. Ulangi sampai semua huruf besar diganti.
Beberapa karakteristik kinerja solusi saya:
Hanya menggunakan utilitas builtin shell, yang menghindari overhead dari memanggil utilitas biner eksternal dalam proses baru
Hindari sub-shell, yang dikenai penalti kinerja
Menggunakan mekanisme shell yang dikompilasi dan dioptimalkan untuk kinerja, seperti penggantian string global dalam variabel, pemangkasan akhiran variabel, dan pencarian dan pencocokan regex. Mekanisme-mekanisme ini jauh lebih cepat daripada iterasi secara manual melalui string
Ulangi hanya beberapa kali yang diperlukan oleh hitungan karakter pencocokan unik untuk dikonversi. Misalnya, mengonversi string yang memiliki tiga karakter huruf besar berbeda menjadi huruf kecil hanya memerlukan 3 iterasi loop. Untuk alfabet ASCII yang telah dikonfigurasikan, jumlah iterasi loop maksimum adalah 26
Jawaban:
Ada berbagai cara:
Standar POSIX
tr
AWK
Non-POSIX
Anda dapat mengalami masalah portabilitas dengan contoh-contoh berikut:
Bash 4.0
sed
Perl
Pesta
Catatan: YMMV yang satu ini. Tidak bekerja untuk saya (GNU bash versi 4.2.46 dan 4.0.33 (dan perilaku yang sama 2.05b.0 tetapi nocasematch tidak diterapkan)) bahkan dengan menggunakan
shopt -u nocasematch;
. Tidak mengonfirmasi bahwa nocasematch menyebabkan [["fooBaR" == "FOObar"]] cocok dengan OK TAPI di dalam case aneh [bz] tidak cocok dengan [AZ]. Bash bingung oleh double-negative ("unsetting nocasematch")! :-)sumber
word="Hi All"
seperti contoh-contoh lain, ia kembaliha
, tidakhi all
. Ini hanya berfungsi untuk huruf kapital dan melompati huruf yang sudah lebih kecil.tr
danawk
contoh yang ditentukan dalam standar POSIX.tr '[:upper:]' '[:lower:]'
akan menggunakan lokal saat ini untuk menentukan setara huruf besar / kecil, jadi itu akan berfungsi dengan lokal yang menggunakan huruf dengan tanda diakritik.b="$(echo $a | tr '[A-Z]' '[a-z]')"
Dalam Bash 4:
Untuk huruf kecil
Ke huruf besar
Toggle (tidak berdokumen, tetapi dapat dikonfigurasi opsional saat waktu kompilasi)
Kapitalisasi (tidak terdokumentasi, tetapi dapat dikonfigurasi secara opsional pada waktu kompilasi)
Judul kasus:
Untuk mematikan
declare
atribut, gunakan+
. Sebagai contohdeclare +c string
,. Ini memengaruhi penugasan selanjutnya dan bukan nilai saat ini.The
declare
pilihan mengubah atribut dari variabel, tetapi bukan isi. Penugasan kembali dalam contoh saya memperbarui konten untuk menunjukkan perubahan.Edit:
Menambahkan "beralih karakter pertama dengan kata" (
${var~}
) seperti yang disarankan oleh ghostdog74 .Sunting: Perilaku tilde yang diperbaiki agar sesuai dengan Bash 4.3.
sumber
string="łódź"; echo ${string~~}
akan mengembalikan "ŁÓDŹ", tetapiecho ${string^^}
mengembalikan "łóDź". Bahkan diLC_ALL=pl_PL.utf-8
. Itu menggunakan bash 4.2.24.en_US.UTF-8
. Ini bug dan saya sudah melaporkannya.echo "$string" | tr '[:lower:]' '[:upper:]'
. Mungkin akan menunjukkan kegagalan yang sama. Jadi masalahnya setidaknya sebagian bukan milik Bash.sumber
tr
tidak berfungsi untuk saya untuk karakter non-ACII. Saya memiliki set lokal yang benar dan file lokal yang dihasilkan. Ada yang tahu apa yang bisa saya lakukan salah?[:upper:]
dibutuhkan?tr :
AWK :
sed :
sumber
a="$(tr [A-Z] [a-z] <<< "$a")"
terlihat paling mudah bagi saya. Saya masih pemula ...sed
solusinya; Saya telah bekerja di lingkungan yang karena alasan tertentu tidak adatr
tetapi saya belum menemukan sistem tanpased
, ditambah banyak waktu saya ingin melakukan ini, saya hanya melakukan sesuatu yang lainsed
sehingga dapat membuat rantai perintah bersama menjadi satu pernyataan (panjang).tr [A-Z] [a-z] A
, shell dapat melakukan ekspansi nama file jika ada nama file yang terdiri dari satu huruf atau nullgob diatur.tr "[A-Z]" "[a-z]" A
akan berperilaku baik.sed
tr [A-Z] [a-z]
salah di hampir semua lokal. misalnya, dien-US
lokal,A-Z
sebenarnya adalah intervalnyaAaBbCcDdEeFfGgHh...XxYyZ
.Saya tahu ini adalah posting lawas tetapi saya membuat jawaban ini untuk situs lain jadi saya pikir saya akan mempostingnya di sini:
UPPER -> lower : use python:
Atau Ruby:
Atau Perl (mungkin favorit saya):
Atau PHP:
Atau Awk:
Atau Sed:
Atau Bash 4:
Atau NodeJS jika Anda memilikinya (dan sedikit gila ...):
Anda juga bisa menggunakan
dd
(tapi saya tidak mau!):lebih rendah -> UPPER :
gunakan python:
Atau Ruby:
Atau Perl (mungkin favorit saya):
Atau PHP:
Atau Awk:
Atau Sed:
Atau Bash 4:
Atau NodeJS jika Anda memilikinya (dan sedikit gila ...):
Anda juga bisa menggunakan
dd
(tapi saya tidak mau!):Juga ketika Anda mengatakan 'shell' saya berasumsi maksud Anda
bash
tetapi jika Anda dapat menggunakannyazsh
semudahuntuk huruf kecil dan
untuk huruf besar.
sumber
a
berisi satu kutipan, Anda tidak hanya merusak perilaku, tetapi juga masalah keamanan yang serius.Dalam zsh:
Harus cinta zsh!
sumber
echo ${(C)a} #Upcase the first char only
Menggunakan GNU
sed
:Contoh:
sumber
Pre Bash 4.0
Bash Turunkan Kasing dari string dan tetapkan ke variabel
sumber
echo
dan pipa: gunakan$(tr '[:upper:]' '[:lower:]' <<<"$VARIABLE")
Untuk shell standar (tanpa bashisme) hanya menggunakan builtin:
Dan untuk huruf besar:
sumber
${var:1:1}
adalah Bashism.Di bash 4 Anda bisa menggunakan setet
Contoh:
sumber
Anda bisa mencoba ini
ref: http://wiki.workassis.com/shell-script-convert-text-to-lowercase-and-uppercase/
sumber
Ekspresi reguler
Saya ingin menerima pujian untuk perintah yang ingin saya bagikan tetapi kenyataannya adalah saya mendapatkannya untuk saya gunakan sendiri dari http://commandlinefu.com . Ini memiliki keuntungan bahwa jika Anda
cd
ke direktori mana pun di dalam folder home Anda sendiri, itu akan mengubah semua file dan folder menjadi huruf kecil secara rekursi, silakan gunakan dengan hati-hati. Ini adalah perbaikan baris perintah yang brilian dan sangat berguna untuk banyak album yang telah Anda simpan di drive Anda.Anda bisa menentukan direktori sebagai pengganti titik (.) Setelah menemukan yang menunjukkan direktori saat ini atau path lengkap.
Saya harap solusi ini terbukti bermanfaat. Satu hal yang tidak dilakukan perintah ini adalah mengganti spasi dengan garis bawah - oh mungkin lain kali.
sumber
prename
dariperl
:dpkg -S "$(readlink -e /usr/bin/rename)"
memberiperl: /usr/bin/prename
Banyak jawaban menggunakan program eksternal, yang sebenarnya tidak digunakan
Bash
.Jika Anda tahu Anda akan memiliki Bash4 tersedia, Anda harus benar-benar hanya menggunakan
${VAR,,}
notasi (mudah dan keren). Untuk Bash sebelum 4 (My Mac masih menggunakan Bash 3.2 misalnya). Saya menggunakan versi koreksi dari jawaban ghostdog74 untuk membuat versi yang lebih portabel.Anda dapat menelepon
lowercase 'my STRING'
dan mendapatkan versi huruf kecil. Saya membaca komentar tentang mengatur hasilnya ke var, tetapi itu tidak benar-benar portabelBash
, karena kita tidak dapat mengembalikan string. Mencetaknya adalah solusi terbaik. Mudah ditangkap dengan sesuatu sepertivar="$(lowercase $str)"
.Bagaimana ini bekerja?
Cara kerjanya adalah dengan mendapatkan representasi integer ASCII dari masing-masing karakter dengan
printf
dan kemudianadding 32
jikaupper-to->lower
, atausubtracting 32
jikalower-to->upper
. Kemudian gunakanprintf
lagi untuk mengubah nomor kembali menjadi char. Dari'A' -to-> 'a'
kami memiliki perbedaan 32 karakter.Menggunakan
printf
untuk menjelaskan:97 - 65 = 32
Dan ini adalah versi yang berfungsi dengan contoh.
Harap perhatikan komentar dalam kode, karena mereka menjelaskan banyak hal:
Dan hasilnya setelah menjalankan ini:
Ini seharusnya hanya berfungsi untuk karakter ASCII .
Bagi saya itu baik-baik saja, karena saya tahu saya hanya akan memberikan karakter ASCII.
Saya menggunakan ini untuk beberapa opsi CLI case-insensitive, misalnya.
sumber
Kasing konversi dilakukan hanya untuk huruf. Jadi, ini harus bekerja dengan rapi.
Saya fokus pada konversi huruf antara az dari huruf besar ke huruf kecil. Setiap karakter lain hanya boleh dicetak di stdout karena ...
Mengonversi semua teks di jalur / ke / file / nama file dalam rentang az ke AZ
Untuk mengubah huruf kecil menjadi huruf besar
Untuk mengkonversi dari huruf besar ke huruf kecil
Sebagai contoh,
nama file:
dikonversi menjadi:
Contoh 2:
Contoh 3:
sumber
Jika menggunakan v4, ini dibakar . Jika tidak, berikut ini adalah solusi sederhana dan dapat diterapkan secara luas . Jawaban lain (dan komentar) pada utas ini cukup membantu dalam membuat kode di bawah ini.
Catatan:
a="Hi All"
lalu:lcase a
akan melakukan hal yang sama seperti:a=$( echolcase "Hi All" )
${!1//\'/"'\''"}
alih-alih${!1}
memungkinkan ini berfungsi bahkan ketika string memiliki tanda kutip.sumber
Untuk versi Bash lebih awal dari 4.0, versi ini harus paling cepat (karena tidak bercabang / mengeksekusi perintah apa pun):
jawaban technosaurus memiliki potensi juga, meskipun itu berjalan dengan baik untukku.
sumber
Terlepas dari berapa usia pertanyaan ini dan mirip dengan jawaban ini oleh technosaurus . Saya kesulitan menemukan solusi yang portabel di sebagian besar platform (Itu Saya Gunakan) serta versi bash yang lebih lama. Saya juga merasa frustrasi dengan array, fungsi dan penggunaan cetakan, gema dan file sementara untuk mengambil variabel sepele. Ini bekerja dengan sangat baik untuk saya sejauh ini saya pikir saya akan berbagi. Lingkungan pengujian utama saya adalah:
Gaya C sederhana untuk loop untuk beralih melalui string. Untuk baris di bawah ini jika Anda belum melihat yang seperti ini sebelumnya ini adalah tempat saya belajar ini . Dalam kasus ini, baris akan memeriksa apakah char $ {input: $ i: 1} (huruf kecil) ada di input dan jika demikian menggantinya dengan char $ {ucs: $ j: 1} (huruf besar) dan menyimpannya kembali ke input.
sumber
Ini adalah variasi yang jauh lebih cepat dari pendekatan JaredTS486 yang menggunakan kemampuan Bash asli (termasuk versi Bash <4.0) untuk mengoptimalkan pendekatannya.
Saya telah menghitung 1.000 iterasi pendekatan ini untuk string kecil (25 karakter) dan string lebih besar (445 karakter), baik untuk konversi huruf kecil dan besar. Karena string tes sebagian besar adalah huruf kecil, konversi ke huruf kecil umumnya lebih cepat daripada huruf besar.
Saya telah membandingkan pendekatan saya dengan beberapa jawaban lain di halaman ini yang kompatibel dengan Bash 3.2. Pendekatan saya jauh lebih berkinerja daripada kebanyakan pendekatan yang didokumentasikan di sini, dan bahkan lebih cepat daripada
tr
dalam beberapa kasus.Berikut adalah hasil waktu untuk 1.000 iterasi 25 karakter:
tr
untuk huruf kecil; 3.81s untuk huruf besarWaktu hasil untuk 1.000 iterasi dari 445 karakter (terdiri dari puisi "The Robin" oleh Witter Bynner):
tr
menjadi huruf kecil; 4s untuk huruf besarLarutan:
Pendekatannya sederhana: sementara string input memiliki huruf besar yang tersisa, temukan yang berikutnya, dan ganti semua instance dari huruf itu dengan varian huruf kecilnya. Ulangi sampai semua huruf besar diganti.
Beberapa karakteristik kinerja solusi saya:
UCS
danLCS
dapat ditambah dengan karakter tambahansumber
Untuk menyimpan string yang diubah menjadi variabel. Mengikuti berhasil bagi saya -
$SOURCE_NAME
untuk$TARGET_NAME
sumber
Cara sederhana
sumber