ฟังก์ชันเรียกกลับใน JavaScript คืออะไร?

บทความนี้ให้ข้อมูลเบื้องต้นสั้น ๆ เกี่ยวกับแนวคิดและการใช้ฟังก์ชันเรียกกลับในภาษาโปรแกรม JavaScript

ฟังก์ชั่นคือวัตถุ

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

ฟังก์ชันการโทรกลับ

ฟังก์ชันการเรียกกลับเป็นฟังก์ชั่นที่ถูกส่งผ่านเป็นอาร์กิวเมนต์ฟังก์ชั่นอื่นที่จะ“เรียกว่ากลับมา” ในเวลาต่อมา ฟังก์ชันที่รับฟังก์ชันอื่นเป็นอาร์กิวเมนต์เรียกว่าฟังก์ชันลำดับที่สูงกว่าซึ่งมีตรรกะเมื่อฟังก์ชันเรียกกลับถูกเรียกใช้งาน เป็นการรวมกันของสองสิ่งนี้ที่ทำให้เราสามารถขยายฟังก์ชันการทำงานของเราได้

เพื่อแสดงให้เห็นถึงการเรียกกลับเรามาเริ่มจากตัวอย่างง่ายๆ:

function createQuote(quote, callback){ var myQuote = "Like I always say, " + quote; callback(myQuote); // 2 } function logQuote(quote){ console.log(quote); } createQuote("eat your vegetables!", logQuote); // 1 // Result in console: // Like I always say, eat your vegetables!

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

นอกจากนี้เรายังต้องให้แน่ใจว่าถ้าฟังก์ชันการเรียกกลับเราผ่านในการขัดแย้งคาดว่าเราจัดหาข้อโต้แย้งเหล่านั้นเมื่อมีการดำเนินการเรียกกลับ(2) ในตัวอย่างข้างต้นนั่นจะเป็นcallback(myQuote);คำสั่งเนื่องจากเรารู้ว่าlogQuoteคาดว่าจะมีการส่งใบเสนอราคา

นอกจากนี้เราสามารถส่งผ่านฟังก์ชันที่ไม่ระบุชื่อเป็นการโทรกลับ คำเรียกร้องด้านล่างcreateQuoteจะให้ผลลัพธ์เช่นเดียวกับตัวอย่างด้านบน

createQuote("eat your vegetables!", function(quote){ console.log(quote); });

อนึ่งคุณไม่จำเป็นต้องใช้คำว่า "callback" เป็นชื่ออาร์กิวเมนต์ของคุณ Javascript เพียงแค่ต้องรู้ว่าเป็นชื่ออาร์กิวเมนต์ที่ถูกต้อง จากตัวอย่างข้างต้นฟังก์ชันด้านล่างจะทำงานในลักษณะเดียวกันทุกประการ

function createQuote(quote, functionToCall) { var myQuote = "Like I always say, " + quote; functionToCall(myQuote); }

เหตุใดจึงต้องใช้ฟังก์ชันโทรกลับ

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

ลองดูตัวอย่างที่จำลองการร้องขอไปยังเซิร์ฟเวอร์:

function serverRequest(query, callback){ setTimeout(function(){ var response = query + "full!"; callback(response); },5000); } function getResults(results){ console.log("Response from the server: " + results); } serverRequest("The glass is half ", getResults); // Result in console after 5 second delay: // Response from the server: The glass is half full!

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

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