การจำกัดความเร็ว Goroutine
ควบคุมการทำงานพร้อมกัน
การจำกัดความเร็ว Goroutine เป็นบทเรียน Go Academy ฟรีบน CoddyKit นี่คือบทเรียนที่ 3 จากทั้งหมด 4 บทเรียน คุณสามารถอ่านบทเรียนทั้งหมดด้านล่างฟรี — จากนั้นลองปฏิบัติด้วยตัวคุณเองในเบราว์เซอร์พร้อมตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7 บทเรียนนี้เป็นส่วนหนึ่งของเส้นทางการเรียน Go Academy และความก้าวหน้าของคุณจะซิงค์ข้ามเว็บและแอป CoddyKit คอร์ส Go Academy มีบทเรียนทั้งหมด 4 บทเรียน
การจำกัดการทำงานพร้อมกัน
บางครั้งคุณไม่ได้จำกัดจำนวนการทำงานต่อวินาที แต่จำกัดจำนวนกอรูทีนที่ทำงาน พร้อมกัน วิธีนี้จำกัดภาระที่เกิดขึ้นพร้อมกันบนทรัพยากรโดยไม่ขึ้นกับจังหวะเวลา
- จำกัดการทำงานแบบขนาน
- ปกป้องพูลการเชื่อมต่อ
- ป้องกันการใช้หน่วยความจำพุ่งสูง
แชนเนลเซมาฟอร์
แชนเนลที่มีบัฟเฟอร์ทำหน้าที่เป็นเซมาฟอร์แบบนับจำนวน ความจุของแชนเนลเท่ากับจำนวนการทำงานพร้อมกันสูงสุด การขอสิทธิ์จะส่งโทเค็นเข้าไป ส่วนการคืนสิทธิ์จะรับโทเค็นออกมา
sem := make(chan struct{}, 3)การขอและคืนสิทธิ์
ก่อนเริ่มงาน ให้ส่งค่าเข้าแชนเนลเพื่อขอช่องว่าง หากแชนเนลเต็ม การดำเนินการจะรอค้าง เมื่อทำงานเสร็จ ให้รับค่าออกมาเพื่อคืนช่องว่างและเปิดช่องให้กอรูทีนอื่น
sem <- struct{}{} // acquire
// do work
<-sem // releaseเหตุใดจึงใช้ struct{}
โครงสร้างว่าง struct{}{} ใช้หน่วยความจำเป็นศูนย์ไบต์ การใช้โครงสร้างนี้เป็นชนิดข้อมูลของแชนเนลทำให้เซมาฟอร์เป็นเพียงสัญญาณ โดยไม่สิ้นเปลืองหน่วยความจำ
การจำกัดการทำงานในลูป
เปิดใช้กอรูทีนหนึ่งตัวต่องาน แต่ให้แต่ละตัวต้องผ่านเซมาฟอร์ก่อน อย่างมาก cap กอรูทีนเท่านั้นที่ทำงานจริงพร้อมกัน ส่วนที่เหลือจะรอค้างตอนขอสิทธิ์
for _, task := range tasks {
sem <- struct{}{}
go func(t Task) {
defer func() { <-sem }()
process(t)
}(t)
}การใช้ร่วมกับ WaitGroup
เซมาฟอร์จำกัดจำนวนการทำงานพร้อมกัน แต่ไม่ได้บอกว่าทุกอย่างเสร็จสิ้นเมื่อใด ให้ใช้ร่วมกับ sync.WaitGroup เพื่อรอให้งานทั้งหมดเสร็จ
var wg sync.WaitGroup
wg.Add(1)
go func() {
defer wg.Done()
defer func() { <-sem }()
process(t)
}()คืนสิทธิ์ใน defer
คืนสิทธิ์ใน defer เสมอ เพื่อให้ช่องว่างถูกคืนแม้งานจะเกิดแพนิกหรือจบการทำงานก่อนกำหนด หากลืมคืนสิทธิ์ ช่องว่างจะรั่วไหลและทำให้ผู้ขอสิทธิ์รายใหม่ติดตายได้ในที่สุด
การทำงานแบบจำกัดพร้อมกันครบถ้วน
โปรแกรมนี้ทำงานทั้งหมดแปดงาน โดยให้ทำงานพร้อมกันได้อย่างมากสองงาน และพิมพ์จุดเริ่มต้นกับจุดสิ้นสุดเพื่อแสดงให้เห็นการจำกัดนี้
package main
import (
"fmt"
"sync"
"time"
)
func main() {
sem := make(chan struct{}, 2)
var wg sync.WaitGroup
for i := 0; i < 8; i++ {
wg.Add(1)
sem <- struct{}{}
go func(id int) {
defer wg.Done()
defer func() { <-sem }()
fmt.Println("start", id)
time.Sleep(20 * time.Millisecond)
fmt.Println("end", id)
}(i)
}
wg.Wait()
fmt.Println("done")
}errgroup พร้อม SetLimit
แพ็กเกจ golang.org/x/sync/errgroup มี SetLimit สำหรับจำกัดกลุ่มและส่งต่อข้อผิดพลาดแรก วิธีนี้เหมาะเป็นทางเลือกที่เรียบง่ายกว่าในหลายกรณี แต่เป็นแพ็กเกจภายนอก
การจำกัดการทำงานเทียบกับพูลกอรูทีน
พูลกอรูทีนใช้กอรูทีนจำนวนคงที่ซ้ำเดิม โดยดึงงานจากคิวมาทำ การจำกัดด้วยเซมาฟอร์จะสร้างกอรูทีนหนึ่งตัวต่องาน แต่จำกัดจำนวนตัวที่ทำงานอยู่ พูลใช้ทรัพยากรน้อยกว่าสำหรับงานจำนวนมหาศาล ส่วนเซมาฟอร์เพิ่มเข้ากับโค้ดเดิมได้ง่ายกว่า
การเลือกขีดจำกัด
สำหรับการเรียกฐานข้อมูล ให้ตั้งขีดจำกัดไม่เกินขนาดพูลการเชื่อมต่อ สำหรับ HTTP ขาออก ให้สอดคล้องกับขีดจำกัดการเชื่อมต่อของโฮสต์ ค่าสูงเกินไปทำให้ทรัพยากรหมด ส่วนค่าต่ำเกินไปทำให้ใช้ความสามารถไม่เต็มที่
ตรวจสอบอย่างรวดเร็ว
ทดสอบความรู้เกี่ยวกับการจำกัดการทำงานของคุณ
สรุป
คุณได้เรียนรู้การจำกัดการทำงานของกอรูทีน:
- แชนเนลที่มีบัฟเฟอร์ทำหน้าที่เป็นเซมาฟอร์แบบนับจำนวน
- ขอสิทธิ์ด้วยการส่ง และคืนสิทธิ์ด้วยการรับใน defer
- สมาชิกชนิด struct{} ใช้หน่วยความจำเป็นศูนย์ไบต์
- ใช้ร่วมกับ WaitGroup เพื่อรอให้งานเสร็จ
- กำหนดขนาดขีดจำกัดให้เหมาะกับทรัพยากรที่ต้องปกป้อง
เรียนรู้ Go ด้วย AI tutor — ฟรี
เขียนและเรียกใช้โค้ดจริงในเบราว์เซอร์ของคุณ รับความช่วยเหลือทันทีจาก AI tutor 24/7 และเรียนรู้ต่อจากที่คุณหยุดบนเว็บหรือในแอป
- คอร์ส
- 51
- บทเรียน
- 203
คำถามที่พบบ่อย
บทเรียน “การจำกัดความเร็ว Goroutine” ฟรีหรือไม่
ใช่ — ข้อความเต็มของ “การจำกัดความเร็ว Goroutine” ฟรีให้อ่านที่นี่บนเว็บ เพื่อปฏิบัติแบบโต้ตอบ (ตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7) และปลดล็อคส่วนที่เหลือของคอร์ส Go Academy ให้อัปเกรดเป็น CoddyKit PRO คอร์ส Go Academy มีบทเรียนทั้งหมด 4 บทเรียน
คุณจะเรียนรู้อะไรในบทเรียน “การจำกัดความเร็ว Goroutine”
ควบคุมการทำงานพร้อมกัน คุณปฏิบัติ Go Academy ด้วยโค้ดที่ใช้งานได้จริงที่คุณเรียกใช้โดยตรงในเบราว์เซอร์ และติวเตอร์ AI ตลอด 24/7 ตอบคำถามของคุณขณะที่คุณไปผ่านบทเรียน
คุณต้องมีประสบการณ์ก่อนที่จะเริ่มเรียน Go Academy หรือไม่
ไม่จำเป็นต้องมีประสบการณ์มาก่อน Go Academy บน CoddyKit ออกแบบมาสำหรับผู้เริ่มต้นไปจนถึงผู้เรียนขั้นสูง คุณสามารถเริ่มต้นที่นี่หรือเริ่มจากตัวแรกและเรียนด้วยความเร็วของคุณเอง นี่คือบทเรียนที่ 3 จากทั้งหมด 4 บทเรียน
บทเรียน “การจำกัดความเร็ว Goroutine” ใช้เวลานานแค่ไหน
บทเรียน CoddyKit ส่วนใหญ่ใช้เวลาประมาณ 5–10 นาที แต่ละบทเรียนจึงสั้นและเป็นแบบโต้ตอบ คุณสามารถก้าวหน้าอย่างต่อเนื่องและกลับมาเรียนต่อจากตรงที่เพิ่งหยุดบนเว็บและแอปได้เลย
ฉันเขียนและรันโค้ดในบทเรียน Go Academy นี้ได้ไหม
ได้ บทเรียน Go Academy ทุกบทมีตัวแก้ไขโค้ดในตัว คุณจึงเขียนและรันโค้ดจริงได้เลยในเบราว์เซอร์ และได้รับข้อเสนอแนะจาก AI ในทันที — ไม่ต้องติดตั้งในเครื่องของคุณ
บทเรียนทั้งหมดในหลักสูตรนี้
- แนวคิดบักเก็ตโทเค็น
- golang.org/x/time/rate
- การจำกัดความเร็ว Goroutine
- การหน่วงเวลาและลองใหม่