Het beheren van numerieke precisie is een hoeksteen van dubbel boekhouden. In digitale boekhouding, vooral bij meerdere valuta, aandelenkoersen en fractionele aandelen, kunnen kleine afrondingsverschillen snel leiden tot frustrerende balanceringsfouten. Beancount biedt een geavanceerd maar intuïtief systeem voor het verwerken van precisie en het instellen van acceptabele toleranties. Deze gids legt uit hoe het werkt. ⚙️
Kernconcepten van precisie
Het primaire doel van Beancount is ervoor te zorgen dat elke transactie op nul uitkomt. Berekeningen met prijzen of kosten leveren echter vaak resultaten op met meer decimalen dan praktisch is om vast te leggen. Het tolerantiesysteem staat kleine, acceptabele onevenwichtigheden toe.
Automatische tolerantie-afleiding
Standaard leidt Beancount de benodigde tolerantie voor elke transactie automatisch af. Deze afleiding wordt per transactie afzonderlijk uitgevoerd en apart berekend voor elke betrokken valuta.
De regel is eenvoudig: de tolerantie is de helft van het laatste significante cijfer van de getallen in de postingen van de transactie.
Neem bijvoorbeeld deze aankoop:
2013-04-03 * "Fonds kopen"
Assets:Fund 10.22626 FUND {37.61 USD}
Assets:Cash -384.61 USDBeancount leidt de toleranties als volgt af:
- Voor het
FUND-instrument heeft het getal10.226265 decimalen. De tolerantie is de helft van het laatste cijfer, dusFUND. - Voor het
USD-instrument heeft het getal-384.612 decimalen. De tolerantie is de helft van het laatste cijfer, dusUSD.
Regels voor transactiegewichten
Bij het controleren of een transactie in evenwicht is, berekent Beancount het "gewicht" van elke post. De regels voor deze berekening zijn:
- Eenvoudig bedrag: Als een post alleen een bedrag heeft (bijv.
Assets:Cash -100.00 USD), is het gewicht dat exacte bedrag. - Prijs posting: Als een post een prijs per eenheid heeft (bijv.
10 FUND @ 38.46 USD), is het gewichtbedrag × prijs. - Kosten posting: Als een post een totale kostprijs heeft (bijv.
10 FUND {384.61 USD}), is het gewicht het totale kostprijsbedrag. - Kosten en prijs: Als een post zowel een totale kostprijs als een prijs per eenheid heeft (bijv.
10 FUND {384.61 USD} @ 38.46 USD), wordt alleen de totale kostprijs gebruikt voor de balancering. De prijs per eenheid wordt behandeld als opmerking of memo.
Regels voor precisie-afleiding
Het automatische afleidingssysteem volgt een aantal specifieke regels:
- Getalnotatie
- Gehele bedragen (bijv.
10 USD) dragen niet bij aan precisie-afleiding. - De maximaal automatisch af te leiden tolerantie is
0.05eenheden (bijv. van een getal als10.1 USD). Als je een grotere tolerantie nodig hebt, moet je deze handmatig specificeren. - Kosten en prijzen (bijv.
{37.61 USD}) worden uitgesloten van tolerantie-afleiding. Alleen de primaire bedragen van de postingen worden gebruikt. - Als postingen voor dezelfde valuta verschillende precisies hebben (bijv.
-10.10 USDen5.123 USD), gebruikt Beancount de grofste (grootste) tolerantie. In dit geval zou dat gebaseerd zijn op-10.10 USD, wat een tolerantie vanUSDoplevert.
-
Standaardafhandeling Je kunt een globale of valuta-specifieke standaardtolerantie instellen als een transactie geen getallen met decimalen heeft om deze af te leiden.
; Stelt een standaardtolerantie in voor alle valuta zonder expliciete regels option "inferred_tolerance_default" "*:0.001" ; Stelt een specifieke standaardtolerantie in voor USD option "inferred_tolerance_default" "USD:0.003" -
Tolerantievermenigvuldiger Je kunt alle afgeleide toleranties wereldwijd verhogen met een vaste vermenigvuldiger. Dit is handig om controles in je hele bestand te versoepelen zonder elke transactie te wijzigen. Een vermenigvuldiger van
1.2verhoogt alle afgeleide toleranties met 20%.option "inferred_tolerance_multiplier" "1.2" -
Op kosten gebaseerde afleiding Hoewel kosten normaal gesproken worden genegeerd voor tolerantie-afleiding, kun je Beancount instrueren om ze te gebruiken. Dit is handig wanneer het uiteindelijke bedrag (bijv. een contante opname) het meest precieze getal in een transactie is.
option "infer_tolerance_from_cost" "TRUE"
Saldo-asserties
Saldo-asserties (balance) worden gebruikt om te verifiëren dat het saldo van je rekening overeenkomt met een bekende waarde op een specifieke datum. Ze hebben ook een bijbehorende tolerantie.
Basismotatie
Net als bij transacties wordt de tolerantie voor een balance-assertie afgeleid van het aantal decimalen in het bedrag.
; Stelt dat het saldo 4.271 RGAGX is met een tolerantie van ±0.0005
2015-05-08 balance Assets:Fund 4.271 RGAGX
; Stelt dat het saldo 4.27 RGAGX is met een tolerantie van ±0.005
2015-05-08 balance Assets:Fund 4.27 RGAGXHet berekende saldo moet binnen dit bereik vallen. Voor het tweede voorbeeld zou elk saldo tussen en de controle doorstaan.
Expliciete toleranties
Als de afgeleide tolerantie niet geschikt is, kun je er expliciet een specificeren met het tilde (~)-teken.
; Stelt dat het saldo 4.271 RGAGX is met een aangepaste tolerantie van ±0.01 RGAGX
2015-05-08 balance Assets:Fund 4.271 ~ 0.01 RGAGXHier zal de assertie slagen als het berekende saldo tussen en RGAGX ligt.
Afrondingsbeheer
Voor gevallen waarin kleine restanten uit berekeningen verwacht en acceptabel zijn, biedt Beancount hulpmiddelen om deze systematisch te beheren.
Afrondingsfoutentracking
Je kunt een speciale rekening aanwijzen om automatisch afrondingsfouten te verzamelen. Dit houdt je transacties perfect in evenwicht door kleine overgebleven bedragen naar één plek te verplaatsen.
Schakel eerst de optie in en open de rekening:
option "account_rounding" "Equity:Afrondingsfout"
2000-01-01 open Equity:AfrondingsfoutNu voegt Beancount automatisch een derde poot toe aan elke transactie die niet binnen de tolerantie in evenwicht is, waarbij het verschil naar Equity:Afrondingsfout wordt geboekt.
2013-02-23 * "Aankoop"
Assets:Invest 1.245 RGAGX {43.23 USD}
Assets:Cash -53.82 USDIn deze transactie is . De transactie is niet in evenwicht met USD. Met de afrondingsoptie ingeschakeld, behandelt Beancount het intern als:
2013-02-23 * "Aankoop"
Assets:Invest 1.245 RGAGX {43.23 USD}
Assets:Cash -53.82 USD
Equity:Afrondingsfout -0.00135 USD ; Automatisch toegevoegdAfgeleide getalprecisie
Beancount kan ook tolerantie-instellingen gebruiken om getallen automatisch af te ronden voordat ze in de datastructuren van het boek worden ingevoegd.
-
Geen tolerantie gespecificeerd: Als er geen tolerantie is gedefinieerd, worden getallen op volledige precisie gebruikt. Er vindt geen afronding plaats.
-
Met standaardtolerantie: Als je een standaardtolerantie instelt, worden getallen gekwantiseerd tot dat niveau.
option "default_tolerance" "USD:0.001"Met deze instelling wordt een getal als
53.82135 USDafgerond en opgeslagen als53.821 USD. -
Met afrondingsrekening: Als zowel een standaardtolerantie als een afrondingsrekening actief zijn, kwantiseert Beancount het getal en vangt het residu op.
option "default_tolerance" "USD:0.01" option "account_rounding" "Equity:Afrondingsfout"Een getal als
53.82135 USDzou worden opgeslagen als53.82 USD, en het residu van-0.00135 USDzou worden geboekt naarEquity:Afrondingsfout.
Implementatiedetails
Een paar technische punten verduidelijken hoe Beancount deze betrouwbaarheid bereikt.
-
Getalweergave: Beancount gebruikt de
decimal-module van Python, geen getallen met drijvende komma. Dit maakt tot 28 decimalen precisie mogelijk en voorkomt de binaire representatiefouten die gebruikelijk zijn bij floats. -
DisplayContext-klasse: Deze interne klasse handelt alle getalnotatie voor weergavedoeleinden af. Het respecteert valuta-specifieke precisie-instellingen en kan uitvoer formatteren met uitgelijnde kolommen en komma's.
-
Precisie vs. tolerantie: Het is cruciaal om deze twee concepten te onderscheiden:
- Precisie heeft betrekking op het weergaveformaat van een getal (hoeveel decimalen worden getoond).
- Tolerantie is de toegestane afwijking voor onevenwicht die wordt gebruikt tijdens verificatiecontroles.
Beste praktijken ✨
Hier zijn enkele praktische aanbevelingen voor het beheren van precisie in je grootboek.
Initiële configuratie
Voor de meeste nieuwe grootboeken is dit een robuuste startconfiguratie:
; Een redelijke standaard voor de meeste valuta (bijv. USD, EUR)
option "inferred_tolerance_default" "*:0.005"
; Een buffer van 10% op alle afgeleide toleranties
option "inferred_tolerance_multiplier" "1.1"
; Een rekening om alle afrondingsresten op te vangen
option "account_rounding" "Equity:Afrondingsfout"
2000-01-01 open Equity:AfrondingsfoutTips voor probleemoplossing
Als je balanceringsfouten tegenkomt:
- Voeg decimalen toe aan het bedrag van een post om een strakkere, nauwkeurigere lokale tolerantie-afleiding te creëren.
- Gebruik expliciete toleranties (
~) bijbalance-asserties die mislukken door voorspelbare afwijkingen. - Volg afrondingsfouten in een speciale rekening om te zien waar en hoe vaak ze voorkomen.
- Overweeg het instellen van valuta-specifieke standaarden als je vaak werkt met valuta die verschillende conventies hebben (bijv. JPY heeft geen decimalen).
Migratiestrategie
Bij het toepassen van deze concepten op een bestaand, rommelig grootboek:
- Begin met een ruime globale tolerantie (bijv.
*:0.05) en een hoge vermenigvuldiger om het bestand gevalideerd te krijgen. - Verstrak de toleranties geleidelijk en los de fouten op die verschijnen.
- Voeg expliciete cijfers toe aan bedragen in problematische transacties om de afleiding zijn werk te laten doen.
- Houd het saldo van de afrondingsrekening in de gaten. Een groot of snelgroeiend saldo kan wijzen op een systeemprobleem dat onderzocht moet worden.