Управління числовою точністю є наріжним каменем подвійної бухгалтерії. У цифровому бухгалтерському обліку, особливо під час роботи з кількома валютами, цінами акцій та дробовими частками, невеликі розбіжності округлення можуть швидко призвести до неприємних помилок балансування. Beancount пропонує складну, але інтуїтивно зрозумілу систему для обробки точності та встановлення прийнятних допусків. Цей посібник проведе вас через те, як це працює. ⚙️
Основні концепції точності
Головна мета Beancount — забезпечити, щоб кожна транзакція зводилася до нуля. Однак обчислення, що включають ціни або витрати, часто дають результати з більшою кількістю десяткових знаків, ніж практично записати. Система допусків дозволяє невеликі прийнятні дисбаланси.
Автоматичне визначення допуску
За замовчуванням Beancount автоматично визначає необхідний допуск для кожної транзакції. Це визначення виконується індивідуально для кожної транзакції та розраховується окремо для кожної залученої валюти.
Правило просте: допуск дорівнює половині останньої значущої цифри чисел, присутніх у проводках транзакції.
Наприклад, розглянемо цю покупку:
2013-04-03 * "Купівля фонду"
Assets:Fund 10.22626 FUND {37.61 USD}
Assets:Cash -384.61 USDBeancount визначає допуски наступним чином:
- Для товару
FUNDчисло10.22626має 5 знаків після коми. Допуск дорівнює половині останньої цифри, тобто $0.00001 \div 2 = 0.000005$FUND. - Для товару
USDчисло-384.61має 2 знаки після коми. Допуск дорівнює половині останньої цифри, тобто $0.01 \div 2 = 0.005$USD.
Правила ваги транзакції
Перевіряючи, чи балансує транзакція, Beancount розраховує "вагу" кожної проводки. Правила для цього розрахунку:
- Проста сума: Якщо проводка має лише суму (наприклад,
Assets:Cash -100.00 USD), її вага дорівнює цій точній сумі. - Проводка з ціною: Якщо проводка має ціну за одиницю (наприклад,
10 FUND @ 38.46 USD), її вага дорівнюєсума × ціна. - Проводка з вартістю: Якщо проводка має загальну вартість (наприклад,
10 FUND {384.61 USD}), її вага дорівнює сумі загальної вартості. - Вартість і ціна: Якщо проводка має як загальну вартість, так і ціну за одиницю (наприклад,
10 FUND {384.61 USD} @ 38.46 USD), для балансування використовується лише загальна вартість. Ціна за одиницю розглядається як коментар або нотатка.
Правила визначення точності
Система автоматичного визначення дотримується кількох конкретних правил:
- Формат числа
- Цілі суми (наприклад,
10 USD) не впливають на визначення точності. - Максимальний допуск, який можна автоматично визначити, становить
0.05одиниць (наприклад, з числа10.1 USD). Якщо вам потрібен більший допуск, ви повинні вказати його вручну. - Вартість і ціни (наприклад,
{37.61 USD}) виключаються з визначення допуску. Використовуються лише основні суми проводок. - Якщо проводки для однієї валюти мають різну точність (наприклад,
-10.10 USDі5.123 USD), Beancount використовує найгрубіший (найбільший) допуск. У цьому випадку він базуватиметься на-10.10 USD, даючи допуск $0.005$USD.
-
Обробка за замовчуванням Ви можете встановити глобальний допуск за замовчуванням або за валютою, якщо транзакція не має чисел з десятковими знаками, з яких можна його визначити.
; Встановлює допуск за замовчуванням для всіх валют без явних правил option "inferred_tolerance_default" "*:0.001" ; Встановлює конкретний допуск за замовчуванням для USD option "inferred_tolerance_default" "USD:0.003" -
Множник допуску Ви можете глобально збільшити всі визначені допуски на фіксований множник. Це корисно для послаблення перевірок у всьому файлі без зміни кожної транзакції. Множник
1.2збільшує всі визначені допуски на 20%.option "inferred_tolerance_multiplier" "1.2" -
Визначення на основі вартості Хоча вартість зазвичай ігнорується для визначення допуску, ви можете вказати Beancount використовувати її. Це корисно, коли кінцева сума (наприклад, зняття готівки) є найточнішим числом у транзакції.
option "infer_tolerance_from_cost" "TRUE"
Балансові підтвердження
Балансові підтвердження (balance) використовуються для перевірки того, що баланс вашого рахунку відповідає відомому значенню на певну дату. Вони також мають пов'язаний допуск.
Базовий формат
Подібно до транзакцій, допуск для підтвердження balance визначається з кількості десяткових знаків у сумі.
; Підтверджує, що баланс дорівнює 4.271 RGAGX з допуском ±0.0005
2015-05-08 balance Assets:Fund 4.271 RGAGX
; Підтверджує, що баланс дорівнює 4.27 RGAGX з допуском ±0.005
2015-05-08 balance Assets:Fund 4.27 RGAGXРозрахований баланс повинен потрапляти в цей діапазон. Для другого прикладу будь-який баланс між і пройде перевірку.
Явні допуски
Якщо визначений допуск не підходить, ви можете вказати його явно за допомогою символу тильди (~).
; Підтверджує, що баланс дорівнює 4.271 RGAGX з власним допуском ±0.01 RGAGX
2015-05-08 balance Assets:Fund 4.271 ~ 0.01 RGAGXТут підтвердження буде пройдено, якщо розрахований баланс буде між та RGAGX.
Управління округленням
Для випадків, коли невеликі залишки від обчислень є очікуваними та прийнятними, Beancount надає інструменти для систематичного управління ними.
Відстеження помилок округлення
Ви можете призначити спеціальний рахунок для автоматичного збору помилок округлення. Це підтримує ваші транзакції ідеально збалансованими, збираючи крихітні залишкові суми в одне місце.
Спочатку увімкніть опцію та відкрийте рахунок:
option "account_rounding" "Equity:RoundingError"
2000-01-01 open Equity:RoundingErrorТепер Beancount автоматично додаватиме третю ногу до будь-якої транзакції, яка не балансує в межах свого допуску, розміщуючи різницю на Equity:RoundingError.
2013-02-23 * "Покупка"
Assets:Invest 1.245 RGAGX {43.23 USD}
Assets:Cash -53.82 USDУ цій транзакції . Транзакція незбалансована на USD. З увімкненою опцією округлення Beancount внутрішньо обробляє її як:
2013-02-23 * "Покупка"
Assets:Invest 1.245 RGAGX {43.23 USD}
Assets:Cash -53.82 USD
Equity:RoundingError -0.00135 USD ; Додано автоматичноВизначена точність чисел
Beancount також може використовувати налаштування допуску для автоматичного округлення чисел ще до того, як вони будуть вставлені в структури даних книги.
-
Допуск не вказано: Якщо допуск не визначено, числа використовуються з повною точністю. Округлення не відбувається.
-
З допуском за замовчуванням: Якщо ви встановите допуск за замовчуванням, числа будуть квантовані до цього рівня.
option "default_tolerance" "USD:0.001"З цим налаштуванням число, наприклад,
53.82135 USD, буде округлено та збережено як53.821 USD. -
З рахунком округлення: Якщо активні як допуск за замовчуванням, так і рахунок округлення, Beancout квантує число та фіксує залишок.
option "default_tolerance" "USD:0.01" option "account_rounding" "Equity:RoundingError"Число, наприклад,
53.82135 USD, буде збережено як53.82 USD, а залишок-0.00135 USDбуде розміщено наEquity:RoundingError.
Деталі реалізації
Кілька технічних моментів пояснюють, як Beancount досягає такої надійності.
-
Представлення чисел: Beancount використовує модуль Python
decimal, а не числа з плаваючою комою. Це дозволяє до 28 знаків після коми точності та уникає помилок двійкового представлення, поширених для чисел з плаваючою комою. -
Клас DisplayContext: Цей внутрішній клас обробляє все форматування чисел для відображення. Він враховує специфічні для валюти налаштування точності та може форматувати вихідні дані з вирівняними стовпцями та комами.
-
Точність проти Допуску: Важливо розрізняти ці два поняття:
- Точність стосується формату відображення числа (скільки десяткових знаків показано).
- Допуск — це дозволений дисбаланс, який використовується під час перевірок.
Найкращі практики ✨
Ось кілька практичних рекомендацій щодо управління точністю у вашій книзі.
Початкове налаштування
Для більшості нових книг це надійна початкова конфігурація:
; Розумне значення за замовчуванням для більшості валют (наприклад, USD, EUR)
option "inferred_tolerance_default" "*:0.005"
; Буфер 10% на всі визначені допуски
option "inferred_tolerance_multiplier" "1.1"
; Рахунок для збору всіх залишків округлення
option "account_rounding" "Equity:RoundingError"
2000-01-01 open Equity:RoundingErrorПоради з усунення несправностей
Якщо ви зіткнулися з помилками балансування:
- Додайте десяткові знаки до суми проводки, щоб створити більш точне локальне визначення допуску.
- Використовуйте явні допуски (
~) для підтвердженьbalance, які не проходять через передбачувані розбіжності. - Відстежуйте помилки округлення на виділеному рахунку, щоб бачити, де і як часто вони виникають.
- Розгляньте можливість встановлення специфічних для валюти значень за замовчуванням, якщо ви часто працюєте з валютами, що мають різні умовності (наприклад, JPY не має десяткових знаків).
Стратегія міграції
Застосовуючи ці концепції до існуючої, безладної книги:
- Почніть з щедрого глобального допуску (наприклад,
*:0.05) та високого множника, щоб файл пройшов валідацію. - Поступово звужуйте допуски та виправляйте помилки, які з'являються.
- Додавайте явні знаки до сум у проблемних транзакціях, щоб дозволити визначенню працювати.
- Слідкуйте за балансом рахунку округлення. Великий або швидко зростаючий баланс може свідчити про системну проблему, яка потребує розслідування.