ขอบเขตตัวแปรส่วนกลางและเฉพาะรายการ

บทความนี้จะอธิบายขอบเขตและวิธีการทำงานของขอบเขตใน JavaScript

ขอบเขตเป็นแนวคิดพื้นฐานใน JavaScript และภาษาโปรแกรมอื่นๆ ที่กำหนดบริบทที่มีการเข้าถึงและใช้ตัวแปร ซึ่งจะมีประโยชน์และสามารถใช้ได้กับโค้ดของคุณมากขึ้น เมื่อคุณเรียนรู้ JavaScript และทำงานกับตัวแปรมากขึ้นอย่างต่อเนื่อง

ขอบเขตจะช่วยคุณในเรื่องต่อไปนี้

  • ใช้หน่วยความจำอย่างมีประสิทธิภาพมากขึ้น: ขอบเขตมอบความสามารถในการโหลดตัวแปรเมื่อจำเป็นเท่านั้น หากตัวแปรอยู่นอกขอบเขต คุณไม่จำเป็นต้องทำให้ตัวแปรใช้ได้กับโค้ดที่กำลังใช้งาน
  • ค้นหาและแก้ไขข้อบกพร่องได้ง่ายขึ้น: การแยกตัวแปรด้วยขอบเขตภายในเครื่องช่วยให้คุณแก้ไขข้อบกพร่องในโค้ดได้ง่ายขึ้น เนื่องจากเราเชื่อว่าโค้ดจากขอบเขตภายนอกจะจัดการตัวแปรที่กำหนดขอบเขตเฉพาะเครื่องได้ ซึ่งต่างจากตัวแปรร่วม
  • สร้างโค้ดสั้นๆ ที่นํามาใช้ใหม่ได้: เช่น คุณสามารถเขียนฟังก์ชันล้วนที่ไม่ต้องอาศัยขอบเขตภายนอก คุณสามารถย้ายฟังก์ชันดังกล่าวไปที่อื่นได้อย่างง่ายดายโดยมีการเปลี่ยนแปลงเพียงเล็กน้อย

ขอบเขตคืออะไร

ขอบเขตของตัวแปรเป็นตัวกำหนดว่าคุณสามารถใช้ตัวแปรได้จากที่ใดภายในโค้ด

JavaScript จะกำหนดตัวแปรของขอบเขตรวมหรือขอบเขตภายในเครื่อง ดังนี้

  • ตัวแปรที่มีขอบเขตรวมจะพร้อมใช้งานจากขอบเขตอื่นๆ ทั้งหมดภายในโค้ด JavaScript
  • ตัวแปรที่มีขอบเขตภายในจะใช้ได้เฉพาะในบริบทท้องถิ่นที่ระบุเท่านั้น และสร้างขึ้นโดยคีย์เวิร์ด เช่น var, let และ const หากคุณใช้คีย์เวิร์ด var, let หรือ const เพื่อสร้างตัวแปรภายในฟังก์ชัน ตัวแปรนั้นจะมีขอบเขตภายในเครื่อง

ส่วนถัดไปในบทความนี้จะกล่าวถึงขอบเขตบล็อกและคำศัพท์

  • ตัวแปรขอบเขตการบล็อก จะพร้อมใช้งานภายในสำหรับการบล็อกตามที่ระบุโดยตำแหน่งของวงเล็บปีกกาตรงตำแหน่งที่มีการกำหนดคำสั่งบล็อกไว้ เฉพาะตัวแปรที่ประกาศด้วยคีย์เวิร์ด let หรือ const เท่านั้นที่มีขอบเขตการบล็อก
  • ขอบเขตแบบยืดหยุ่น ใช้ตำแหน่งที่มีการประกาศตัวแปรในซอร์สโค้ดเพื่อกำหนดตำแหน่งที่ใช้ตัวแปรได้ คุณใช้การปิดเพื่อให้สิทธิ์เข้าถึงฟังก์ชันแบบปิดในการเข้าถึงตัวแปรที่อ้างอิงในขอบเขตภายนอกที่เรียกว่าสภาพแวดล้อมแบบคำศัพท์

เมื่อมีการเข้าถึงตัวแปรภายในขอบเขตของตัวแปร JavaScript จะแสดงผลค่าที่กำหนดไว้หรือทำให้เกิดข้อผิดพลาด

วิธีประกาศตัวแปร

  • ใช้คีย์เวิร์ด var, const หรือ let เพื่อประกาศตัวแปรภายในหรือขอบเขตรวม
  • ใช้คีย์เวิร์ด const หรือ let เพื่อประกาศตัวแปรขอบเขตระดับบล็อก

เมื่อคุณประกาศตัวแปร var ในฟังก์ชัน การประกาศจะทำให้ตัวแปรพร้อมใช้งานในฟังก์ชันที่ล้อมรอบที่ใกล้ที่สุด คุณใช้คีย์เวิร์ด var เพื่อประกาศตัวแปรที่มีขอบเขตเป็นบล็อกไม่ได้

ตัวอย่างขอบเขต

ตัวอย่างนี้แสดงขอบเขตรวมเนื่องจากมีการประกาศตัวแปร greeting นอกฟังก์ชันหรือบล็อก ซึ่งทำให้โค้ดทั้งหมดในเอกสารปัจจุบันใช้ค่าได้

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

ในตัวอย่างขอบเขตรวม ตัวแปร greeting จะได้รับการกำหนดค่า hello

ตัวอย่างนี้แสดงขอบเขตภายในเครื่องเนื่องจากประกาศตัวแปร greeting ที่มีคีย์เวิร์ด let ภายในฟังก์ชัน ตัวแปร greeting เป็นตัวแปรที่กำหนดขอบเขตระดับภายในเครื่องและไม่พร้อมใช้งานนอกฟังก์ชัน

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

ตัวอย่างนี้แสดงขอบเขตบล็อกเนื่องจากมีการประกาศตัวแปร greeting ภายในบล็อก เพื่อให้ตัวแปรเข้าถึงได้ภายในวงเล็บปีกกาเท่านั้น

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

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

โปรดสังเกตว่าเมื่อฟังก์ชัน console.log พยายามแสดงผลค่าของตัวแปร greeting JavaScript จะแสดงผลข้อความแสดงข้อผิดพลาด ReferenceError แทนข้อความ hello ที่คาดไว้ เหตุผล

ระบบแสดงผลข้อผิดพลาดเนื่องจากตัวแปร greeting มีขอบเขตการบล็อก และบล็อกที่ใกล้เคียงที่สุดเป็นส่วนหนึ่งของคำสั่งแบบมีเงื่อนไข if คุณจะเข้าถึงตัวแปร let และ const ที่ประกาศไว้ภายในบล็อกจากภายนอกบล็อกไม่ได้ คุณจึงเข้าถึงได้เฉพาะตัวแปร greeting ในวงเล็บปีกกา ซึ่งระบุขอบเขตบล็อกเท่านั้น

ตัวอย่างนี้แก้ไขข้อผิดพลาดเพราะย้ายเมธอด console.log(message) ภายในวงเล็บปีกกา โค้ดที่อัปเดตจะย้ายเมธอด console.log(message) ภายในการบล็อก

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

ประเภทของขอบเขต

ขอบเขตรวม

คุณเข้าถึงตัวแปรที่มีขอบเขตรวมได้จากทุกที่ในโปรแกรม

พิจารณาไฟล์ HTML ที่นำเข้าไฟล์ JavaScript 2 ไฟล์ ได้แก่ file-1.js และ file-2.js

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

ในตัวอย่างนี้ ตัวแปร globalMessage มีขอบเขตรวมและเขียนนอกฟังก์ชัน ระหว่างการเรียกใช้และการดำเนินการ คุณจะเข้าถึงค่าของตัวแปร globalMessage ได้จากทุกที่ในโปรแกรม JavaScript

คุณดูเนื้อหาของไฟล์ file-1.js และ file-2.js ได้ในข้อมูลโค้ดนี้ สังเกตความพร้อมใช้งานของตัวแปร globalMessage ในทั้ง 2 ไฟล์

// 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!

ยังมีขอบเขตอีกประเภทหนึ่งที่ไม่ได้กล่าวถึงมากในบทความนี้ หากสร้างตัวแปรภายในโมดูล JavaScript แต่อยู่นอกฟังก์ชันหรือบล็อก ตัวแปรนั้นจะไม่มีขอบเขตรวมทั้งหมด แต่เป็นขอบเขตของโมดูล ตัวแปรที่มีขอบเขตโมดูลจะมีได้ทุกที่ภายในโมดูลปัจจุบัน แต่จะไม่มีอยู่ในไฟล์หรือโมดูลอื่น หากต้องการให้ตัวแปรที่กําหนดขอบเขตระดับโมดูลใช้ได้กับไฟล์อื่นๆ คุณต้องส่งออกจากโมดูลที่สร้างตัวแปรนั้น แล้วimportจากโมดูลที่ต้องการเข้าถึงตัวแปร

ขอบเขตในเครื่องและขอบเขตฟังก์ชัน

เมื่อคุณสร้างตัวแปรในฟังก์ชัน JavaScript ด้วยคีย์เวิร์ด var, let หรือ const ตัวแปรจะอยู่ในฟังก์ชันนั้น คุณจึงเข้าถึงได้จากภายในฟังก์ชันเท่านั้น ระบบจะสร้างตัวแปรภายในเมื่อฟังก์ชันเริ่มทำงาน และจะถูกลบออกเมื่อการทำงานของฟังก์ชันเสร็จสิ้น

ตัวอย่างนี้ประกาศตัวแปร total ในฟังก์ชัน addNumbers() คุณจะเข้าถึงตัวแปร a, b, และ total ภายในฟังก์ชัน addNumbers() ได้เท่านั้น

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

addNumbers(3, 4);

คุณใช้คีย์เวิร์ด let และ const เพื่อตั้งชื่อตัวแปรได้ JavaScript จะอัปเดตตัวแปรได้เมื่อคุณใช้คีย์เวิร์ด let แต่เมื่อใช้คีย์เวิร์ด const ตัวแปรนี้จะคงตัว

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

ขอบเขตการบล็อก

การบล็อกใช้เพื่อจัดกลุ่มคำสั่งเดี่ยวหรือชุดคำสั่งไว้ด้วยกัน คุณสามารถใช้คีย์เวิร์ด const หรือ let เพื่อประกาศตัวแปรในพื้นที่ของขอบเขตบล็อก โปรดทราบว่าคุณไม่สามารถใช้คีย์เวิร์ด var เพื่อประกาศตัวแปรที่มีขอบเขตบล็อก

เช่น ในบล็อกนี้ ขอบเขตของตัวแปร name และค่า "Elizabeth" จะอยู่ในวงเล็บปีกกา ตัวแปรภายในขอบเขตบล็อกจะไม่สามารถใช้ได้นอกการบล็อก

{
    const name = "Elizabeth";
}

คุณสามารถใช้ตัวแปรที่กําหนดขอบเขตระดับบล็อกภายในคําสั่ง if, for หรือ while

สังเกตการวนซ้ำ for 2 รอบในข้อมูลโค้ดนี้ ลูป for 1 รายการใช้คีย์เวิร์ด var เพื่อประกาศตัวแปรเครื่องมือเริ่มต้น ซึ่งจะเพิ่มขึ้นผ่านตัวเลข 0, 1 และ 2 อีก for ลูปใช้คีย์เวิร์ด let เพื่อประกาศตัวแปรเริ่มต้น

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.

ในตัวอย่างโค้ดก่อนหน้านี้ คุณอาจสังเกตเห็นว่าตัวแปร i ในลูป for ครั้งแรกมีการรั่วไหลภายนอกลูป for และยังคงค่า 2 ไว้ เนื่องจากคีย์เวิร์ด var ไม่ได้ใช้ขอบเขตการบล็อก ปัญหานี้ได้รับการแก้ไขในลูป for ครั้งที่ 2 ซึ่งตัวแปร j ประกาศด้วยคีย์เวิร์ด let ถูกกำหนดขอบเขตไว้ที่บล็อกของลูป for และไม่มีอยู่หลังจากการวนซ้ำ for สิ้นสุดลง

การใช้ชื่อตัวแปรซ้ำในขอบเขตอื่น

ขอบเขตจะแยกตัวแปรภายในฟังก์ชันได้ แม้ว่าคุณจะนำชื่อตัวแปรเดียวกันมาใช้ซ้ำในที่อื่นๆ ในขอบเขตอื่นก็ตาม

ตัวอย่างนี้แสดงให้เห็นว่าการใช้ขอบเขตช่วยให้คุณนำชื่อตัวแปรเดียวกันมาใช้ซ้ำในฟังก์ชันต่างๆ ได้อย่างไร

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

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

listOne();
listTwo();

ระบบจะกําหนดค่าตัวแปร listItems ในฟังก์ชัน listOne() และ listTwo() ตามค่าที่คาดไว้ ดังนั้นจึงไม่ขัดแย้งกัน

การปิดการสนทนาและขอบเขตคำศัพท์

การปิดหมายถึงฟังก์ชันแบบปิด ซึ่งฟังก์ชันภายในสามารถเข้าถึงขอบเขตฟังก์ชันภายนอก หรือที่เรียกว่าสภาพแวดล้อมแบบคำศัพท์ ดังนั้นใน JavaScript คุณใช้การปิดเพื่อให้ฟังก์ชันอ้างอิงสภาพแวดล้อมคำศัพท์ภายนอก ซึ่งจะทำให้โค้ดภายในตัวแปรอ้างอิงฟังก์ชันที่ประกาศนอกฟังก์ชันได้ อันที่จริง คุณสามารถเขียนโค้ดชุดการอ้างอิงไปยังสภาพแวดล้อมคำศัพท์ภายนอกเพื่อให้ฟังก์ชันนั้นเรียกโดยฟังก์ชัน ซึ่งส่งผลให้ฟังก์ชันอื่นเรียกใช้

ในตัวอย่างนี้ โค้ดจะปิดด้วยสภาพแวดล้อมแบบพจนานุกรมซึ่งสร้างขึ้นเมื่อมีการเรียกใช้ฟังก์ชัน outer() ซึ่งปิดทับตัวแปร hello ดังนั้น ตัวแปร hello จึงใช้ภายในฟังก์ชันเรียกกลับของ setTimeout

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

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

outer();

สำหรับขอบเขตคำศัพท์ จะมีการกำหนดขอบเขตระหว่างการคอมไพล์ซอร์สโค้ด ไม่ใช่ที่รันไทม์ หากต้องการเรียนรู้เพิ่มเติมเกี่ยวกับสภาพแวดล้อมแบบคลังบทความ โปรดดูกำหนดขอบเขตและการปิดน้อยที่สุด

โมดูล

โมดูล JavaScript ช่วยในการจัดระเบียบโค้ด JavaScript ในการใช้งานอย่างเหมาะสม แท็กเหล่านี้ให้โครงสร้างที่มีประสิทธิภาพสำหรับฐานของโค้ดและช่วยในการใช้รหัสซ้ำ โมดูล JavaScript มีเทคนิคในการส่งออกและimport แทนที่จะใช้ตัวแปรร่วมเพื่อแชร์ตัวแปรในไฟล์ต่างๆ

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

export { hello };

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

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

การสาธิตเครื่องมือแสดงภาพขอบเขต

ขอบเขตเป็นแนวคิดพื้นฐานที่นักพัฒนาซอฟต์แวร์ JavaScript ทุกคนควรเข้าใจ เพื่อให้เข้าใจระบบขอบเขตได้ดียิ่งขึ้น ให้ลองเขียนโค้ดของคุณเองด้วย JS Scope Visualizer การสาธิตใช้การใส่สีในโค้ดเพื่อช่วยให้เห็นภาพขอบเขต JavaScript

บทสรุป

บทความนี้จะแนะนำขอบเขตประเภทต่างๆ ขอบเขต JavaScript เป็นหนึ่งในแนวคิดขั้นสูงขึ้นภายในการพัฒนาเว็บ การได้อ่านเนื้อหานี้โดยละเอียดและใช้เวลาทำความเข้าใจหัวข้อนี้ได้เป็นอย่างดี

ขอบเขตไม่ใช่ฟีเจอร์ที่แสดงต่อผู้ใช้ การปรับปรุงนี้จะส่งผลต่อนักพัฒนาเว็บที่เขียนโค้ดเท่านั้น แต่ความรู้เกี่ยวกับวิธีการทำงานของขอบเขตจะช่วยให้คุณแก้ไขข้อบกพร่องที่เกิดขึ้นได้