Cakupan variabel global dan lokal

Dalam artikel ini, Anda akan mempelajari cakupan dan cara kerjanya di JavaScript.

Cakupan adalah konsep dasar dalam JavaScript dan bahasa pemrograman lainnya yang menentukan konteks di mana variabel diakses dan digunakan. Ini menjadi lebih berguna dan sesuai untuk kode Anda saat Anda terus mempelajari JavaScript dan bekerja lebih banyak dengan variabel.

Cakupan dapat membantu Anda:

  • Menggunakan memori secara lebih efisien: Cakupan memberikan kemampuan untuk memuat variabel hanya saat diperlukan. Jika variabel berada di luar cakupan, Anda tidak perlu membuatnya tersedia untuk kode yang sedang dieksekusi.
  • Menemukan dan memperbaiki bug dengan lebih mudah: Mengisolasi variabel dengan cakupan lokal mempermudah pemecahan masalah bug dalam kode Anda karena tidak seperti variabel global, Anda dapat merasa yakin bahwa kode dari luar cakupan tidak dapat memanipulasi variabel cakupan lokal.
  • Buat blok kecil kode yang dapat digunakan kembali: Misalnya, Anda dapat menulis fungsi murni yang tidak bergantung pada cakupan luar. Anda dapat dengan mudah memindahkan fungsi tersebut ke tempat lain dengan sedikit perubahan.

Apa yang dimaksud dengan ruang lingkup?

Cakupan variabel menentukan dari mana Anda dapat menggunakan variabel dalam kode.

JavaScript menentukan variabel cakupan global atau lokal:

  • Variabel dengan cakupan global tersedia dari semua cakupan lain dalam kode JavaScript.
  • Variabel dengan cakupan lokal hanya tersedia dalam konteks lokal tertentu dan dibuat dengan kata kunci, seperti var, let, dan const. Jika Anda menggunakan kata kunci var, let, atau const untuk membuat variabel dalam fungsi, variabel tersebut akan memiliki cakupan lokal.

Bagian selanjutnya dalam artikel ini membahas blok dan cakupan leksikal:

  • Variabel cakupan blok tersedia secara lokal ke blok seperti yang ditentukan oleh lokasi tanda kurung kurawal tempat pernyataan blok ditentukan. Hanya variabel yang dideklarasikan dengan kata kunci let atau const yang memiliki cakupan pemblokiran.
  • Cakupan leksikal menggunakan lokasi tempat variabel dideklarasikan dalam kode sumber untuk menentukan tempat variabel tersebut tersedia. Anda menggunakanclosure untuk memberikan akses fungsi tertutup ke variabel yang dirujuk dalam cakupan luar yang dikenal sebagai lingkungan leksikal.

Saat variabel diakses dalam cakupannya, JavaScript akan menampilkan nilai yang ditetapkan atau menghasilkan error.

Untuk mendeklarasikan variabel:

  • Gunakan kata kunci var, const, atau let untuk mendeklarasikan variabel cakupan lokal atau global.
  • Gunakan kata kunci const atau let untuk mendeklarasikan variabel cakupan blok.

Saat Anda mendeklarasikan variabel var dalam suatu fungsi, deklarasi tersebut akan menyediakan variabel tersebut ke fungsi pembatas terdekat. Anda tidak dapat menggunakan kata kunci var untuk mendeklarasikan variabel dengan cakupan pemblokiran.

Contoh cakupan

Contoh ini menunjukkan cakupan global karena variabel greeting dideklarasikan di luar fungsi atau blok apa pun, sehingga nilainya tersedia untuk semua kode dalam dokumen saat ini:

const greeting = 'hello';
console.log(greeting); // 'hello'

Dalam contoh cakupan global, variabel greeting diberi nilai hello.

Contoh ini menunjukkan cakupan lokal karena mendeklarasikan variabel greeting dengan kata kunci let dalam suatu fungsi. Variabel greeting adalah variabel cakupan lokal dan tidak tersedia di luar fungsi.

function greet() {
  let greeting = 'Hello World!';
  console.log(greeting);
}

Contoh ini menunjukkan cakupan blok karena mendeklarasikan variabel greeting dalam blok sehingga variabel hanya dapat diakses di dalam tanda kurung kurawal:

if (true) {
   const greeting = 'hello';
}

console.log(greeting); // ReferenceError: greeting is not defined

Perhatikan bahwa saat fungsi console.log mencoba menghasilkan nilai variabel greeting, JavaScript akan menampilkan pesan error ReferenceError, bukan pesan hello yang diharapkan. Mengapa?

Error akan ditampilkan karena variabel greeting memiliki cakupan blok dan blok terdekat adalah bagian dari pernyataan kondisional if. Anda tidak dapat mengakses variabel let dan const yang Anda deklarasikan di dalam blok dari luar blok. Dengan demikian, Anda hanya dapat mengakses variabel greeting dalam tanda kurung kurawal, yang menentukan cakupan blok.

Contoh ini memperbaiki error karena memindahkan metode console.log(message) ke dalam tanda kurung kurawal. Kode yang diperbarui memindahkan metode console.log(message) di dalam blok.

if (true) {
   const greeting = 'hello';
   console.log(greeting);
}

Jenis cakupan

Cakupan global

Anda dapat mengakses variabel dengan cakupan global dari mana saja dalam program.

Pertimbangkan file HTML yang mengimpor dua file JavaScript: file-1.js dan file-2.js:

<script src="file-1.js"></script>
<script src="file-2.js"></script>

Dalam contoh ini, variabel globalMessage memiliki cakupan global dan ditulis di luar fungsi. Selama pengoperasian dan eksekusi, Anda dapat mengakses nilai variabel globalMessage dari mana saja dalam program JavaScript.

Anda dapat melihat konten file file-1.js dan file-2.js dalam cuplikan kode ini. Perhatikan ketersediaan variabel globalMessage di kedua file.

// file-1.js
function hello() {
    var localMessage = 'Hello!';
}

var globalMessage = 'Hey there!';

// file-2.js
console.log(localMessage); // localMessage is not defined
console.log(globalMessage); // Hey there!

Ada jenis ruang lingkup lain yang tidak banyak dibahas dalam artikel ini. Jika Anda membuat variabel dalam modul JavaScript tetapi di luar fungsi atau blok, variabel tersebut tidak memiliki cakupan global, melainkan cakupan modul. Variabel dengan cakupan modul tersedia di mana saja dalam modul saat ini, tetapi tidak tersedia dari file atau modul lain. Agar variabel cakupan modul tersedia untuk file lain, Anda harus mengekspornya dari modul tempat variabel dibuat, lalu import dari modul yang perlu mengakses variabel.

Cakupan lokal dan cakupan fungsi

Saat Anda membuat variabel dalam fungsi JavaScript dengan kata kunci var, let, atau const, variabel tersebut akan bersifat lokal untuk fungsi, sehingga Anda hanya dapat mengaksesnya dari dalam fungsi. Variabel lokal dibuat saat sebuah fungsi dimulai dan dihapus secara efektif saat eksekusi fungsi selesai.

Contoh ini mendeklarasikan variabel total dalam fungsi addNumbers(). Anda hanya dapat mengakses variabel a, b,, dan total dalam fungsi addNumbers().

function addNumbers(a, b) {
    const total = a + b;
}

addNumbers(3, 4);

Anda dapat menggunakan kata kunci let dan const untuk memberi nama variabel. Saat Anda menggunakan kata kunci let, JavaScript dapat memperbarui variabel. Namun, dengan kata kunci const, variabelnya tetap konstan.

var variable1 = 'Declared with var';
var variable1 = 'Redeclared with var';
variable1; // Redeclared with var

let variable2 = 'Declared with let. Cannot be redeclared.';
variable2 = 'let cannot be redeclared, but can be updated';
variable2; // let cannot be redeclared, but can be updated

const variable3 = 'Declared with const. Cannot be redeclared or updated';
variable3; // Declared with const. Cannot be redeclared or updated

Blokir cakupan

Blok digunakan untuk mengelompokkan satu pernyataan atau sekumpulan pernyataan. Anda dapat menggunakan kata kunci const atau let untuk mendeklarasikan variabel lokal cakupan blok. Perhatikan bahwa Anda tidak dapat menggunakan kata kunci var untuk mendeklarasikan variabel dengan cakupan pemblokiran.

Misalnya, dalam blok ini, cakupan untuk variabel name dan nilai "Elizabeth"-nya terdapat dalam tanda kurung kurawal. Variabel dalam cakupan blok tidak tersedia di luar blok tersebut.

{
    const name = "Elizabeth";
}

Anda dapat menggunakan variabel cakupan blok dalam pernyataan if, for, atau while.

Catat dua loop for dalam cuplikan kode ini. Satu loop for menggunakan kata kunci var untuk mendeklarasikan variabel penginisialisasi, yang bertambah melalui angka 0, 1, dan 2. Loop for lainnya menggunakan kata kunci let untuk mendeklarasikan variabel penginisialisasi.

for (var i = 0; i < 2; i++) {
    // ...
}

console.log(i); // 2

for (let j = 0; j < 2; j++) {
    // ...
}

console.log(j); // The j variable isn't defined.

Pada contoh kode sebelumnya, Anda mungkin melihat bahwa variabel i dalam loop for pertama bocor ke luar loop for dan masih mempertahankan nilai 2 karena kata kunci var tidak menggunakan cakupan pemblokiran. Masalah ini telah diperbaiki dalam loop for kedua tempat variabel j yang dideklarasikan dengan kata kunci let dicakupkan ke blok loop for dan tidak ada setelah loop for selesai.

Penggunaan kembali nama variabel dalam cakupan yang berbeda

Cakupan dapat mengisolasi variabel dalam sebuah fungsi, meskipun Anda menggunakan kembali nama variabel yang sama di tempat lain dalam cakupan yang berbeda.

Contoh ini menunjukkan bagaimana penggunaan cakupan memungkinkan Anda menggunakan kembali nama variabel yang sama dalam fungsi yang berbeda:

function listOne() {
    let listItems = 10;
    console.log(listItems); // 10
}

function listTwo() {
   let listItems = 20;
   console.log(listItems); // 20
}

listOne();
listTwo();

Variabel listItems dalam fungsi listOne() dan listTwo() diberi nilai yang diharapkan, sehingga tidak bertentangan.

{i>Closures<i} dan cakupan leksikal

Penutupan mengacu pada fungsi tertutup tempat fungsi internal dapat mengakses cakupan fungsi luar, yang juga dikenal sebagai lingkungan leksikal. Dengan demikian, dalam JavaScript, Anda menggunakanclosure untuk memungkinkan fungsi mereferensikan lingkungan leksikal luar, yang memungkinkan kode di dalam variabel referensi fungsi yang dideklarasikan di luar fungsi. Bahkan, Anda dapat membuat kode rantai referensi ke lingkungan leksikal luar sehingga fungsi dipanggil oleh fungsi, yang kemudian dipanggil oleh fungsi lain.

Dalam contoh ini, kode membentuk penutupan dengan lingkungan leksikal yang dibuat saat fungsi outer() dipanggil, yang menutup variabel hello. Dengan demikian, variabel hello digunakan dalam fungsi callback setTimeout.

function outer() {
    const hello = 'world';

    setTimeout(function () {
        console.log('Within the closure!', hello)
    }, 100);
}

outer();

Dengan cakupan leksikal, cakupan ditentukan selama kompilasi kode sumber, bukan saat runtime. Untuk mempelajari lingkungan leksikal lebih lanjut, lihat Cakupan dan Penutupan leksikal.

Modul

Modul JavaScript membantu mengatur kode JavaScript. Jika digunakan dengan benar, format ini akan memberikan struktur yang efektif untuk codebase Anda dan membantu penggunaan kembali kode. Daripada menggunakan variabel global untuk berbagi variabel di berbagai file, modul JavaScript menyediakan teknik untuk mengekspor dan import variabel.

// hello.js file
function hello() {
  return 'Hello world!';
}

export { hello };

// app.js file
import { hello } from './hello.js';

console.log(hello()); // Hello world!

Demo visualizer cakupan

Cakupan adalah konsep dasar yang harus dipahami oleh setiap developer JavaScript. Untuk lebih memahami sistem cakupan, Anda dapat mencoba menulis kode Anda sendiri dengan JS Scope Visualizer. Demo ini menggunakan pewarnaan dalam kode untuk membantu Anda memvisualisasikan cakupan JavaScript.

Kesimpulan

Artikel ini memperkenalkan berbagai jenis ruang lingkup. Cakupan JavaScript adalah salah satu konsep lanjutan dalam pengembangan web, jadi bagus Anda telah membaca secara menyeluruh konten ini dan meluangkan waktu untuk memahami topik ini.

Cakupan bukan fitur yang ditampilkan kepada pengguna. Hal ini hanya memengaruhi developer web yang menulis kode, tetapi pengetahuan tentang cara kerja cakupan dapat membantu Anda memperbaiki bug ketika muncul.