งูต้นฉบับกำลังปล่อยเมล็ดผ่านผืนผ้าทรงโค้งให้กองหนาแน่นตรงกลางและบางลงสองด้าน

Python NormalDist: แปลงค่าเฉลี่ยกับส่วนเบี่ยงเบนเป็น threshold ที่อธิบายได้

พี่โชว์Engineering

การตั้ง alert ที่ “ค่าเฉลี่ยบวกสองเท่าของส่วนเบี่ยงเบนมาตรฐาน” มักถูกคัดลอกมาโดยไม่รู้ว่าครอบคลุมความน่าจะเป็นเท่าไรครับ statistics.NormalDist ทำให้สมมติฐานนั้นเป็น object และแปลงระหว่างค่า, percentile และ probability ได้ด้วย standard library

เปรียบเหมือนกองเมล็ดที่หนาตรงกลางและบางลงสองข้าง เราเลือกเส้นกั้นจากสัดส่วนที่ยอมให้ล้น แทนเดาตำแหน่งเส้นด้วยความรู้สึก

import unittest
from statistics import NormalDist


def upper_threshold(mean: float, stdev: float, percentile: float) -> float:
    if not 0.0 < percentile < 1.0:
        raise ValueError("percentile must be between zero and one")
    return NormalDist(mu=mean, sigma=stdev).inv_cdf(percentile)


class NormalDistTests(unittest.TestCase):
    def test_percentile_and_probability_are_inverse(self):
        latency = NormalDist(mu=120.0, sigma=15.0)
        threshold = upper_threshold(120.0, 15.0, 0.95)
        self.assertAlmostEqual(latency.cdf(threshold), 0.95, places=10)
        self.assertGreater(threshold, latency.mean)

    def test_invalid_percentile_is_rejected(self):
        with self.assertRaises(ValueError):
            upper_threshold(10.0, 2.0, 1.0)


if __name__ == "__main__":
    unittest.main()

สูตรถูกได้ แต่ model ผิดได้

cdf(x) ตอบโอกาสที่ค่าจะไม่เกิน x; inv_cdf(p) ตอบค่าที่ percentile p หากข้อมูลเป็น normal distribution ตาม mu และ sigma ที่ให้ แต่ latency, queue depth และยอดขายมักเอียงขวา มี outlier หรือเปลี่ยน regime ตามเวลา การใช้ NormalDist ไม่ได้ทำให้ข้อมูลจริงเป็นโค้งปกติ

ก่อนใช้ threshold ให้ดู histogram/quantile จริง แยกช่วงเวลาที่ workload ต่างกัน และวัด false positive/false negative หาก sample น้อยหรือ tail สำคัญ ใช้ empirical percentile อาจตรงกว่า ส่วน NormalDist.from_samples เหมาะกับการประมาณจากตัวอย่างเมื่อยอมรับข้อจำกัดเรื่อง sampling แล้ว อย่าส่ง sigma=0 เข้า calculation ที่ต้องหารด้วยส่วนเบี่ยงเบน และอย่าแปล percentile เป็น SLA โดยไม่มี business context

Recap

  • ใช้ inv_cdf เพื่อคำนวณ threshold จาก percentile ที่ต้องการ
  • ใช้ cdf ตรวจ probability ของค่าที่สังเกต
  • ตรวจรูป distribution จริงก่อนสมมติว่าเป็น normal
  • ติดตาม error rate หลังนำ threshold ไปใช้