0Pricing
Go Academy · บทเรียน

รูปแบบกลุ่มผู้ทำงาน

สร้างกลุ่มผู้ทำงานกอรูทีนที่มีขนาดคงที่

รูปแบบกลุ่มผู้ทำงาน เป็นบทเรียน Go Academy ฟรีบน CoddyKit นี่คือบทเรียนที่ 4 จากทั้งหมด 4 บทเรียน คุณสามารถอ่านบทเรียนทั้งหมดด้านล่างฟรี — จากนั้นลองปฏิบัติด้วยตัวคุณเองในเบราว์เซอร์พร้อมตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7 บทเรียนนี้เป็นส่วนหนึ่งของเส้นทางการเรียน Go Academy และความก้าวหน้าของคุณจะซิงค์ข้ามเว็บและแอป CoddyKit คอร์ส Go Academy มีบทเรียนทั้งหมด 4 บทเรียน

worker pool คืออะไร

worker pool สร้างโกโรทีนจำนวนคงที่ไว้ล่วงหน้าเพื่อประมวลผลงานจากคิวที่ใช้ร่วมกัน วิธีนี้จำกัดจำนวนงานที่ทำพร้อมกัน และป้องกันการใช้ทรัพยากรจนหมดจากการสร้างโกโรทีนไม่จำกัด

การนำไปใช้งานพื้นฐาน

สร้างช่องสัญญาณ jobs และโกโรทีนจำนวน N ตัวที่อ่านจากช่องสัญญาณนี้ทั้งหมด:

func workerPool(n int, jobs <-chan Job, results chan<- Result) {
    var wg sync.WaitGroup
    for i := 0; i < n; i++ {
        wg.Add(1)
        go func() {
            defer wg.Done()
            for job := range jobs {
                results <- process(job)
            }
        }()
    }
    wg.Wait()
    close(results)
}

การส่งงาน

ส่งงานทั้งหมดไปยังช่องสัญญาณ จากนั้นปิดช่องสัญญาณ worker จะประมวลผลงานทั้งหมดและออกจากลูปการวนอ่านค่าเมื่อช่องสัญญาณถูกปิด

jobs := make(chan Job, 100)
for _, j := range allJobs {
    jobs <- j
}
close(jobs) // signals workers to stop after draining

การรวบรวมผลลัพธ์

อ่านผลลัพธ์ไปพร้อมกับการส่งงาน ใช้โกโรทีนสำหรับ pool เพื่อไม่ให้การรวบรวมผลลัพธ์เกิดการหยุดชะงักกับการส่งงาน

results := make(chan Result, 100)
go workerPool(5, jobs, results)
for r := range results {
    collect(r)
}

การปรับขนาด pool

สำหรับงานที่ใช้ CPU เป็นหลัก ให้กำหนดขนาด pool เป็น runtime.NumCPU() สำหรับงานที่ใช้การรับส่งข้อมูลเป็นหลัก ตัวคูณที่สูงขึ้น (เช่น 10×) จะใช้ประโยชน์จากช่วงเวลาที่ต้องรอได้มากขึ้น ทำ profiling เพื่อหาจุดที่เหมาะสมที่สุด

n := runtime.NumCPU()
if ioHeavy { n = runtime.NumCPU() * 10 }

การเพิ่มการยกเลิกด้วยบริบท

ส่งบริบทไปยัง worker เพื่อให้หยุดทำงานก่อนกำหนดเมื่อมีการยกเลิก:

for {
    select {
    case job, ok := <-jobs:
        if !ok { return }
        results <- process(ctx, job)
    case <-ctx.Done():
        return
    }
}

ทางเลือกแบบ Semaphore

แทนที่จะใช้ pool ของโกโรทีนจำนวนคงที่ ให้ใช้ช่องสัญญาณแบบมีบัฟเฟอร์เป็น semaphore เพื่อจำกัดจำนวนโกโรทีนที่ทำงานพร้อมกัน โดยยังคงสร้างโกโรทีนหนึ่งตัวต่องานได้

sem := make(chan struct{}, 10)
for _, job := range jobs {
    sem <- struct{}{}
    go func(j Job) {
        defer func() { <-sem }()
        process(j)
    }(job)
}

การจัดการข้อผิดพลาด

ส่งข้อผิดพลาดไปพร้อมกับผลลัพธ์โดยใช้โครงสร้างผลลัพธ์ ยกเลิกบริบทเมื่อพบข้อผิดพลาดแรก หรือรวบรวมข้อผิดพลาดทั้งหมดเพื่อรายงานในตอนท้าย

type Result struct{ Val int; Err error }

การปรับขนาด pool แบบไดนามิก

สำหรับ pool ที่ปรับตามสถานการณ์ ให้ใช้ golang.org/x/sync/semaphore ซึ่งอนุญาตให้ขอใช้และคืนทรัพยากรแบบมีน้ำหนักได้ จึงรองรับการจำกัดจำนวนงานที่ทำพร้อมกันแบบไดนามิก

worker pool เทียบกับ errgroup

golang.org/x/sync/errgroup มี API ที่ง่ายกว่าสำหรับการสร้างโกโรทีนจำนวน N ตัวและรวบรวมข้อผิดพลาดแรก ใช้ pool เมื่อจำเป็นต้องมี worker ที่นำกลับมาใช้ซ้ำได้อย่างต่อเนื่อง

การปิดระบบอย่างเรียบร้อย

ปิดช่องสัญญาณ jobs เพื่อส่งสัญญาณให้ worker หยุดทำงาน หลังจาก WaitGroup ทำงานเสร็จแล้ว ให้ปิดผลลัพธ์ การส่งงานที่ค้างอยู่ทั้งหมดต้องเกิดขึ้นก่อน close(jobs)

ตรวจสอบความเข้าใจอย่างรวดเร็ว

worker pool ส่งสัญญาณให้ worker หยุดประมวลผลอย่างไร

ทบทวน: Worker Pool

ประเด็นสำคัญ:

  • โกโรทีนจำนวน N ที่กำหนดไว้ตายตัวอ่านจากช่องสัญญาณ jobs เดียว
  • ปิดช่องสัญญาณ jobs เพื่อส่งสัญญาณให้ worker ทำงานจนเสร็จ
  • WaitGroup ติดตามการทำงานที่เสร็จสิ้น และปิดผลลัพธ์เมื่อเสร็จแล้ว
  • งานที่ใช้ CPU เป็นหลัก: ขนาด pool ใกล้เคียง NumCPU ส่วนงานที่ใช้การรับส่งข้อมูลเป็นหลัก: ใช้ขนาดที่ใหญ่กว่า

คำถามที่พบบ่อย

บทเรียน “รูปแบบกลุ่มผู้ทำงาน” ฟรีหรือไม่

ใช่ — ข้อความเต็มของ “รูปแบบกลุ่มผู้ทำงาน” ฟรีให้อ่านที่นี่บนเว็บ เพื่อปฏิบัติแบบโต้ตอบ (ตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7) และปลดล็อคส่วนที่เหลือของคอร์ส Go Academy ให้อัปเกรดเป็น CoddyKit PRO คอร์ส Go Academy มีบทเรียนทั้งหมด 4 บทเรียน

คุณจะเรียนรู้อะไรในบทเรียน “รูปแบบกลุ่มผู้ทำงาน”

สร้างกลุ่มผู้ทำงานกอรูทีนที่มีขนาดคงที่ คุณปฏิบัติ Go Academy ด้วยโค้ดที่ใช้งานได้จริงที่คุณเรียกใช้โดยตรงในเบราว์เซอร์ และติวเตอร์ AI ตลอด 24/7 ตอบคำถามของคุณขณะที่คุณไปผ่านบทเรียน

คุณต้องมีประสบการณ์ก่อนที่จะเริ่มเรียน Go Academy หรือไม่

ไม่จำเป็นต้องมีประสบการณ์มาก่อน Go Academy บน CoddyKit ออกแบบมาสำหรับผู้เริ่มต้นไปจนถึงผู้เรียนขั้นสูง คุณสามารถเริ่มต้นที่นี่หรือเริ่มจากตัวแรกและเรียนด้วยความเร็วของคุณเอง นี่คือบทเรียนที่ 4 จากทั้งหมด 4 บทเรียน

บทเรียน “รูปแบบกลุ่มผู้ทำงาน” ใช้เวลานานแค่ไหน

บทเรียน CoddyKit ส่วนใหญ่ใช้เวลาประมาณ 5–10 นาที แต่ละบทเรียนจึงสั้นและเป็นแบบโต้ตอบ คุณสามารถก้าวหน้าอย่างต่อเนื่องและกลับมาเรียนต่อจากตรงที่เพิ่งหยุดบนเว็บและแอปได้เลย

ฉันเขียนและรันโค้ดในบทเรียน Go Academy นี้ได้ไหม

ได้ บทเรียน Go Academy ทุกบทมีตัวแก้ไขโค้ดในตัว คุณจึงเขียนและรันโค้ดจริงได้เลยในเบราว์เซอร์ และได้รับข้อเสนอแนะจาก AI ในทันที — ไม่ต้องติดตั้งในเครื่องของคุณ

บทเรียนทั้งหมดในหลักสูตรนี้

  1. คำสั่ง select
  2. การหมดเวลาและตัวนับช่วงเวลา
  3. รูปแบบ Fan-in และ Fan-out
  4. รูปแบบกลุ่มผู้ทำงาน
← กลับไปที่ Go Academy