เอกสารฉบับนี้นำเสนอผลการวิเคราะห์ข้อผิดพลาดของอัลกอริทึมคำนวณทิศทางการเคลื่อนที่ของกลุ่มฝน ในสคริปต์ royalrain.php ซึ่งใช้ภาพเรดาร์ CAPPI ย้อนหลัง 6 เฟรม (ทุก 6 นาที) จากสถานี Rong Kwang เพื่อประกอบการเฝ้าระวังสภาพอากาศบริเวณสนามบินน่าน (VTCN) จากการตรวจสอบพบว่าวิธีเดิมคำนวณทิศทาง โดยมองกลุ่มฝนทั้งภาพเป็น “ก้อนเดียว” ผ่านจุดศูนย์ถ่วงถ่วงน้ำหนัก ซึ่งมีจุดอ่อนสำคัญสามประการ ได้แก่ (1) จุดศูนย์ถ่วงของกลุ่มฝนหลายกลุ่มที่แยกจากกันอาจตกอยู่ในพื้นที่ว่างที่ไม่มีฝนจริง (2) กลุ่มฝนขนาดใหญ่ที่ถูกครอบตัดโดยขอบรัศมีเรดาร์สามารถดึงทิศทางโดยรวมให้คลาดเคลื่อนได้ และ (3) การอ้างอิงตำแหน่งจากเฟรมแรกเพียงเฟรมเดียวทำให้ความคลาดเคลื่อนสะสมในทุกเวกเตอร์ บทความนี้เสนอแนวทางแก้ไขด้วยการติดตามตำแหน่งกลุ่มฝนแยกเป็นรายกลุ่ม (per-cluster tracking) ด้วยเทคนิค local cross-correlation ระหว่างคู่เฟรมที่ติดกัน พร้อมทั้งคัดกรองกลุ่มฝนที่ถูกครอบตัดออกจาก การคำนวณ ผลการทดสอบด้วยภาพจำลองยืนยันว่าวิธีใหม่สามารถระบุทิศทางของแต่ละกลุ่มฝนได้อย่างถูกต้องและ เป็นอิสระต่อกัน โดยไม่ถูกกลุ่มฝนอื่นที่มีน้ำหนักมากกว่ารบกวนผลลัพธ์อีกต่อไป
ระบบ royalrain.php เป็นสคริปต์ประมวลผลภาพเรดาร์ CAPPI (Constant Altitude Plan Position Indicator) ที่ดาวน์โหลดจากสถานีเรดาร์ Rong Kwang ของกรมฝนหลวงและการบินเกษตร (Royal Rainmaking) โดยดึงภาพ ย้อนหลัง 6 เฟรม (ทุก 6 นาที รวมช่วงเวลา 30 นาที) มาวิเคราะห์ตำแหน่งกลุ่มฝนและคำนวณทิศทางการเคลื่อนที่ เพื่อวาดลูกศรกำกับลงบนภาพล่าสุด สำหรับสนับสนุนการเฝ้าระวังสภาพอากาศบริเวณสนามบินน่าน (VTCN) ของกรม อุตุนิยมวิทยา
ในการใช้งานจริงพบว่าลูกศรทิศทางที่ได้บางครั้งชี้ไปยังพื้นที่ที่ไม่มีกลุ่มฝนปรากฏอยู่เลย และทิศทางที่ แสดงไม่สอดคล้องกับการเคลื่อนที่ที่สังเกตได้จริงจากภาพเคลื่อนไหวย้อนหลัง เอกสารฉบับนี้จึงจัดทำขึ้นเพื่อ วิเคราะห์สาเหตุของความคลาดเคลื่อนดังกล่าวอย่างเป็นระบบ และบันทึกแนวทางการปรับปรุงอัลกอริทึมที่ดำเนินการ ไปแล้ว เพื่อเป็นเอกสารอ้างอิงสำหรับการพัฒนาต่อยอดในอนาคต
อัลกอริทึมเดิม (ฟังก์ชัน computeOverallMotion) แปลงแต่ละเฟรมภาพเป็นกริดความเข้มสี โดยกรองเฉพาะ
พิกเซลสี “เหลืองขึ้นไป” (ตัดโทนเขียวซึ่งหมายถึงฝนเบาออก) จากนั้นหาจุดที่นิ่งสนิททุกเฟรม (ถือเป็น legend
หรือลายน้ำที่ฝังอยู่ในภาพ) มากันออกจากการคำนวณ ขั้นตอนสำคัญคือการหา “จุดศูนย์ถ่วงถ่วงน้ำหนัก” (weighted
centroid) ของพิกเซลฝนทั้งหมดในภาพต่อเฟรม โดยไม่แยกว่าพิกเซลนั้นอยู่กลุ่มฝนก้อนใด แล้วสร้างเวกเตอร์จาก
จุดศูนย์ถ่วงของเฟรมแรก (เวลาช้าที่สุด) ไปยังจุดศูนย์ถ่วงของแต่ละเฟรมที่เหลือ ก่อนเฉลี่ยเวกเตอร์ทั้งหมด
เป็นทิศทางเดียว แล้วนำทิศทางเดียวกันนี้ไปวาดลูกศรกำกับที่ทุกกลุ่มฝนที่ตรวจพบในเฟรมล่าสุด
จากตัวอย่างการประมวลผลภาพชุดวันที่ 17 สิงหาคม 2569 เวลา 13:00–13:30 น. ซึ่งปรากฏกลุ่มฝนที่แยกจากกัน อย่างชัดเจนอย่างน้อย 3 บริเวณ (แถบเหนือ-ตะวันตกใกล้พะเยา บริเวณกลางใกล้แพร่/น่าน และกลุ่มฝนขนาดใหญ่ ความเข้มสูงใกล้ตาก-กำแพงเพชรซึ่งอยู่ชิดขอบรัศมีการตรวจของเรดาร์) ผลลัพธ์จากอัลกอริทึมเดิมแสดงลูกศร เพียงลูกเดียว อยู่ในพื้นที่ว่างระหว่างจังหวัดอุตรดิตถ์และเลยซึ่งไม่มีฝนปรากฏอยู่เลย และทิศทางที่ได้ไม่ตรงกับ แนวโน้มการเคลื่อนตัวจริงของกลุ่มฝนกลุ่มใดในภาพ ดังแสดงแนวคิดของปัญหาในรูปที่ 1 (ฝั่งซ้าย)
เมื่อภาพมีกลุ่มฝนที่แยกจากกันทางกายภาพหลายกลุ่ม จุดศูนย์ถ่วงถ่วงน้ำหนักของพิกเซลฝนทั้งหมดรวมกัน มีลักษณะเดียวกับจุดศูนย์ถ่วงของมวลหลายก้อนที่แยกกัน ซึ่งโดยทั่วไปจะตกอยู่ "ระหว่าง" มวลเหล่านั้น ไม่ใช่ บนมวลก้อนใดก้อนหนึ่ง ดังนั้นเมื่ออัลกอริทึมเดิมใช้ตำแหน่งนี้เป็นจุดเริ่มวาดลูกศร (ในกรณีที่ไม่พบกลุ่มฝนที่ ผ่านเกณฑ์การตรวจจับ) จึงมีโอกาสสูงที่ลูกศรจะปรากฏในพื้นที่ที่ไม่มีฝนอยู่จริง
กลุ่มฝนที่มีน้ำหนัก (ขนาดพื้นที่คูณความเข้มสี) สูงกว่ากลุ่มอื่นอย่างมีนัยสำคัญ จะมีอิทธิพลต่อจุดศูนย์ถ่วง รวมมากกว่าสัดส่วนที่ควรจะเป็น หากกลุ่มดังกล่าวตั้งอยู่ใกล้ขอบรัศมีการตรวจจับของเรดาร์ (ในกรณีศึกษานี้คือ รัศมี 240 กิโลเมตร) พื้นที่ที่มองเห็นได้ของกลุ่มนั้นจะเปลี่ยนแปลงไปตามการครอบตัดของขอบเขตวงกลม ซึ่งเป็น ผลจากมุมมองของเรดาร์ ไม่ใช่การเคลื่อนที่จริงของกลุ่มฝน การเปลี่ยนแปลงนี้ทำให้จุดศูนย์ถ่วงรวม "ขยับ" ไปใน ทิศทางที่ไม่เกี่ยวข้องกับการเคลื่อนตัวจริงของกลุ่มฝนกลุ่มใดเลย
วิธีเดิมสร้างเวกเตอร์การเคลื่อนที่โดยอ้างอิงจากจุดศูนย์ถ่วงของเฟรมแรก (เวลาช้าที่สุด) เพียงเฟรมเดียว เป็นจุดตั้งต้นของทุกเวกเตอร์ หากเฟรมแรกมีองค์ประกอบน้ำหนักที่ผิดปกติ (เช่น กลุ่มฝนหนึ่งเพิ่งก่อตัวหรือ สลายตัวพอดีในช่วงเวลานั้น) ความคลาดเคลื่อนจะติดไปกับทุกเวกเตอร์ที่คำนวณต่อจากนั้นทั้งหมด ต่างจากวิธี มาตรฐานที่ใช้ผลต่างตำแหน่งระหว่างเฟรมที่ติดกัน (frame-to-frame) ซึ่งจะลดทอนผลกระทบของเฟรมผิดปกติ เฟรมใดเฟรมหนึ่งได้ดีกว่า เนื่องจากความคลาดเคลื่อนจะจำกัดอยู่เฉพาะคู่เฟรมที่เกี่ยวข้องเท่านั้น
แนวทางแก้ไขหลักคือการเปลี่ยนจากการคำนวณทิศทาง "รวมทั้งภาพเป็นก้อนเดียว" มาเป็นการติดตามและคำนวณ ทิศทางของ "แต่ละกลุ่มฝนแยกจากกัน" โดยหลังจากแยกกลุ่มฝนด้วยเทคนิค connected component ในเฟรมล่าสุด แล้ว จะกำหนดพื้นที่ค้นหา (search region) รอบขอบเขตของกลุ่มนั้น ขยายด้วยระยะขอบ (margin) จากนั้นใช้ เทคนิค local cross-correlation เปรียบเทียบกริดความเข้มสีระหว่างคู่เฟรมที่ติดกันทุกคู่ ภายในพื้นที่ค้นหานั้น เพื่อหาการเลื่อนตำแหน่ง (shift) ที่ทำให้รูปแบบสองเฟรมสอดคล้องกันมากที่สุด ดังแสดงในรูปที่ 2
การเลื่อนตำแหน่งที่ได้จากแต่ละคู่เฟรมจะถูกแปลงเป็น "ความเร็ว" โดยหารด้วยผลต่างเวลาจริงระหว่างสองเฟรม นั้น (หน่วยช่องกริดต่อนาที) ก่อนนำความเร็วจากทุกคู่เฟรมมาเฉลี่ยรวมเป็นเวกเตอร์เดียวสำหรับกลุ่มฝนนั้น วิธีนี้ช่วยลดผลกระทบจากความคลาดเคลื่อนของเฟรมใดเฟรมหนึ่ง เนื่องจากใช้ข้อมูลจากคู่เฟรมที่ติดกันหลายคู่ แทนที่จะยึดจุดอ้างอิงตายตัวเพียงจุดเดียวตามที่กล่าวถึงในหัวข้อ 3.3
กลุ่มฝนที่มีขอบเขต (bounding box) สัมผัสขอบของกริดภาพ ถือว่ามีความเสี่ยงสูงที่จะถูกครอบตัดโดยขอบเขต รัศมีการตรวจจับของเรดาร์ อัลกอริทึมที่ปรับปรุงแล้วจะไม่คำนวณทิศทางให้กลุ่มลักษณะนี้ และจะไม่วาดลูกศร กำกับ เนื่องจากพื้นที่ที่มองเห็นได้ของกลุ่มดังกล่าวเปลี่ยนแปลงจากการครอบตัด ไม่ใช่จากการเคลื่อนที่จริง ทำให้ผลการติดตามไม่น่าเชื่อถือ อีกทั้งกลุ่มลักษณะนี้จะถูกตัดออกจากการคำนวณทิศทางสรุป (ค่าเฉลี่ยถ่วงน้ำหนัก สำหรับแสดงเป็นข้อความ) ด้วยเช่นกัน ซึ่งแก้ปัญหาที่ระบุไว้ในหัวข้อ 3.2 ได้โดยตรง
ภาพรวมของขั้นตอนการทำงานทั้งหมดหลังการปรับปรุง แสดงในรูปที่ 3
ระหว่างการทดสอบการติดตามแบบแยกรายกลุ่มด้วยภาพจำลอง พบปัญหาความเสถียรของฟังก์ชันจับคู่รูปแบบ
(bestShiftInRegion) ซึ่งเดิมกำหนดเกณฑ์ "จำนวนช่องซ้อนทับขั้นต่ำ" (minimum overlap) โดยอิงกับขนาด
ของกลุ่มฝนเท่านั้น เมื่อนำมาใช้กับพื้นที่ค้นหาที่จำกัดเฉพาะรอบกลุ่ม (แคบกว่าภาพเต็มมาก) พบว่าการเลื่อน
ตำแหน่งที่ผิดพลาด ซึ่งเหลือพื้นที่เปรียบเทียบจริงเพียงเล็กน้อยบริเวณขอบภาพ (ส่วนใหญ่เป็นพื้นหลังว่างที่
เหมือนกันทั้งสองเฟรมโดยบังเอิญ) สามารถได้คะแนนความคลาดเคลื่อนต่ำกว่าการเลื่อนตำแหน่งที่ถูกต้องจริง
เนื่องจากเปรียบเทียบกันด้วยจำนวนจุดข้อมูลที่น้อยเกินไป ดังแสดงแนวคิดในรูปที่ 4
แนวทางแก้ไขคือปรับเกณฑ์จำนวนช่องซ้อนทับขั้นต่ำให้อิงกับ "จำนวนช่องที่ไม่ถูกมาสก์จริงในพื้นที่ค้นหา" (คำนวณที่การเลื่อน = 0 เป็นเส้นฐาน) แทนที่จะใช้สัดส่วนคงที่ของขนาดกลุ่มฝนหรือขนาดพื้นที่ค้นหาดิบ เนื่องจากบางส่วนของพื้นที่ค้นหาอาจถูกมาสก์ออกอย่างถูกต้องแล้วตั้งแต่ขั้นตอนก่อนหน้า (เช่น แกนกลางของ กลุ่มฝนที่มีความเข้มสีคงที่ไม่เปลี่ยนแปลงระหว่างเฟรม ซึ่งถูกจัดเป็น "จุดนิ่ง" เช่นเดียวกับลายน้ำ) การใช้ เส้นฐานนี้ทำให้เกณฑ์ปรับตัวตามลักษณะข้อมูลจริงของแต่ละกลุ่มโดยอัตโนมัติ
เนื่องจากไม่สามารถเข้าถึงเซิร์ฟเวอร์ต้นทาง (file.royalrain.go.th) จากสภาพแวดล้อมที่ใช้พัฒนาได้โดยตรง การทดสอบจึงดำเนินการด้วยภาพจำลอง (synthetic CAPPI-like frames) ที่สร้างขึ้นให้มีคุณสมบัติใกล้เคียงกับ สถานการณ์จริงที่พบปัญหา จำนวน 2 ชุดทดสอบ ดังสรุปในตารางที่ 1
| ชุดทดสอบ | สถานการณ์จำลอง | ผลที่คาดหวัง | ผลที่ได้จริง |
|---|---|---|---|
| 1 | กลุ่มฝน 2 กลุ่มแยกกันอย่างชัดเจน เคลื่อนที่คนละทิศทาง (กลุ่ม A ไปทางตะวันออกเฉียงใต้ กลุ่ม B ไปทางตะวันตก) | แต่ละกลุ่มควรได้ทิศทางของตนเอง ไม่เท่ากัน | กลุ่ม A = 123.7° (SE) กลุ่ม B = 285.9° (W) ตรงตามที่กำหนด |
| 2 | กลุ่มขนาดใหญ่ น้ำหนักสูง ชิดขอบภาพ (จำลองการครอบตัด) คู่กับกลุ่มขนาดเล็กที่เคลื่อนที่จริงไปทางตะวันออก | กลุ่มชิดขอบต้องไม่มีทิศทาง และไม่รบกวนทิศทางสรุป | กลุ่มชิดขอบ: bearing = null (ไม่วาดลูกศร) กลุ่มปกติ = 90° (E) ตรงตามที่กำหนด ทิศทางสรุป = 90° (ไม่ถูกกลุ่มชิดขอบรบกวน) |
ผลการทดสอบทั้งสองชุดยืนยันว่าอัลกอริทึมที่ปรับปรุงแล้วสามารถ (1) ระบุทิศทางที่แตกต่างกันของกลุ่มฝน แต่ละกลุ่มได้อย่างถูกต้องและเป็นอิสระต่อกัน และ (2) ป้องกันไม่ให้กลุ่มฝนที่ถูกครอบตัดโดยขอบภาพ ซึ่งมัก มีน้ำหนักสูงกว่ากลุ่มอื่น เข้ามารบกวนผลการคำนวณทิศทางของกลุ่มอื่นหรือทิศทางสรุปโดยรวม ซึ่งตรงกับสาเหตุ หลักที่วิเคราะห์ไว้ในหัวข้อที่ 3
นอกจากนี้ยังตรวจสอบความถูกต้องทางไวยากรณ์ของโค้ด (PHP syntax) ด้วยคำสั่ง php -l
ซึ่งไม่พบข้อผิดพลาด
การวิเคราะห์นี้ชี้ให้เห็นว่าการมองกลุ่มฝนที่แยกกันทางกายภาพเป็น "ก้อนเดียว" สำหรับคำนวณทิศทางการ เคลื่อนที่ เป็นสมมติฐานที่ไม่สอดคล้องกับลักษณะข้อมูลจริงของภาพเรดาร์ที่มักปรากฏกลุ่มฝนหลายกลุ่มพร้อมกัน การเปลี่ยนมาใช้การติดตามแยกรายกลุ่มด้วยเทคนิค local cross-correlation ร่วมกับการคัดกรองกลุ่มที่ถูก ครอบตัดโดยขอบเรดาร์ออกจากการคำนวณ สามารถแก้ปัญหาหลักที่พบได้ทั้งในเชิงทฤษฎีและผลการทดสอบ
ข้อเสนอแนะสำหรับการพัฒนาต่อยอด มีดังนี้
datetime_bangkok ที่ได้จาก API กับเวลาที่ปรากฏบน legend ของภาพต้นฉบับ ซึ่งพบส่วนต่างคงที่ประมาณ 7 ชั่วโมงในการสังเกตเบื้องต้น อันเป็นประเด็นแยกจากการคำนวณทิศทางที่กล่าวถึงในเอกสารนี้