GNU/Linux >> Belajar Linux >  >> Linux

Daftar Shell yang Mendukung Kata Kunci `local` Untuk Mendefinisikan Variabel Lokal?

Saya tahu bahwa Bash dan Zsh mendukung local variabel, tetapi ada sistem yang hanya memiliki shell yang kompatibel dengan POSIX. Dan local tidak terdefinisi dalam shell POSIX.

Jadi saya ingin bertanya shell mana yang mendukung local kata kunci untuk mendefinisikan variabel lokal?

Edit :Tentang shell yang saya maksud adalah /bin/sh default default cangkang.

Jawaban yang Diterima:

Tidak sesederhana mendukung local atau tidak. Ada banyak variasi pada sintaks dan cara melakukannya antara shell yang memiliki satu bentuk atau lingkup lokal lainnya.

Itulah mengapa sangat sulit untuk menghasilkan standar yang cocok untuk semua orang. Lihat http://austingroupbugs.net/bug_view_page.php?bug_id=767 untuk upaya POSIX di bagian depan itu.

cakupan lokal ditambahkan pertama kali di ksh pada awal 80-an.

Sintaks untuk mendeklarasikan variabel lokal dalam suatu fungsi adalah dengan typeset :

function f {
  typeset var=value
  set -o noglob # also local to the function
  ...
}

(dukungan fungsi ditambahkan ke shell Bourne nanti, tetapi dengan sintaks yang berbeda (f() command ) dan ksh menambahkan dukungan untuk yang itu juga nanti; shell Bourne tidak pernah memiliki cakupan lokal (kecuali tentu saja melalui subkulit))

local builtin AFAIK ditambahkan pertama kali ke shell Almquist (digunakan di BSDs, dash, busybox sh) pada tahun 1989, tetapi bekerja secara signifikan berbeda dari ksh typeset . ash turunan tidak mendukung typeset sebagai alias untuk local , tetapi Anda selalu dapat menentukannya dengan tangan.

bash dan zsh menambahkan typeset alias ke local masing-masing pada tahun 1989 dan 1991.

ksh88 menambahkan local sebagai alias tidak berdokumen untuk typeset sekitar tahun 1990 dan pdksh dan turunannya pada tahun 1994. posh (berdasarkan pdksh ) menghapus typeset (untuk kepatuhan yang ketat terhadap Kebijakan Debian yang memerlukan local , tapi bukan typeset ).

POSIX awalnya keberatan untuk menentukan typeset dengan alasan bahwa itu dinamis pelingkupan. Jadi ksh93 (penulisan ulang ksh pada tahun 1993 oleh David Korn) beralih ke statis pelingkupan sebagai gantinya. Juga di ksh93, sebagai lawan dari ksh88, pelingkupan lokal hanya dilakukan untuk fungsi yang dideklarasikan dengan ksh sintaks (function f {...} ), bukan sintaks Bourne (f() {...} ) dan local alias telah dihapus.

Namun ksh93v- beta dan versi final dari AT&T dapat dikompilasi dengan mode "bash" eksperimental (sebenarnya diaktifkan secara default) yang melakukan pelingkupan dinamis (dalam bentuk fungsi yang mengganggu, termasuk dengan local dan typeset ) ketika ksh93 dipanggil sebagai bash . local berbeda dari typeset dalam hal itu hanya dapat dipanggil dari dalam suatu fungsi. bash . itu mode akan dinonaktifkan secara default di ksh2020 meskipun local /declare alias untuk typeset akan dipertahankan bahkan ketika mode bash tidak dikompilasi (meskipun masih dengan pelingkupan statis).

yash (ditulis jauh kemudian), memiliki typeset (à la ksh88), tetapi hanya memiliki local sebagai alias sejak versi 2.48 (Desember 2018).

@Schily mempertahankan turunan Bourne shell yang baru-baru ini dibuat sebagian besar sesuai dengan POSIX, yang disebut bosh yang mendukung cakupan lokal sejak versi 07-07-06 (dengan local , mirip dengan ash ).

Jadi shell seperti Bourne yang memiliki beberapa bentuk lingkup lokal untuk variabel saat ini adalah:

  • ksh, semua implementasi dan turunannya (ksh88, ksh93, pdksh dan turunannya seperti posh, mksh, OpenBSD sh).
  • ash dan semua turunannya (NetBSD sh, FreeBSD sh, dash, busybox sh)
  • bash
  • zsh
  • yash
  • boss
Terkait:bandingkan dua kolom file yang berbeda dan cetak jika cocok?

Sejauh sh dari sistem yang berbeda pergi, perhatikan bahwa ada sistem di mana POSIX sh ada di /bin (sebagian besar), dan yang lainnya tidak (seperti Solaris yang ada di /usr/xpg4/bin ). Untuk sh implementasi pada berbagai sistem yang kami miliki:

  • ksh88:sebagian besar Unices komersial yang diturunkan dari SysV (AIX, HP/UX, Solaris¹…)
  • bash:sebagian besar sistem GNU/Linux, Cygwin, macOS
  • ash:secara default pada Debian dan sebagian besar turunannya (termasuk Ubuntu, Linux/Mint) meskipun dapat diubah oleh admin menjadi bash atau mksh. NetBSD, FreeBSD dan beberapa turunannya (bukan macOS).
  • busybox sh:banyak jika bukan sebagian besar sistem Linux yang disematkan
  • pdksh atau turunannya:OpenBSD, MirOS

Sekarang, di mana mereka berbeda:

  • typeset (ksh, pdksh, bash, zsh, yash) vs local (ksh88, pdksh, bash, zsh, ash, yash 2.48+).
  • statis (ksh93, dalam function f {...} fungsi), vs pelingkupan dinamis (semua cangkang lainnya). Misalnya, apakah function f { typeset v=1; g; echo "$v"; }; function g { v=2; }; f keluaran 1 atau 2 . Lihat juga cara export atribut memengaruhi pelingkupan di ksh93 .
  • apakah local /typeset buat saja variabel lokal (ash , bosh ), atau membuat instance baru dari variabel (shell lainnya). Misalnya, apakah v=1; f() { local v; echo "${v:-empty}"; }; f keluaran 1 atau empty (lihat juga localvar_inherit opsi di bash 5.0 dan di atasnya).
  • dengan variabel yang membuat variabel baru, apakah variabel baru tersebut mewarisi atribut (seperti export ) dan/atau ketik dan yang mana dari variabel dalam lingkup induk. Misalnya, apakah export V=1; f() { local V=2; printenv V; }; f mencetak 1 , 2 atau tidak sama sekali.
  • apakah variabel baru itu memiliki nilai awal (kosong, 0, daftar kosong, tergantung jenisnya, zsh ) atau awalnya tidak disetel.
  • apakah unset V pada variabel dalam lingkup lokal membiarkan variabel unset , atau cukup kupas satu tingkat pelingkupan (mksh , yash , bash dalam beberapa keadaan). Misalnya, apakah v=1; f() { local v=2; unset v; echo "$v"; } keluaran 1 atau tidak sama sekali (lihat juga localvar_unset opsi di bash 5.0 dan di atasnya)
  • suka untuk export , apakah itu kata kunci atau hanya bawaan atau keduanya dan dalam kondisi apa kata kunci itu dianggap sebagai kata kunci.
  • suka untuk export , apakah argumen diuraikan sebagai argumen perintah normal atau sebagai tugas (dan dalam kondisi apa).
  • apakah Anda dapat mendeklarasikan lokal variabel yang hanya dapat dibaca dalam cakupan induk.
  • interaksi dengan v=value myfunction di mana myfunction sendiri mendeklarasikan v sebagai lokal atau tidak.

Itulah yang saya pikirkan sekarang. Periksa bug grup austin di atas untuk detail lebih lanjut.

Sejauh pelingkupan lokal untuk opsi shell (sebagai lawan dari variabel ), shell yang mendukungnya adalah:

  • ksh88 (dengan kedua sintaks definisi fungsi):dilakukan secara default, saya tidak mengetahui cara apa pun untuk menonaktifkannya.
  • ash (sejak 1989):dengan local - . Itu membuat $- parameter (yang menyimpan daftar opsi) lokal.
  • ksh93 :sekarang hanya dilakukan untuk function f {...} fungsi.
  • zsh (sejak 1995). Dengan setopt localoptions . Juga dengan emulate -L agar mode emulasi (dan rangkaian opsinya) dibuat lokal untuk fungsi tersebut.
  • bash (sejak 2016) dengan local - seperti di ash .

Terkait:Perintah biner dan mode teks Md5sum?
Linux
  1. Spasi Untuk Variabel Dalam Skrip Bash?

  2. Linux – Dukungan Umum Linux Untuk IPv6 Siap?

  3. Daftar Aplikasi &Sumber Daya yang Luar Biasa untuk OS dasar

  1. RedHat Dan SUSE Diumumkan Untuk Menarik Dukungan Untuk OpenLDAP

  2. Menggunakan variabel dalam SQLCMD untuk Linux

  3. Alternatif untuk tail -f yang mengikuti nama file

  1. 80 Alat Pemantauan Linux untuk SysAdmins

  2. Bagaimana Mengkonfigurasi virt-manager untuk Dukungan Virtualisasi Bersarang?

  3. Sebutkan Semua Perintah yang Diketahui Shell?