#faq#rounding#decimal#gl#vat
ระบบปัดเศษทศนิยมเงินอย่างไร ทำไมยอดต่างกัน 0.01
ตอบสั้น: เงินทุกยอดคำนวณด้วย big.Rat และเก็บเป็นข้อความทศนิยม ไม่ใช้ float มีวิธีปัด 3 แบบ ใช้ต่างจุดกัน คือ ปัดครึ่งขึ้น, _round ของ C# ตาม round_type และ Math.Round แบบ ToEven ยอดต่าง 0.01 มักเกิดจากการปัดรายบรรทัดแล้วรวม เทียบกับรวมก่อนแล้วปัด
รายละเอียด
ค่าเงินจากจอ/DB แปลงด้วย ParseDecimalRat / numericToRat แล้วจัดรูปเป็นข้อความด้วย FormatRat ซึ่งปัดครึ่งขึ้นที่ scale ที่ส่งมา ดู การปัดเศษ ทศนิยม และตัวเลขเงิน (Rounding & Decimal Policy)
จำนวนทศนิยม (scale)
- ยอดในเอกสาร ใช้
erp_option.item_amount_decimal(erp_option — ตัวเลือกระบบ (สวิตช์ + ทศนิยมของบริษัท)) - GL ตามรูปแบบเอกสาร ใช้
gl_no_decimalถ้าว่างใช้ '2' (glSQLOptions) - GL เส้นมาตรฐาน ตรวจสมดุลที่ 2 ตำแหน่งตายตัว (
ValidateAndBalanceJournal(lines, 2))
วิธีปัด
| ฟังก์ชัน | ปัดแบบ | ใช้ที่ |
|---|---|---|
RoundHalfUp |
ครึ่งขึ้น (ห่างจากศูนย์) | FormatRat, GL มาตรฐาน, ยอดชำระ, มัดจำ, ค่าเสื่อม |
smlRound |
round_type = 1 คือครึ่งขึ้น (+0.000001), ค่าอื่นปัดไล่ทีละหลัก เช่น 3.7449 → 3.745 → 3.75 |
ยอดในตารางสินค้า, ยอดแปลงสกุลเงิน (เอกสารสกุลเงินต่างประเทศคำนวณและลงบัญชีกำไร/ขาดทุนอัตราแลกเปลี่ยนอย่างไร) |
roundHalfEven |
ครึ่งไปเลขคู่ (C# Math.Round) | sum_amount_exclude_vat (เฉพาะ vat_type 1 และ tax_type 0), GL ตามรูปแบบ, VAT ขายสินทรัพย์ |
csRound |
สำเนาของ _round ในงาน rebuild สต็อก |
stock_rebuild.go |
ผลต่างจากการปัด
- GL ตามรูปแบบ (ตั้งรูปแบบการลงบัญชี (GL) ในรูปแบบเอกสารยังไง และระบบใช้เมื่อไร):
addDiffยอมผลต่าง Dr−Cr ได้ไม่เกิน 0.1 ต่อแถวรายละเอียด แล้วลงบัญชีผลต่างที่กำหนดด้วย action 90 ของรูปแบบ - GL เส้นมาตรฐาน: ไม่มีบรรทัดผลต่าง ถ้าปัดแต่ละบรรทัดแล้ว Dr ≠ Cr จะถูกปฏิเสธ (
ErrUnbalancedJournal) ดู บันทึกเอกสารแล้วขึ้น GL ไม่สมดุล (debit credit do not balance) แก้ยังไง - ฝั่งจอแสดงผลใช้
getSmlDecimals/formatMoneyDisplay
ข้อควรระวัง
sum_of_cost(qty × cost) ปัด 2 ตำแหน่งตายตัว ไม่ใช้item_amount_decimal(trans.go:1058)round_typeที่ไม่ใช่ 1 ทุกค่าจะปัดไล่หลัก (grid_calc.go:99) ค่า −1 (roundHalfUpType) ใช้ภายในโค้ดเท่านั้น- งาน rebuild สต็อกใช้ VAT 7% ตายตัว (
stock_rebuild.go:179-180) - e-Tax:
etaxAmountsรับค่าเป็นfloat64และมีทางสำรองที่ใช้math.Round(etax/handler.go:1016) - การปัดลอยตัวของ declining balance ในค่าเสื่อม ใช้
Text('e',14)= 15 หลักนัยสำคัญ (คิดค่าเสื่อมราคาสินทรัพย์ (โอนค่าเสื่อม 1801) คำนวณและลงบัญชีอย่างไร)
ดูเพิ่ม
- การปัดเศษ ทศนิยม และตัวเลขเงิน (Rounding & Decimal Policy)
- บทเรียนบั๊กการปัดเศษและทศนิยมเงิน (Rounding & Decimal Bugs)
- VAT แยกนอก กับ รวมใน คำนวณต่างกันยังไง ส่วนลดท้ายบิลหักก่อนหรือหลังภาษี
- บันทึกเอกสารแล้วขึ้น GL ไม่สมดุล (debit credit do not balance) แก้ยังไง
- แท็บรับ/จ่ายชำระ (เงินสด โอน เช็ค บัตร PromptPay ภาษีหัก) เก็บและลงบัญชีอย่างไร ทำไมขึ้น "ยอดการจ่ายเงินไม่สมบูรณ์"
ที่มาในโค้ด
backend/internal/application/process/service.go:107ParseDecimalRatbackend/internal/application/process/service.go:149RoundHalfUp;:177FormatRatbackend/internal/application/process/service.go:508ValidateAndBalanceJournal;:1614เรียกที่ scale 2backend/internal/application/process/grid_calc.go:99round_type ≠ 1;:132smlRoundbackend/internal/application/process/fa_sale.go:93roundHalfEvenbackend/internal/application/process/trans.go:1055sum_amount_exclude_vatToEven;:1058sum_of_cost2 ตำแหน่งbackend/internal/application/process/gl_template.go:378addDiff;:730glSQLOptions(gl_no_decimal)backend/internal/application/process/gl_template_rules.go:344action 90 บัญชีผลต่างbackend/internal/application/process/stock_rebuild.go:113csRoundfrontend/src/lib/numeric.ts:522getSmlDecimals;:587formatMoneyDisplay