Memakai Ulang Kode melalui Fungsi
Fungsi memberi nama pada operasi yang dapat dipakai ulang. Parameter menyatakan input yang diterima, function body berisi kode yang dijalankan, dan statement return mengirimkan hasil kepada pemanggil.
Struktur dan Sintaks Fungsi
Setiap fungsi Python mengikuti struktur dasar yang sama:
def nama_fungsi(parameter_list):
"""Docstring opsional untuk menjelaskan fungsi"""
# Blok kode yang akan dijalankan
statement_1
statement_2
return nilai_kembalian # OpsionalKomponen fungsi terdiri dari:
- Kata kunci
defuntuk memulai definisi fungsi - Nama fungsi yang mengikuti aturan penamaan variabel Python
- Tanda kurung yang berisi daftar parameter (bisa kosong)
- Titik dua untuk mengakhiri baris definisi
- Blok kode yang diindentasi
- Statement
returnbersifat opsional dan mengembalikan nilai kepada pemanggil
Cara Kerja Pemanggilan Fungsi
Saat fungsi dipanggil, Python memastikan nama atau ekspresi tersebut merujuk ke objek callable. Python kemudian memasangkan setiap argumen dengan parameter dan menjalankan function body di local scope baru.
# Definisi fungsi
def sapa(nama):
pesan = f"Halo, {nama}!"
return pesan
# Pemanggilan fungsi
hasil = sapa("Alice")
print(hasil) # Output: Halo, Alice!
# Pemanggilan langsung dalam print
print(sapa("Bob")) # Output: Halo, Bob!Proses yang terjadi saat pemanggilan fungsi:
- Python mengevaluasi nama atau ekspresi dan memeriksa bahwa hasilnya callable
- Argument binding memasangkan setiap argumen dengan parameter pada definisi fungsi
- Python menjalankan function body di local scope baru
returnmengakhiri pemanggilan dengan nilai. Mencapai akhir fungsi mengembalikanNone
Parameter dan Argumen
Parameter adalah variabel yang didefinisikan dalam fungsi, sedangkan argumen adalah nilai aktual yang dikirimkan saat memanggil fungsi. Python menyediakan beberapa jenis parameter untuk fleksibilitas yang lebih besar.
Parameter Posisi dan Kata Kunci
def perkenalan(nama, umur, kota="Jakarta"):
return f"Namaku {nama}, umurku {umur} tahun, dan aku tinggal di {kota}"
# Menggunakan parameter posisi
print(perkenalan("Sari", 25))
# Output: Namaku Sari, umurku 25 tahun, dan aku tinggal di Jakarta
# Menggunakan parameter kata kunci
print(perkenalan(umur=30, nama="Budi", kota="Bandung"))
# Output: Namaku Budi, umurku 30 tahun, dan aku tinggal di Bandung
# Campuran parameter posisi dan kata kunci
print(perkenalan("Andi", umur=28, kota="Surabaya"))
# Output: Namaku Andi, umurku 28 tahun, dan aku tinggal di SurabayaAturan penggunaan parameter:
- Argumen posisi diberikan sesuai urutan parameter
- Keyword argument dapat diberikan dalam urutan apa saja
- Argumen posisi ditulis sebelum keyword argument
- Parameter dengan default value tidak wajib diberi argumen
Argumen Tambahan
Python dapat mengumpulkan argumen tambahan melalui *args dan **kwargs. Fungsi tetap perlu memeriksa jumlah, jenis, dan nilai argumen sesuai aturan yang dibutuhkan program.
def hitung_total(*angka):
"""Menghitung total dari sejumlah angka"""
total = 0
for num in angka:
total += num
return total
# Memanggil dengan berbagai jumlah argumen
print(hitung_total(1, 2, 3)) # Output: 6
print(hitung_total(5, 10, 15, 20)) # Output: 50
def info_siswa(nama, **detail):
"""Menampilkan informasi siswa dengan detail tambahan"""
print(f"Nama: {nama}")
for kunci, nilai in detail.items():
print(f"{kunci.capitalize()}: {nilai}")
# Memanggil dengan keyword arguments
info_siswa("Maya", umur=20, jurusan="Informatika", ipk=3.8)
# Output:
# Nama: Maya
# Umur: 20
# Jurusan: Informatika
# Ipk: 3.8Parameter *args mengumpulkan argumen posisi tambahan ke dalam tuple, sedangkan **kwargs mengumpulkan argumen kata kunci tambahan ke dalam dictionary.
Return Value
Fungsi dapat mengembalikan nilai dengan statement return. Jika tidak ada return, atau jika return ditulis tanpa nilai, fungsi mengembalikan None.
def luas_lingkaran(radius):
"""Menghitung luas lingkaran"""
import math
return math.pi * radius ** 2
def cari_min_max(daftar_angka):
"""Mengembalikan nilai minimum dan maksimum"""
if not daftar_angka:
return None, None
return min(daftar_angka), max(daftar_angka)
def cetak_pesan(pesan):
"""Fungsi tanpa return eksplisit"""
print(f"Pesan: {pesan}")
# Tidak ada return, otomatis return None
# Contoh penggunaan
luas = luas_lingkaran(5)
print(f"Luas lingkaran: {luas:.2f}") # Output: Luas lingkaran: 78.54
nilai_min, nilai_max = cari_min_max([3, 1, 4, 1, 5, 9])
print(f"Min: {nilai_min}, Max: {nilai_max}") # Output: Min: 1, Max: 9
hasil = cetak_pesan("Hello World") # Output: Pesan: Hello World
print(f"Hasil fungsi cetak_pesan: {hasil}") # Output: Hasil fungsi cetak_pesan: NoneScope dalam Fungsi
Setiap nama dalam Python memiliki scope yang menentukan bagian program yang dapat mengaksesnya. Ketika beberapa scope memakai nama yang sama, Python mencarinya menurut urutan LEGB.
Variabel Lokal dan Global
# Variabel global
counter = 0
def tambah_counter():
# Variabel lokal dengan nama sama
counter = 10
print(f"Counter lokal: {counter}")
def tambah_global_counter():
global counter
counter += 1
print(f"Counter global: {counter}")
# Demonstrasi penggunaan
print(f"Counter awal: {counter}") # Output: Counter awal: 0
tambah_counter() # Output: Counter lokal: 10
print(f"Counter setelah fungsi: {counter}") # Output: Counter setelah fungsi: 0
tambah_global_counter() # Output: Counter global: 1
print(f"Counter akhir: {counter}") # Output: Counter akhir: 1Pencarian nama mengikuti urutan LEGB:
- Local - di dalam fungsi saat ini
- Enclosing - di fungsi luar tempat fungsi saat ini dibuat, khusus untuk fungsi bersarang
- Global - di level modul
- Built-in - nama yang disediakan Python
Fungsi sebagai First Class Object
Python memperlakukan fungsi sebagai nilai. Karena itu, fungsi dapat disimpan dalam variabel, diberikan sebagai argumen, atau dikembalikan oleh fungsi lain. Sifat ini disebut first class object.
def kali_dua(x):
return x * 2
def kali_tiga(x):
return x * 3
def terapkan_operasi(fungsi, nilai):
"""Menerapkan fungsi pada nilai"""
return fungsi(nilai)
# Menyimpan fungsi dalam variabel
operasi = kali_dua
print(operasi(5)) # Output: 10
# Menyimpan fungsi dalam list
daftar_operasi = [kali_dua, kali_tiga]
for op in daftar_operasi:
print(op(4))
# Output:
# 8
# 12
# Mengirim fungsi sebagai argumen
hasil1 = terapkan_operasi(kali_dua, 7)
hasil2 = terapkan_operasi(kali_tiga, 7)
print(f"Hasil: {hasil1}, {hasil2}") # Output: Hasil: 14, 21Dokumentasi Fungsi dengan Docstring
Docstring adalah string literal yang ditempatkan sebagai statement pertama dalam definisi fungsi. Isinya menjelaskan tujuan fungsi dan cara menggunakannya.
def hitung_faktorial(n):
"""
Menghitung faktorial dari bilangan bulat nonnegatif.
Parameter:
n (int): Bilangan bulat nonnegatif
Returns:
int: Nilai faktorial dari n
Raises:
ValueError: Jika n negatif
TypeError: Jika n bukan bilangan bulat
Contoh:
>>> hitung_faktorial(5)
120
>>> hitung_faktorial(0)
1
"""
if not isinstance(n, int):
raise TypeError("Input harus berupa bilangan bulat")
if n < 0:
raise ValueError("Input harus bilangan positif atau nol")
if n <= 1:
return 1
return n * hitung_faktorial(n - 1)
# Mengakses docstring
print(hitung_faktorial.__doc__)
# Menggunakan fungsi
print(hitung_faktorial(5)) # Output: 120
print(hitung_faktorial(0)) # Output: 1Konvensi penulisan docstring yang baik:
- Baris pertama berisi ringkasan singkat fungsi
- Jika perlu penjelasan tambahan, pisahkan dengan baris kosong
- Jelaskan parameter, return value, dan exception yang mungkin terjadi
- Berikan contoh penggunaan jika membantu
Closure pada Fungsi Bersarang
Python mengizinkan fungsi didefinisikan di dalam fungsi lain. Jika inner function dikembalikan, fungsi tersebut tetap dapat mengakses nama dari enclosing scope. Inner function beserta environment yang dipertahankan ini disebut closure.
def buat_pengali(faktor):
"""Membuat fungsi pengali dengan faktor tertentu"""
def pengali(nilai):
"""Fungsi dalam yang mengali nilai dengan faktor"""
return nilai * faktor
return pengali
# Membuat fungsi pengali khusus
pengali_dua = buat_pengali(2)
pengali_lima = buat_pengali(5)
print(pengali_dua(10)) # Output: 20
print(pengali_lima(4)) # Output: 20
def kalkulator_sederhana():
"""Kalkulator dengan fungsi bersarang"""
def tambah(a, b):
return a + b
def kurang(a, b):
return a - b
def kali(a, b):
return a * b
# Mengembalikan dictionary berisi fungsi-fungsi
return {
'tambah': tambah,
'kurang': kurang,
'kali': kali
}
# Menggunakan kalkulator
calc = kalkulator_sederhana()
print(calc['tambah'](5, 3)) # Output: 8
print(calc['kurang'](10, 4)) # Output: 6
print(calc['kali'](6, 7)) # Output: 42Error Handling dalam Fungsi
Tentukan jenis dan nilai input yang diterima fungsi, lalu hasilkan error yang jelas ketika kontrak input dilanggar. Tangkap exception hanya ketika kode dapat memulihkan keadaan, menambahkan keterangan yang berguna, atau menjelaskan kegagalan kepada pengguna.
def bagi(pembilang, penyebut):
"""Membagi dua bilangan riil dengan kontrak input eksplisit."""
if not isinstance(pembilang, (int, float)):
raise TypeError("Pembilang harus berupa bilangan riil")
if not isinstance(penyebut, (int, float)):
raise TypeError("Penyebut harus berupa bilangan riil")
if penyebut == 0:
raise ValueError("Penyebut tidak boleh nol")
return pembilang / penyebut
def konversi_ke_int(nilai):
"""Konversi nilai yang didukung dan pertahankan error dari Python."""
return int(nilai)
# Pemanggilan yang berhasil tetap langsung
print(f"Hasil pembagian: {bagi(10, 2)}")
# Output: Hasil pembagian: 5.0
print(konversi_ke_int("123"))
# Output: 123
# Tangkap error di lapisan presentasi yang dapat menanganinya
for nilai in ("abc", [1, 2]):
try:
print(konversi_ke_int(nilai))
except (TypeError, ValueError) as error:
print(f"Tidak dapat mengonversi {nilai!r}: {error}")