Bash'te fonksiyon, bir grup komutu tek bir ada bağlamanın yoludur ve iki biçimde tanımlanır: ad() { komutlar; } ya da function ad { komutlar; }. Tanımdan sonra fonksiyonu sıradan bir komut gibi adıyla çağırırsınız; verdiğiniz argümanlar fonksiyon çalışırken $1, $2, $@ ve $# olarak görünür. Fonksiyon yeni bir süreç başlatmaz, çağıran kabuğun içinde çalışır. Sonucu iki yolla geri verir: return ile 0-255 arası bir çıkış durumu ya da echo veya printf ile yazdırılıp $( ) ile yakalanan bir metin.

Bu yazıda tanım biçimlerini, süslü parantezlerin neden boşluk istediğini, argümanların nasıl aktarıldığını, return ile değer döndürmenin sınırlarını, tanıma yönlendirme eklemeyi, fonksiyonları listeleme, silme ve alt süreçlere aktarma yollarını GNU Bash kılavuzuna dayanarak anlatıyoruz. Bütün örnekler bir dosyaya yazılıp GNU Bash 5.2.37 ile çalıştırıldı; yorumlardaki çıktılar gerçek çıktılardır. Seriye yeni başlıyorsanız önce Bash öğrenme rehberi sayfasına, betik dosyası oluşturmayı bilmiyorsanız Bash script yazma ve çalıştırma yazısına bakabilirsiniz.

İki tanım biçimi ve farkları

İki tanım biçimi ve farkları

Kılavuz iki sözdizimi verir. Birincisi ad () bileşik-komut, ikincisi function ad [()] bileşik-komut biçimidir. function ayrılmış sözcüğünü yazarsanız addan sonraki parantezler isteğe bağlı olur; yazmazsanız parantezler zorunludur. Üç yazımın davranışı da aynıdır, aşağıdaki örnekte yan yana görebilirsiniz:

bash
#!/usr/bin/env bash
selamla() {
  echo "Merhaba, $1"
}

function veda {
  echo "Güle güle, $1"
}

function ozet() {
  echo "$# argüman geldi: $*"
}

selamla Ayşe        # çıktı: Merhaba, Ayşe
veda Mehmet         # çıktı: Güle güle, Mehmet
ozet bir iki üç     # çıktı: 3 argüman geldi: bir iki üç

Bash açısından aralarında davranış farkı yoktur. Kılavuz ad () biçimini ilk sırada verir ve POSIX modunda Bash, tanımları ekrana yazdırırken function sözcüğünü gerekmedikçe kullanmaz; declare -f çıktısında da tanım ad () biçiminde görünür. Hangisini seçerseniz seçin, bir projede tek bir biçimde karar kılmak okunabilirliği artırır. Kılavuza göre POSIX modunda fonksiyon adının geçerli bir kabuk adı olması ve özel yerleşik komutlardan biriyle aynı olmaması gerekir; POSIX modu dışında ise $ içermeyen, tırnaksız herhangi bir kabuk sözcüğü ad olabilir. Ayrıntılar için Bash ve sh farkı yazısına bakın.

Fonksiyon gövdesi aslında herhangi bir bileşik komuttur. Çoğunlukla { } içine yazılmış bir komut listesi kullanılır, ama gövde ( ), (( )), [[ ]], if, for ya da case da olabilir. Gövdeyi ( ) ile yazarsanız fonksiyon her çağrıldığında alt kabukta çalışır; içeride yaptığınız cd veya değişken ataması dışarıya taşmaz. Bu, geçici bir dizin değişikliğini fonksiyonun içine hapsetmenin temiz bir yoludur:

bash
# Gövde ( ) ise fonksiyon her çağrıda alt kabukta çalışır
gecici_dizin() (
  cd /
  echo "fonksiyon içinde: $PWD"
)
baslangic=$PWD
gecici_dizin                                         # çıktı: fonksiyon içinde: /
[[ $PWD == "$baslangic" ]] && echo "dizin değişmedi"  # çıktı: dizin değişmedi

# Gövde (( )) da olabilir: sonuç sıfır dışıysa durum 0 olur
cift_mi() (( $1 % 2 == 0 ))
cift_mi 4 && echo "4 çift"   # çıktı: 4 çift
cift_mi 7 || echo "7 tek"    # çıktı: 7 tek

İkinci kısımdaki cift_mi fonksiyonunun gövdesi tek bir aritmetik komuttur. (( )) ifadesi sıfır dışı bir değer üretirse çıkış durumu 0 olur, bu yüzden fonksiyonu doğrudan && ve || ile kullanabiliyoruz. Aritmetik komutun kurallarını Bash aritmetik işlemler yazısında, alt kabuk ile { } grubunun farkını Bash subshell ve çalışma ortamı yazısında ayrıntılı anlatıyoruz.

Süslü parantez kuralı: boşluk ve noktalı virgül

Yeni başlayanların en sık takıldığı yer süslü parantezlerdir. Kılavuz, { ve } karakterlerinin ayrılmış sözcük olduğunu ve ancak komut listesinden boşluk ya da başka bir metakarakterle ayrıldıklarında tanındığını söyler. Ayrıca kapanış parantezinden önce listenin noktalı virgül, & ya da yeni satırla bitmesi gerekir. Önce açılıştaki boşluğu unutalım:

bash
yaz() {echo "merhaba"}
yaz
# çıktı:
#   ornek.sh: line 1: syntax error near unexpected token `{echo'
#   ornek.sh: line 1: `yaz() {echo "merhaba"}'

Burada {echo tek bir sözcük olarak okunuyor. Bash bunu gövdenin başlangıcı olarak tanımadığı için ilk satırda sözdizimi hatası veriyor ve hatalı satırı da tekrar yazdırıyor. İkinci denemede parantezin önünde boşluk var ama echo komutu noktalı virgülle bitmiyor:

bash
yaz() { echo "merhaba" }
yaz
# çıktı: ornek.sh: line 4: syntax error: unexpected end of file

Bu kez } karakteri echo komutunun sıradan bir argümanı sanılıyor, gövde hiç kapanmıyor ve Bash dosyanın sonuna gelince unexpected end of file hatası veriyor. Hata satır numarası dosyanın sonunu gösterdiği için asıl sorunun yukarıda olduğunu fark etmek zorlaşır; uzun bir betikte bu hatayı görürseniz önce kapanmamış süslü parantezleri, tırnakları ve fi, done gibi kapanış sözcüklerini arayın. Kural basit: tek satırlık tanımlarda ad() { komut; } yazın, yani açılıştan sonra bir boşluk ve kapanıştan önce bir noktalı virgül bırakın. Çok satırlı tanımlarda yeni satır, noktalı virgülün işini görür.

Fonksiyonu çağırmadan önce tanımlayın

Bash betiği yukarıdan aşağıya okuyup çalıştırır. Bir fonksiyonun adı ancak tanım satırı çalıştıktan sonra bilinir. Tanımdan önce çağırırsanız kabuk adı fonksiyonlar arasında bulamaz, yerleşik komutlara ve PATH dizinlerine bakar, orada da bulamayınca 127 durumuyla command not found hatası verir:

bash
yedekle
yedekle() { echo "yedek alındı"; }
yedekle
# çıktı:
#   ornek.sh: line 1: yedekle: command not found
#   yedek alındı

Bu yüzden büyük betiklerde yaygın düzen şudur: dosyanın başında bütün fonksiyonlar tanımlanır, en sonda tek bir ana "$@" çağrısı yapılır. Fonksiyon gövdeleri tanım sırasında çalışmadığı için bir fonksiyonun içinden daha aşağıda tanımlanmış başka bir fonksiyonu çağırmak sorun değildir; önemli olan, çağrının gerçekten yapıldığı anda ikisinin de tanımlanmış olmasıdır. Kılavuzdaki komut arama sırasına göre bir ad önce fonksiyonlarda, sonra yerleşik komutlarda, en son PATH dizinlerinde aranır. Yani yanlışlıkla test ya da cd adında bir fonksiyon tanımlarsanız betiğin geri kalanı gerçek komut yerine sizin fonksiyonunuzu çalıştırır; fonksiyon adlarını bu yüzden ayırt edici seçin.

Argümanlar: $1, $#, "$@" ve değişmeyen $0

Fonksiyon çalışırken ona verdiğiniz argümanlar geçici olarak konumsal parametrelerin yerini alır. $# yeni argüman sayısını gösterir, fonksiyon bitince eski değerler geri gelir. $0 ise değişmez, betiğin adını göstermeye devam eder. Fonksiyonun kendi adını öğrenmek için kılavuzun anlattığı FUNCNAME dizisinin ilk elemanını kullanırsınız:

bash
goster() {
  echo "içeride: \$0=$0 \$#=$# \$1=$1"
  echo "FUNCNAME[0]=${FUNCNAME[0]}"
}
set -- dis1 dis2 dis3
goster ic1
echo "dışarıda: \$#=$# \$1=$1"
# çıktı:
#   içeride: $0=ornek.sh $#=1 $1=ic1
#   FUNCNAME[0]=goster
#   dışarıda: $#=3 $1=dis1

Argümanları başka bir komuta veya fonksiyona olduğu gibi iletmek istediğinizde mutlaka "$@" yazın. Tırnaksız $@ her argümanı yeniden sözcüklere böler ve içinde boşluk olan bir argümanı ikiye ayırır:

bash
say() { echo "$# argüman"; }
ilet_dogru() { say "$@"; }
ilet_yanlis() { say $@; }

ilet_dogru "bir iki" üç    # çıktı: 2 argüman
ilet_yanlis "bir iki" üç   # çıktı: 3 argüman

İlk çağrıda "bir iki" tek argüman olarak korunuyor, ikincisinde bölünüyor. $* ile $@ farkı, shift ve ${10} gibi konumsal parametre ayrıntılarını Bash script argümanları ve özel değişkenler yazısında bulabilirsiniz; oradaki kurallar fonksiyon argümanları için de aynen geçerlidir. Fonksiyonun isteğe bağlı argümanlarına varsayılan değer vermek için ${1:-varsayilan} kalıbını, zorunlu argümanlar için ${1:?mesaj} kalıbını Bash varsayılan değer yazısında anlatıyoruz.

return ile çıkış durumu döndürmek

Fonksiyonun çıkış durumu, gövdede çalışan son komutun durumudur. return n fonksiyonu hemen bitirir ve n değerini durum olarak bırakır; n verilmezse son çalışan komutun durumu kullanılır. Kılavuz, verilen sayının yalnızca en düşük 8 bitinin kullanıldığını söyler. Bu yüzden 300 değeri 44'e dönüşür, sayısal olmayan bir argüman ise hata verir:

bash
dosya_var_mi() {
  [[ -e $1 ]]          # son komutun durumu fonksiyonun durumu olur
}

yas_kontrol() {
  if (( $1 < 18 )); then
    return 1
  fi
  echo "uygun"
  return 0
}

dosya_var_mi ./olmayan.txt; echo "durum: $?"   # çıktı: durum: 1
yas_kontrol 20; echo "durum: $?"
# çıktı:
#   uygun
#   durum: 0
yas_kontrol 15; echo "durum: $?"               # çıktı: durum: 1

buyuk() { return 300; }
buyuk; echo "durum: $?"                        # çıktı: durum: 44

yanlis() { return evet; }
yanlis; echo "durum: $?"
# çıktı:
#   ornek.sh: line 23: return: evet: numeric argument required
#   durum: 2

return bir hesap sonucu taşımak için değil, başarı ya da başarısızlık bildirmek için tasarlanmıştır. 0 başarı, sıfır dışındaki her değer bir çeşit hata anlamına gelir; if fonksiyon; then yapısı da bu kurala göre çalışır. İlk örnekteki dosya_var_mi fonksiyonunda return hiç yazmadık, çünkü son komut olan [[ -e $1 ]] testinin durumu zaten istediğimiz sonuçtur. Kılavuza göre return ifadesini fonksiyon dışında ya da source ile okunmayan bir betikte kullanmak da hata durumu üretir. Çıkış kodlarının genel anlamlarını Bash exit kodları ve çıkış durumu yazısında anlatıyoruz.

Fonksiyondan değer almak: üç yol

Fonksiyondan değer almak: üç yol: Çıktıyı yakalamak, Global değişken, İsim referansı, Çıkış durumu

Bir fonksiyondan sayı ya da metin geri almanın üç yaygın yolu vardır. Birincisi sonucu standart çıktıya yazmak ve çağıran tarafta komut ikamesiyle yakalamaktır. Bu en okunaklı yöntemdir, ama kılavuza göre komut ikamesi bir alt kabukta çalıştığı için fonksiyonun içinde yaptığınız değişken değişiklikleri kaybolur:

bash
kare() {
  echo $(( $1 * $1 ))
}
sonuc=$(kare 12)
echo "12'nin karesi: $sonuc"      # çıktı: 12'nin karesi: 144

sayac=0
artir() {
  sayac=$(( sayac + 1 ))
  echo "içeride: $sayac"
}
yakalanan=$(artir)
echo "$yakalanan"                  # çıktı: içeride: 1
echo "dışarıda: $sayac"            # çıktı: dışarıda: 0
artir                              # çıktı: içeride: 1
echo "dışarıda: $sayac"            # çıktı: dışarıda: 1

$(artir) çağrısında sayaç alt kabukta 1 oluyor ama ana kabuktaki sayac 0 kalıyor. Aynı fonksiyonu doğrudan çağırdığımızda ise değişiklik kalıcı oluyor. İkinci yol tam da bu davranışa dayanır: fonksiyonun sonucu global bir değişkene yazması. Kısa betiklerde işe yarar ama hangi fonksiyonun hangi değişkeni değiştirdiğini takip etmek zorlaşır. Üçüncü yol, sonucun yazılacağı değişkenin adını argüman olarak vermek ve fonksiyon içinde local -n ile bir isim referansı oluşturmaktır:

bash
topla() {
  local -n _hedef=$1      # _hedef artık adı $1 olan değişkeni temsil eder
  _hedef=$(( $2 + $3 ))
}
topla toplam 7 5
echo "$toplam"            # çıktı: 12

İsim referansı alt kabuk açmaz ve dizi gibi birden fazla değeri döndürmeye de uygundur. İsim çakışması gibi tuzakları ve local komutunun bütün ayrıntılarını Bash local değişken ve kapsam yazısında ele alıyoruz. Komut ikamesinin sondaki yeni satırları silmesi gibi inceliklerini ise Bash komut ikamesi yazısında bulabilirsiniz. Aşağıdaki tablo dört yöntemi karşılaştırıyor:

YöntemNasılArtısıDikkat
Çıktıyı yakalamaksonuc=$(fonk)Okunaklı, yan etkisizAlt kabuk açar, değişken değişikliği kaybolur
Global değişkenfonk; echo "$SONUC"Alt kabuk yokGizli bağımlılık oluşturur
İsim referansıfonk hedef ve içeride local -n r=$1Alt kabuk yok, dizi döndürebilirHedef adı fonksiyonun yerel adıyla çakışmamalı
Çıkış durumureturn 0..255if ile doğrudan kullanılırYalnızca 8 bitlik sayı taşır

Tanıma yönlendirme eklemek

Kılavuzdaki sözdiziminde bileşik komuttan sonra isteğe bağlı yönlendirmeler gelebilir. Bu yönlendirmeler tanım sırasında değil, fonksiyon her çalıştığında uygulanır. Aşağıdaki fonksiyonun bütün çıktısı her çağrıda rapor.txt dosyasına yazılıyor; > kullandığımız için dosya her seferinde baştan oluşturuluyor ve iki çağrıdan sonra bile içinde yalnızca iki satır kalıyor:

bash
rapor() {
  echo "satır 1"
  echo "satır 2"
} > rapor.txt

rapor
rapor                     # dosya her çağrıda yeniden yazılır
while IFS= read -r s; do echo "dosyada: $s"; done < rapor.txt
# çıktı:
#   dosyada: satır 1
#   dosyada: satır 2

Bu teknik, bir fonksiyonun bütün mesajlarını her zaman standart hataya göndermek (} >&2) veya bir günlük fonksiyonunu tek yerde bir dosyaya bağlamak için kullanışlıdır. Çağıran kişi her seferinde yönlendirme yazmak zorunda kalmaz. Yönlendirme operatörlerinin kendisini Bash yönlendirme: stdout ve stderr yazısında anlatıyoruz.

Fonksiyonları listelemek, silmek ve alt süreçlere aktarmak

Tanımlı fonksiyonları görmek için declare yerleşik komutu kullanılır: declare -f ad tanımı Bash'in yeniden biçimlendirdiği haliyle yazdırır, declare -F yalnızca adları listeler. type -t ad bir adın fonksiyon mu, yerleşik komut mu, takma ad mı olduğunu tek sözcükle söyler. Bir tanımı kaldırmak için unset -f ad yazılır:

bash
merhaba() { echo "merhaba"; }

declare -F merhaba        # çıktı: merhaba
type -t merhaba           # çıktı: function
declare -f merhaba
# çıktı:
#   merhaba ()
#   {
#       echo "merhaba"
#   }

unset -f merhaba
type -t merhaba || echo "artık tanımlı değil"   # çıktı: artık tanımlı değil

declare -f çıktısında tanımın sizin yazdığınız biçimde değil, Bash'in kendi düzeninde gösterildiğine dikkat edin; tek satırlık tanım çok satıra açılmış. Fonksiyonlar normalde yalnızca tanımlandıkları kabukta yaşar. Ayrı bir bash süreci başlattığınızda o süreç onları görmez. Kılavuza göre export -f ile işaretlenen fonksiyonlar ortam üzerinden alt kabuk süreçlerine aktarılır:

bash
selam() { echo "yeni bash: $1"; }

bash -c 'selam deneme' 2>/dev/null || echo "dışa aktarılmadı"   # çıktı: dışa aktarılmadı
export -f selam
bash -c 'selam deneme'                                          # çıktı: yeni bash: deneme

Bu özellik yalnızca yeni süreç de Bash olduğunda işe yarar. Ortam değişkenlerinin alt süreçlere nasıl geçtiğini Bash değişkenler ve atama yazısında, declare seçeneklerinin tamamını Bash declare ve readonly yazısında bulabilirsiniz.

Özyineleme ve FUNCNEST sınırı

Bash fonksiyonları kendilerini çağırabilir ve kılavuza göre varsayılan olarak özyinelemeli çağrı sayısına bir sınır konmaz. FUNCNEST değişkenine 0'dan büyük bir sayı verirseniz bu sayı en fazla iç içe çağrı seviyesini belirler; sınırı aşan çağrı içinde bulunduğu komutu iptal eder:

bash
faktoriyel() {
  local n=$1 onceki
  if (( n <= 1 )); then
    echo 1
    return
  fi
  onceki=$(faktoriyel $(( n - 1 )))
  echo $(( n * onceki ))
}
faktoriyel 5              # çıktı: 120

FUNCNEST=3
derin() { echo "seviye $1"; derin $(( $1 + 1 )); }
derin 1
echo "betik devam ediyor"
# çıktı:
#   seviye 1
#   seviye 2
#   seviye 3
#   ornek.sh: line 13: derin: maximum function nesting level exceeded (3)
#   betik devam ediyor

Faktöriyel örneği her adımda komut ikamesiyle yeni bir alt kabuk açtığı için büyük değerlerde yavaşlar; burada amaç kavramı göstermektir. İkinci kısımda sınır 3 olduğu için dördüncü çağrı hata veriyor, komut iptal ediliyor ve betik bir sonraki satırdan devam ediyor. FUNCNEST, sonsuz özyinelemeye düşen bir betiğin kontrolden çıkmasını önlemek için bir güvenlik ağı olarak kullanılabilir.

Fonksiyon, alias ve ayrı betik karşılaştırması

Fonksiyon, alias ve ayrı betik karşılaştırması: Argüman alır mı, Ayrı süreç, Çağıranın değişkenini değiştirebilir mi, Yerel değişken

Benzer bir işi bir takma adla, bir fonksiyonla ya da ayrı bir betik dosyasıyla yapabilirsiniz. Kılavuzun takma adlar bölümü, neredeyse her amaç için fonksiyonların takma adlara tercih edilmesi gerektiğini söyler. Aşağıdaki tablo farkları özetliyor:

ÖzellikFonksiyonAliasAyrı betik
Argüman alır mıEvet, $1 ve $@ ileHayır, yalnızca metin yerine koyarEvet
Ayrı süreçHayır, aynı kabuktaHayırEvet, yeni süreç
Çağıranın değişkenini değiştirebilir miEvetEvetHayır
Yerel değişkenlocal ileYokBütün değişkenleri kendine ait
Betik içinde varsayılan olarak çalışır mıEvetHayır, expand_aliases gerekirEvet

Takma adların ayrıntıları için Bash alias tanımlama, ortak fonksiyonları ayrı bir dosyada tutup betiklere eklemek için Bash source ve nokta komutu yazısına bakın.

Uygulamalı örnek: küçük bir yardımcı betik

Şimdi öğrendiklerimizi bir araya getirelim. Aşağıdaki betikte dört fonksiyon var: log mesajları standart hataya yazar, kullanim doğru kullanımı gösterir, satir_say bir dosyanın satırlarını sayıp sonucu çıktı olarak verir, ana ise argümanları kontrol edip diğerlerini çağırır. Her fonksiyon tek bir iş yapıyor ve başarısını çıkış durumuyla bildiriyor:

bash
#!/usr/bin/env bash
log() {
  local seviye=$1
  shift
  printf '[%s] %s\n' "$seviye" "$*" >&2
}

kullanim() {
  echo "Kullanım: ${0##*/} <dosya>"
}

satir_say() {
  local n=0 satir
  while IFS= read -r satir; do
    n=$(( n + 1 ))
  done < "$1"
  echo "$n"
}

ana() {
  if (( $# != 1 )); then
    kullanim
    return 2
  fi
  if [[ ! -f $1 ]]; then
    log HATA "$1 bulunamadı"
    return 1
  fi
  log BILGI "$1 işleniyor"
  echo "$1: $(satir_say "$1") satır"
}

printf 'a\nb\nc\n' > veri.txt
ana;            echo "durum: $?"
ana yok.txt;    echo "durum: $?"
ana veri.txt;   echo "durum: $?"
# çıktı:
#   Kullanım: ornek.sh <dosya>
#   durum: 2
#   [HATA] yok.txt bulunamadı
#   durum: 1
#   [BILGI] veri.txt işleniyor
#   veri.txt: 3 satır
#   durum: 0

Birkaç ayrıntıya dikkat edin. ${0##*/} betik adının dizin kısmını atar; bu parametre genişletme kalıbını Bash string işlemleri yazısında anlatıyoruz. log içinde shift ile ilk argümanı alıp kalanını $* ile tek mesaj olarak birleştiriyoruz. satir_say içindeki n ve satir değişkenleri local olduğu için dışarıdaki aynı adlı değişkenleri bozmaz. Kullanım hatasında 2, dosya bulunamadığında 1 döndürmek, betiği çağıran başka bir programın iki durumu ayırt etmesini sağlar. Gerçek bir betikte son satır ana "$@" olur ve betiğin kendi argümanlarını fonksiyona iletir.

Sık yapılan hatalar

  • Süslü parantezden sonra boşluk ya da kapanıştan önce noktalı virgül unutmak: f() {echo x} sözdizimi hatası verir.
  • Fonksiyonu tanımından önce çağırmak: Bash betiği satır satır okuduğu için command not found alırsınız.
  • Hesap sonucunu return ile döndürmeye çalışmak: değer 255'i aşınca 8 bite kırpılır; sonucu echo ile yazdırıp yakalayın.
  • $( ) ile çağrılan fonksiyondan global değişken değiştirmesini beklemek: komut ikamesi alt kabukta çalışır.
  • Argümanları tırnaksız $@ ile iletmek: boşluk içeren argümanlar bölünür, her zaman "$@" yazın.
  • Bütün değişkenleri global bırakmak: yardımcı değişkenleri local ile tanımlamazsanız çağıranın değişkenlerini ezersiniz.

Fonksiyonlar beklenmedik davrandığında set -x ile her satırın nasıl genişletildiğini görebilirsiniz; bu konu Bash script hata ayıklama yazısında. Hata mesajlarının genel bir listesi için Bash sık hata mesajları yazısına bakın.

Sık Sorulan Sorular

function sözcüğünü kullanmalı mıyım?

Zorunlu değil. Bash için ad() { ...; } ve function ad { ...; } aynı fonksiyonu tanımlar. Betiğin sh gibi başka kabuklarda da çalışması gerekiyorsa hangi yazımın desteklendiğini o kabuğun belgesinden kontrol edin; yalnızca Bash kullanıyorsanız ekip içinde tek bir biçim seçmeniz yeterli.

Fonksiyon bir dizi döndürebilir mi?

return yalnızca sayı taşır. Diziyi döndürmek için en temiz yol, hedef dizinin adını argüman olarak verip fonksiyonda local -n ile ona yazmaktır. Alternatif olarak elemanları satır satır yazdırıp çağıran tarafta mapfile ile okuyabilirsiniz; bu yöntem mapfile ve readarray yazısında.

Fonksiyon içinde exit yazarsam ne olur?

Fonksiyon aynı kabukta çalıştığı için exit bütün betiği sonlandırır. Yalnızca fonksiyondan çıkmak istiyorsanız return kullanın. Fonksiyon $( ) içinde çağrıldıysa ya da gövdesi ( ) ise exit yalnızca o alt kabuğu bitirir.

Bir fonksiyonun hangi dosyada tanımlandığını nasıl görürüm?

Kılavuza göre extdebug kabuk seçeneği açıkken declare -F ad komutu fonksiyonun adıyla birlikte tanımlandığı dosyayı ve satır numarasını da gösterir. Seçeneği shopt -s extdebug ile açabilirsiniz; diğer seçenekler için shopt seçenekleri yazısına bakın.

Marka adları sahiplerine aittir. Bu yazı bağımsız bir teknik rehberdir; adı geçen kuruluşlarla bayilik veya ortaklık ilişkisi bulunduğu anlamına gelmez.

İlgili içerikler: Bash öğrenme rehberi · local ve değişken kapsamı · Betik argümanları · Komut ikamesi · Exit kodları · source komutu