§ 32a EStG · Grundtarif
Stückweise Tariffunktion mit fünf Stufen. Der Klassiker — und der größte Schmerz jeder Steuersoftware.
Gesetzlicher Rahmen
Das Modul bildet das Veranlagungsschema des § 2 EStG ab und schließt mit dem tariflichen Einkommensteuerbetrag nach § 32a EStG und der festzusetzenden Einkommensteuer (§ 2 Abs. 6). Maßgeblich ist die konsolidierte Fassung „ab Veranlagungszeitraum 2026". Jede Stufe der gesetzlichen Reihenfolge ist eine eigene, einzeln auditierbare Funktion:
- 1 § 2 Abs. 1–3 Summe der Einkünfte
SummeDerEinkuenfte - 2 § 2 Abs. 3 Gesamtbetrag der Einkünfte
GesamtbetragDerEinkuenfte - 3 § 2 Abs. 4 Einkommen
Einkommen - 4 § 2 Abs. 5 zu versteuerndes Einkommen
ZuVersteuerndesEinkommen - 5 § 32a tarifliche Einkommensteuer
TariflicheEinkommensteuer - 6 § 2 Abs. 6 festzusetzende Einkommensteuer
FestzusetzendeEinkommensteuer
Die Tarifformel · § 32a Abs. 1
Der Grundtarif ist eine fünfzonige Funktion des zu versteuernden
Einkommens. Das Gesetz schreibt die Koeffizienten Zone für Zone vor — FinDSL
bildet sie 1:1 als wähle-Ausdruck ab, jede Konstante mit @Quelle-Verweis auf ihren Satz im Gesetz.
- Zone 1 bis 12.348 € steuerfrei (Grundfreibetrag)
- Zone 2 bis 17.799 € Eingangsprogression (y²)
- Zone 3 bis 69.878 € Hauptprogression (z²)
- Zone 4 bis 277.825 € 42 % (proportional)
- Zone 5 darüber 45 % (proportional)
@Quelle("§ 32a Absatz 1 EStG")
fn EstGrundtarif(zve: Euro): Euro = wähle {
falls zve < 0 als Euro -> abbruch("§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve})")
falls zve < GFB + 1 -> 0
falls zve < ZONE_2_OBERGRENZE + 1 -> {
var y: Dezimal = (zve - GFB) / ZEHNTAUSEND
var roh: Dezimal = (ZONE_2_PROGRESSION * y + ZONE_2_LINEAR) * y
roh.abrunden() als Euro
}
falls zve < ZONE_3_OBERGRENZE + 1 -> {
var z: Dezimal = (zve - ZONE_2_OBERGRENZE) / ZEHNTAUSEND
var roh: Dezimal = (ZONE_3_PROGRESSION * z + ZONE_3_LINEAR) * z + ZONE_3_KONSTANTE
roh.abrunden() als Euro
}
falls zve < ZONE_4_OBERGRENZE + 1 -> (ZONE_4_SATZ * zve - ZONE_4_ABZUG).abrunden()
sonst -> (ZONE_5_SATZ * zve - ZONE_5_ABZUG).abrunden()
}Das Veranlagungsschema · § 2
Der Orchestrator ruft die Stufen in gesetzlicher Reihenfolge auf und legt jede Zwischengröße als eigenes Feld ab — vom Gesamtbetrag der Einkünfte bis zur festzusetzenden Steuer. So lässt sich jeder Bescheid Schritt für Schritt nachvollziehen.
@Quelle("§ 2 EStG, § 32a EStG")
fn BerechneEinkommensteuer(fall: EinkommensteuerFall): EinkommensteuerErgebnis = {
var sde: Euro = SummeDerEinkuenfte(fall)
var gde: Euro = GesamtbetragDerEinkuenfte(sde, fall)
var kfb: Euro = KinderfreibetragGesamt(fall.kinder)
var agb: Euro = AbziehbareAussergewoehnlicheBelastungen(fall, gde)
var ein: Euro = Einkommen(gde, fall)
var zve: Euro = ZuVersteuerndesEinkommen(ein, fall)
var tariflich: Euro = TariflicheEinkommensteuer(zve, fall.tarifart)
var fest: Euro = FestzusetzendeEinkommensteuer(tariflich, fall)
EinkommensteuerErgebnis(
summeDerEinkuenfte = sde,
gesamtbetragDerEinkuenfte = gde,
kinderfreibetraege = kfb,
abziehbareAussergewoehnlicheBelastungen = agb,
einkommen = ein,
zuVersteuerndesEinkommen = zve,
tariflicheEinkommensteuer = tariflich,
festzusetzendeEinkommensteuer = fest,
)
}Das vollständige Modul
Konstanten (§ 32a Abs. 1, § 32 Abs. 6, § 33 Abs. 3, § 10b), der Tarif samt
Splitting (§ 32a Abs. 5) und die Veranlagungskaskade — unverändert aus findsl/findsl übernommen.
Modul anzeigen est.findsl · 595 Zeilen
--
# Einkommensteuer — Veranlagungsschema § 2 EStG + Tarif § 32a EStG (VZ 2026)
Bildet die **Einkommensteuer-Kaskade** nach § 2 EStG ab, schließt mit
dem tariflichen Einkommensteuerbetrag (§ 32a) und der festzusetzenden
Einkommensteuer (§ 2 Abs. 6). Maßgebliche Quelle:
`examples/est/estg.xml` (juris-Stand 2026-05-06), § 32a/§ 32 Abs. 6 in
der konsolidierten Fassung „ab Veranlagungszeitraum 2026".
Gesetzliche Reihenfolge (jede Stufe = eigene Funktion, auditierbar):
Summe der Einkünfte (§ 2 Abs. 1–3) → Gesamtbetrag der Einkünfte
(§ 2 Abs. 3) → Einkommen (§ 2 Abs. 4) → zu versteuerndes Einkommen
(§ 2 Abs. 5) → tarifliche Einkommensteuer (§ 32a) → festzusetzende
Einkommensteuer (§ 2 Abs. 6).
**Echte Rechenvorschrift (modelliert) — auch mehr-entitätig:**
- **§ 32 Abs. 6 Kinderfreibetrag/BEA je Kind** über `Liste<Kind>`
(3.414 € + 1.464 € je Kind, Verdopplung Satz 2/3 per Faktor,
Zwölftelung Satz 5, Auslandskürzung Satz 4) → aggregiert.
- **§ 33 Abs. 1/3 außergewöhnliche Belastungen**: Summe der
zwangsläufigen Aufwendungen abzüglich der **zumutbaren Belastung**
(§ 33 Abs. 3, **staffelweise** über die drei GdE-Stufen × vier
Personengruppen).
- **§ 10b Abs. 1 Spenden**: abziehbar bis zum Höchstbetrag
max(20 % GdE; 4 ‰ (Umsätze + Löhne)).
- Die gesamte § 2-Verknüpfungs-Arithmetik + § 32a-Tarif + § 2 Abs. 6.
**Geprüfte Eingabe, weil anderes Recht / Verfahren (nicht Tooling-
Grenze):**
- **Ermittlung der sieben Einkunftsarten** je Art (Gewinn §§ 4–7k/13a,
Überschuss §§ 8–9a, § 20 Abs. 9, AfA § 7 mehrperiodig) — saldierter
Betrag je Art als Eingabe.
- **§ 24a / § 24b / § 13 Abs. 3** — Beträge als Eingabe (eigene §§).
- **Übrige Sonderausgaben §§ 10–10c** außer § 10b (Vorsorgeaufwen-
dungen mit eigenen Höchstbeträgen/Günstigerprüfung) — Aggregat-
Eingabe `sonstigeSonderausgaben`.
- **Verlustabzug § 10d** (mehrperiodig) — negatives zvE → 0 tariflich,
Verlustabzug selbst nicht modelliert.
- **Sachverhalte je Kind** (Kindschaftsverhältnis → `faktor`,
Auslands-Ländergruppe → `auslandsfaktor`, Berücksichtigungsmonate)
und die § 33-Zwangsläufigkeit/Angemessenheit (§ 33 Abs. 2),
§ 10b-Empfänger-Voraussetzungen (§ 10b Abs. 2) — Sachverhalt.
- **§ 32a Abs. 6** Witwen-/Gnadensplitting; **§ 2 Abs. 6-Komponenten**
(§§ 34c/35/35a/32d Abs. 3/4 …) als zwei gerichtete Aggregat-Eingaben;
Annexsteuern (SolZ, KiSt). Verfahren/eigene Gesetze.
**Modellierungs-Entscheidung (Statut schweigt):** jede listen-
abgeleitete Kategorie-Abzugssumme (Kinderfreibetrag, abziehbare agB,
abziehbare Spenden) wird auf **volle Euro abgerundet** (`.abrunden()`
mit Euro-Kontext),
bevor sie in die Euro-Kaskade eingeht — deterministisch, konsistent mit
§ 32a Abs. 1 Satz 1 (zvE auf volle Euro), fiskuskonservativ.
--
// ===========================================================================
// Konstanten — § 32a Absatz 1 EStG (Fassung ab VZ 2026)
// ===========================================================================
--
Grundfreibetrag — bis zu diesem zu versteuernden Einkommen beträgt die
tarifliche Einkommensteuer 0 (§ 32a Absatz 1 Satz 2 Nummer 1).
--
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 1 EStG")
konst GFB: Euro = 12.348
-- Obere Grenze der Eingangs-Progressionszone (Zone 2). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 2 EStG")
konst ZONE_2_OBERGRENZE: Euro = 17.799
-- Obere Grenze der Hauptprogressionszone (Zone 3). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
konst ZONE_3_OBERGRENZE: Euro = 69.878
-- Obere Grenze der ersten Proportionalzone (Zone 4); darüber Zone 5. --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 4 EStG")
konst ZONE_4_OBERGRENZE: Euro = 277.825
--
Teiler für die Größen „y" und „z": ein Zehntausendstel des den
jeweiligen Sockel übersteigenden, auf vollen Euro abgerundeten zvE
(§ 32a Absatz 1 Satz 3 und 4).
--
@Quelle("§ 32a Absatz 1 Satz 3 und 4 EStG")
konst ZEHNTAUSEND: Ganzzahl = 10.000
-- Progressionskoeffizient der Zone 2 (Faktor vor y²). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 2 EStG")
konst ZONE_2_PROGRESSION: Dezimal = 914,51
-- Linearer Koeffizient der Zone 2 (Faktor vor y). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 2 EStG")
konst ZONE_2_LINEAR: Dezimal = 1.400
-- Progressionskoeffizient der Zone 3 (Faktor vor z²). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
konst ZONE_3_PROGRESSION: Dezimal = 173,10
-- Linearer Koeffizient der Zone 3 (Faktor vor z). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
konst ZONE_3_LINEAR: Dezimal = 2.397
-- Konstanter Summand der Zone 3 (Anschluss an Zone 2). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
konst ZONE_3_KONSTANTE: Dezimal = 1.034,87
-- Grenzsteuersatz der Proportionalzone 4 (Spitzensteuersatz). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 4 EStG")
konst ZONE_4_SATZ: Prozent = 42%
-- Abzugsbetrag der Zone 4 (0,42 · x − ZONE_4_ABZUG). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 4 EStG")
konst ZONE_4_ABZUG: EuroCent = 11.135,63
-- Grenzsteuersatz der Proportionalzone 5 („Reichensteuer"). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 5 EStG")
konst ZONE_5_SATZ: Prozent = 45%
-- Abzugsbetrag der Zone 5 (0,45 · x − ZONE_5_ABZUG). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 5 EStG")
konst ZONE_5_ABZUG: EuroCent = 19.470,38
// ===========================================================================
// Konstanten — § 32 Abs. 6 (Kinderfreibetrag), § 33 Abs. 3, § 10b
// ===========================================================================
-- Kinderfreibetrag (sächliches Existenzminimum) je Kind. --
@Quelle("§ 32 Absatz 6 Satz 1 EStG")
konst KINDERFREIBETRAG: Euro = 3.414
-- Freibetrag Betreuungs-/Erziehungs-/Ausbildungsbedarf (BEA) je Kind. --
@Quelle("§ 32 Absatz 6 Satz 1 EStG")
konst BEA_FREIBETRAG: Euro = 1.464
-- Teiler für die Zwölftelung je nicht erfüllten Kalendermonat. --
@Quelle("§ 32 Absatz 6 Satz 5 EStG")
konst ZWOELF: Ganzzahl = 12
-- Erste GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3). --
@Quelle("§ 33 Absatz 3 EStG")
konst ZMB_STUFE_1: Euro = 15.340
-- Zweite GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3). --
@Quelle("§ 33 Absatz 3 EStG")
konst ZMB_STUFE_2: Euro = 51.130
-- Zumutbare Belastung — keine Kinder, Grundtarif (§ 32a Abs. 1): Stufe 1/2/3. --
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG")
konst ZMB_OHNE_KIND_GRUND_1: Prozent = 5%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG")
konst ZMB_OHNE_KIND_GRUND_2: Prozent = 6%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG")
konst ZMB_OHNE_KIND_GRUND_3: Prozent = 7%
-- Zumutbare Belastung — keine Kinder, Splitting (§ 32a Abs. 5/6): Stufe 1/2/3. --
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG")
konst ZMB_OHNE_KIND_SPLIT_1: Prozent = 4%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG")
konst ZMB_OHNE_KIND_SPLIT_2: Prozent = 5%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG")
konst ZMB_OHNE_KIND_SPLIT_3: Prozent = 6%
-- Zumutbare Belastung — ein oder zwei Kinder: Stufe 1/2/3. --
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG")
konst ZMB_1_2_KINDER_1: Prozent = 2%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG")
konst ZMB_1_2_KINDER_2: Prozent = 3%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG")
konst ZMB_1_2_KINDER_3: Prozent = 4%
-- Zumutbare Belastung — drei oder mehr Kinder: Stufe 1/2/3. --
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG")
konst ZMB_AB_3_KINDER_1: Prozent = 1%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG")
konst ZMB_AB_3_KINDER_2: Prozent = 1%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG")
konst ZMB_AB_3_KINDER_3: Prozent = 2%
-- Spenden-Höchstbetrag Variante 1: Anteil des Gesamtbetrags der Einkünfte. --
@Quelle("§ 10b Absatz 1 Satz 1 Nummer 1 EStG")
konst SPENDEN_HB_GDE: Prozent = 20%
-- Spenden-Höchstbetrag Variante 2: Promille der Umsätze + Löhne (4 ‰). --
@Quelle("§ 10b Absatz 1 Satz 1 Nummer 2 EStG")
konst SPENDEN_HB_UMSATZ: Prozent = 0,4%
// ===========================================================================
// Tarifformel — § 32a Absatz 1 EStG
// ===========================================================================
--
Tariflicher Einkommensteuerbetrag nach dem Grundtarif (§ 32a Absatz 1
EStG). Das zu versteuernde Einkommen ist nach Satz 1 auf volle Euro
abgerundet zu verstehen (durch den `Euro`-Typ bereits ganzzahlig). Der
sich ergebende Steuerbetrag wird nach Satz 6 auf den nächsten vollen
Euro abgerundet.
Mit den Hilfsgrößen $y = \frac{\text{zvE} - \text{GFB}}{10000}$ (Zone 2)
und $z = \frac{\text{zvE} - \text{ZONE\_2}}{10000}$ (Zone 3) lautet der
Tarif zonenweise:
$$
\text{ESt}(\text{zvE}) =
\begin{cases}
0 & \text{zvE} \le \text{GFB} \\
(a_2\,y + b_2)\,y & \text{Zone 2} \\
(a_3\,z + b_3)\,z + c_3 & \text{Zone 3} \\
0{,}42 \cdot \text{zvE} - C_4 & \text{Zone 4} \\
0{,}45 \cdot \text{zvE} - C_5 & \text{Zone 5}
\end{cases}
$$
@param zve zu versteuerndes Einkommen in vollen Euro (geprüfte
Eingabe, ≥ 0; negativ → `abbruch`)
@rückgabe tarifliche Einkommensteuer in vollen Euro (Grundtarif)
--
@Quelle("§ 32a Absatz 1 EStG")
fn EstGrundtarif(zve: Euro): Euro = wähle {
falls zve < 0 als Euro -> abbruch("§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve})")
falls zve < GFB + 1 -> 0
falls zve < ZONE_2_OBERGRENZE + 1 -> {
var y: Dezimal = (zve - GFB) / ZEHNTAUSEND
var roh: Dezimal = (ZONE_2_PROGRESSION * y + ZONE_2_LINEAR) * y
roh.abrunden() als Euro
}
falls zve < ZONE_3_OBERGRENZE + 1 -> {
var z: Dezimal = (zve - ZONE_2_OBERGRENZE) / ZEHNTAUSEND
var roh: Dezimal = (ZONE_3_PROGRESSION * z + ZONE_3_LINEAR) * z + ZONE_3_KONSTANTE
roh.abrunden() als Euro
}
falls zve < ZONE_4_OBERGRENZE + 1 -> (ZONE_4_SATZ * zve - ZONE_4_ABZUG).abrunden()
sonst -> (ZONE_5_SATZ * zve - ZONE_5_ABZUG).abrunden()
}
--
Tariflicher Einkommensteuerbetrag nach dem Splitting-Verfahren für
zusammen veranlagte Ehegatten (§ 32a Absatz 5 EStG): das Zweifache des
Steuerbetrags, der sich für die Hälfte des gemeinsam zu versteuernden
Einkommens nach Absatz 1 ergibt. Die Hälfte wird nach Absatz 1 Satz 1
auf volle Euro abgerundet.
@param zve gemeinsam zu versteuerndes Einkommen der Ehegatten in vollen
Euro (geprüfte Eingabe, ≥ 0; negativ → `abbruch`)
@rückgabe tarifliche Einkommensteuer in vollen Euro (Splitting)
--
@Quelle("§ 32a Absatz 5 EStG")
fn EstSplitting(zve: Euro): Euro = wähle {
falls zve < 0 als Euro -> abbruch("§ 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve})")
sonst -> {
var halbesZve: Euro = (zve / 2).abrunden() als Euro
2 * EstGrundtarif(halbesZve)
}
}
// ===========================================================================
// Allgemeine Helfer (modul-intern)
// ===========================================================================
-- Anteil eines Euro-Betrags in der Staffel-Spanne [von, obereGrenze]. --
fn _Spanne(betrag: Euro, von: Euro, obereGrenze: Euro): Euro =
(betrag.höchstens(obereGrenze) - von).mindestens(0)
// ===========================================================================
// Veranlagungsschema — § 2 EStG (Kaskade zu versteuerndes Einkommen)
// ===========================================================================
//
// Veranlagungsform = EINGEBAUTE Aufzählung `Tarifart`
// (`Grundtarif`/`Splitting`, SPEC § 8.5) — global, kein Import.
--
Sachverhalte je Kind (§ 32 Abs. 6). Die Beträge sind Gesetz; diese
Felder sind die Sachverhalts-Eingaben je Kind.
@param faktor 1 = einfacher Freibetrag; 2 = verdoppelt
(§ 32 Abs. 6 Satz 2/3 — Kind zu beiden
Ehegatten bzw. Satz-3-Fälle)
@param berücksichtigteMonate Monate mit erfüllten Voraussetzungen
(§ 32 Abs. 6 Satz 5: je fehlendem Monat 1/12)
@param auslandsfaktor Ländergruppen-Anteil für Auslandskinder
(§ 32 Abs. 6 Satz 4; 100 % = Inlandskind)
--
@Quelle("§ 32 Absatz 6 EStG")
datensatz Kind(
faktor: Ganzzahl = 1, // § 32 Abs. 6 Satz 2/3
berücksichtigteMonate: Ganzzahl = 12, // § 32 Abs. 6 Satz 5
auslandsfaktor: Prozent = 100%, // § 32 Abs. 6 Satz 4
)
--
Eingaben für die Einkommensteuer-Veranlagung.
@param einkuenfteLandUndForstwirtschaft Einkünfte § 2 Abs. 1 Nr. 1 (§§ 13–14)
@param einkuenfteGewerbebetrieb Einkünfte § 2 Abs. 1 Nr. 2 (§§ 15–17)
@param einkuenfteSelbstaendigeArbeit Einkünfte § 2 Abs. 1 Nr. 3 (§ 18)
@param einkuenfteNichtselbstaendigeArbeit Einkünfte § 2 Abs. 1 Nr. 4 (§ 19)
@param einkuenfteKapitalvermoegen veranlagte Einkünfte § 2 Abs. 1 Nr. 5 (§ 20)
@param einkuenfteVermietungVerpachtung Einkünfte § 2 Abs. 1 Nr. 6 (§ 21)
@param sonstigeEinkuenfte sonstige Einkünfte § 2 Abs. 1 Nr. 7 (§ 22)
@param altersentlastungsbetrag Altersentlastungsbetrag (§ 24a)
@param entlastungsbetragAlleinerziehende Entlastungsbetrag Alleinerziehende (§ 24b)
@param freibetragLandUndForstwirtschaft Abzug nach § 13 Absatz 3
@param sonstigeSonderausgaben Sonderausgaben §§ 10–10c ohne § 10b
(Vorsorge u. a. — anderes Recht)
@param spenden abziehbare Zuwendungen § 10b Abs. 1
(Voraussetzungen Abs. 2 = Sachverhalt)
@param umsaetzeUndLoehne Basis der 4-‰-Höchstbetrags-
Variante (§ 10b Abs. 1 Satz 1 Nr. 2)
@param aussergewoehnlicheAufwendungen zwangsläufige Aufwendungen § 33
(Abs. 2 = Sachverhalt), vor
zumutbarer Belastung
@param kinder zu berücksichtigende Kinder (§ 32 Abs. 6)
@param sonstigeAbzuegeVomEinkommen sonstige vom Einkommen abzuziehende
Beträge (§ 2 Abs. 5 Satz 1)
@param tarifart Grund- oder Splittingtarif (§§ 26, 26b)
@param anrechnungenUndErmaessigungen § 2 Abs. 6 „vermindert um"
@param hinzurechnungen § 2 Abs. 6 „vermehrt um" (S. 1–3)
--
@Quelle("§ 2 EStG")
datensatz EinkommensteuerFall(
einkuenfteLandUndForstwirtschaft: Euro = 0, // § 2 Abs. 1 Nr. 1
einkuenfteGewerbebetrieb: Euro = 0, // § 2 Abs. 1 Nr. 2
einkuenfteSelbstaendigeArbeit: Euro = 0, // § 2 Abs. 1 Nr. 3
einkuenfteNichtselbstaendigeArbeit: Euro = 0, // § 2 Abs. 1 Nr. 4
einkuenfteKapitalvermoegen: Euro = 0, // § 2 Abs. 1 Nr. 5
einkuenfteVermietungVerpachtung: Euro = 0, // § 2 Abs. 1 Nr. 6
sonstigeEinkuenfte: Euro = 0, // § 2 Abs. 1 Nr. 7
altersentlastungsbetrag: Euro = 0, // § 24a
entlastungsbetragAlleinerziehende: Euro = 0, // § 24b
freibetragLandUndForstwirtschaft: Euro = 0, // § 13 Abs. 3
sonstigeSonderausgaben: Euro = 0, // §§ 10–10c o. § 10b
spenden: Liste<Euro> = []<Euro>, // § 10b Abs. 1
umsaetzeUndLoehne: Euro = 0, // § 10b Abs. 1 S. 1 Nr. 2
aussergewoehnlicheAufwendungen: Liste<Euro> = []<Euro>, // § 33
kinder: Liste<Kind> = []<Kind>, // § 32 Abs. 6
sonstigeAbzuegeVomEinkommen: Euro = 0, // § 2 Abs. 5 S. 1
tarifart: Tarifart = Grundtarif, // §§ 26, 26b
anrechnungenUndErmaessigungen: Euro = 0, // § 2 Abs. 6 S. 1
hinzurechnungen: Euro = 0, // § 2 Abs. 6 S. 1–3
)
--
Ergebnis der Veranlagung — jede Zwischengröße der gesetzlichen
Reihenfolge des § 2 EStG als eigenes Feld (Schritt-für-Schritt-Audit).
@param summeDerEinkuenfte Summe der Einkünfte (§ 2 Abs. 1–3)
@param gesamtbetragDerEinkuenfte Gesamtbetrag der Einkünfte (§ 2 Abs. 3)
@param kinderfreibetraege Freibeträge § 32 Abs. 6 (aggregiert)
@param abziehbareAussergewoehnlicheBelastungen § 33 nach zumutbarer Belastung
@param einkommen Einkommen (§ 2 Abs. 4)
@param zuVersteuerndesEinkommen zu versteuerndes Einkommen (§ 2 Abs. 5)
@param tariflicheEinkommensteuer tarifliche Einkommensteuer (§ 32a)
@param festzusetzendeEinkommensteuer festzusetzende Einkommensteuer (§ 2 Abs. 6)
--
@Quelle("§ 2 EStG")
datensatz EinkommensteuerErgebnis(
summeDerEinkuenfte: Euro, // § 2 Abs. 1–3
gesamtbetragDerEinkuenfte: Euro, // § 2 Abs. 3
kinderfreibetraege: Euro, // § 32 Abs. 6
abziehbareAussergewoehnlicheBelastungen: Euro, // § 33
einkommen: Euro, // § 2 Abs. 4
zuVersteuerndesEinkommen: Euro, // § 2 Abs. 5
tariflicheEinkommensteuer: Euro, // § 32a
festzusetzendeEinkommensteuer: Euro, // § 2 Abs. 6
)
--
Summe der Einkünfte (§ 2 Absatz 1 und 2 EStG): Summe der sieben
Einkunftsarten. Negative Einkünfte einzelner Arten mindern die Summe
(einkunftsartübergreifende Verlustverrechnungsbeschränkungen sind
anderes Recht und in den Eingaben bereits berücksichtigt).
@param fall die Veranlagungseingaben
@rückgabe Summe der Einkünfte in vollen Euro
--
@Quelle("§ 2 Absatz 1 und 2 EStG")
fn SummeDerEinkuenfte(fall: EinkommensteuerFall): Euro =
fall.einkuenfteLandUndForstwirtschaft
+ fall.einkuenfteGewerbebetrieb
+ fall.einkuenfteSelbstaendigeArbeit
+ fall.einkuenfteNichtselbstaendigeArbeit
+ fall.einkuenfteKapitalvermoegen
+ fall.einkuenfteVermietungVerpachtung
+ fall.sonstigeEinkuenfte
--
Gesamtbetrag der Einkünfte (§ 2 Absatz 3 EStG): Summe der Einkünfte
vermindert um Altersentlastungsbetrag (§ 24a), Entlastungsbetrag für
Alleinerziehende (§ 24b) und Abzug nach § 13 Absatz 3.
@param summe Summe der Einkünfte (Stufe zuvor)
@param fall die Veranlagungseingaben
@rückgabe Gesamtbetrag der Einkünfte in vollen Euro
--
@Quelle("§ 2 Absatz 3 EStG")
fn GesamtbetragDerEinkuenfte(summe: Euro, fall: EinkommensteuerFall): Euro =
summe
- fall.altersentlastungsbetrag
- fall.entlastungsbetragAlleinerziehende
- fall.freibetragLandUndForstwirtschaft
--
Kinderfreibetrag + BEA-Freibetrag, aggregiert über alle Kinder
(§ 32 Absatz 6 EStG): je Kind `(3.414 + 1.464) · faktor ·
berücksichtigteMonate/12 · auslandsfaktor`; die Summe wird auf volle
Euro abgerundet (Modellierungs-Entscheidung, s. Datei-Doc).
@param kinder die zu berücksichtigenden Kinder
@rückgabe Gesamt-Freibetrag in vollen Euro
--
@Quelle("§ 32 Absatz 6 EStG")
fn KinderfreibetragGesamt(kinder: Liste<Kind>): Euro =
(
kinder.zuordnen( {
k ->
(KINDERFREIBETRAG + BEA_FREIBETRAG)
* k.faktor
* (k.berücksichtigteMonate / ZWOELF)
* k.auslandsfaktor
}
).summe()
).abrunden()
--
Zumutbare Belastung (§ 33 Absatz 3 EStG) — **staffelweise** über die
drei GdE-Stufen (bis 15.340 / bis 51.130 / darüber), mit den
Prozentsätzen der vier Personengruppen (keine Kinder Grund/Splitting,
1–2 Kinder, ≥ 3 Kinder). „Kinder" sind die mit Freibetrag § 32 Abs. 6
oder Kindergeld-Anspruch (§ 33 Abs. 3 Satz 2 — hier `kinderzahl`).
@param gde Gesamtbetrag der Einkünfte
@param kinderzahl Zahl der zu berücksichtigenden Kinder
@param tarifart Grund- oder Splittingtarif (nur bei 0 Kindern relevant)
@rückgabe zumutbare Belastung (EuroCent-genau)
--
@Quelle("§ 33 Absatz 3 EStG")
fn ZumutbareBelastung(gde: Euro, kinderzahl: Ganzzahl, tarifart: Tarifart): EuroCent =
_ZmbSatz(1, kinderzahl, tarifart)
* _Spanne(gde, 0, ZMB_STUFE_1)
+ _ZmbSatz(2, kinderzahl, tarifart)
* _Spanne(gde, ZMB_STUFE_1, ZMB_STUFE_2)
+ _ZmbSatz(3, kinderzahl, tarifart)
* (gde - ZMB_STUFE_2).mindestens(0)
-- Prozentsatz der zumutbaren Belastung für GdE-Stufe (1/2/3). --
@Quelle("§ 33 Absatz 3 Satz 1 EStG")
fn _ZmbSatz(stufe: Ganzzahl, kinderzahl: Ganzzahl, tarifart: Tarifart): Prozent = wähle {
falls kinderzahl < 1 -> wähle (tarifart) {
falls Grundtarif -> wähle {
falls stufe < 2 -> ZMB_OHNE_KIND_GRUND_1
falls stufe < 3 -> ZMB_OHNE_KIND_GRUND_2
sonst -> ZMB_OHNE_KIND_GRUND_3
}
falls Splitting -> wähle {
falls stufe < 2 -> ZMB_OHNE_KIND_SPLIT_1
falls stufe < 3 -> ZMB_OHNE_KIND_SPLIT_2
sonst -> ZMB_OHNE_KIND_SPLIT_3
}
}
falls kinderzahl < 3 -> wähle {
falls stufe < 2 -> ZMB_1_2_KINDER_1
falls stufe < 3 -> ZMB_1_2_KINDER_2
sonst -> ZMB_1_2_KINDER_3
}
sonst -> wähle {
falls stufe < 2 -> ZMB_AB_3_KINDER_1
falls stufe < 3 -> ZMB_AB_3_KINDER_2
sonst -> ZMB_AB_3_KINDER_3
}
}
--
Abziehbare außergewöhnliche Belastungen (§ 33 Absatz 1 EStG): Summe der
zwangsläufigen Aufwendungen, soweit sie die zumutbare Belastung
(§ 33 Abs. 3) übersteigt; nie negativ, auf volle Euro abgerundet.
@param fall die Veranlagungseingaben
@param gde Gesamtbetrag der Einkünfte (Bezugsgröße der zumutbaren Belastung)
@rückgabe abziehbarer Betrag in vollen Euro
--
@Quelle("§ 33 Absatz 1 EStG")
fn AbziehbareAussergewoehnlicheBelastungen(fall: EinkommensteuerFall, gde: Euro): Euro =
(
(fall.aussergewoehnlicheAufwendungen.summe() als EuroCent)
- ZumutbareBelastung(gde, fall.kinder.länge, fall.tarifart)
).mindestens(0,00).abrunden()
--
Abziehbare Spenden (§ 10b Absatz 1 EStG): Summe der Zuwendungen,
gedeckelt auf den Höchstbetrag = größerer Wert aus 20 % des
Gesamtbetrags der Einkünfte und 4 ‰ der Umsätze + Löhne; auf volle
Euro abgerundet.
@param fall die Veranlagungseingaben
@param gde Gesamtbetrag der Einkünfte (Bezugsgröße Variante 1)
@rückgabe abziehbare Spenden in vollen Euro
--
@Quelle("§ 10b Absatz 1 EStG")
fn AbziehbareSpenden(fall: EinkommensteuerFall, gde: Euro): Euro = {
var grenzeGde: Euro = (SPENDEN_HB_GDE * gde).abrunden()
var grenzeUmsatz: Euro = (SPENDEN_HB_UMSATZ * fall.umsaetzeUndLoehne).abrunden()
var hoechstbetrag: Euro = grenzeGde.mindestens(grenzeUmsatz)
fall.spenden.summe().höchstens(hoechstbetrag)
}
--
Einkommen (§ 2 Absatz 4 EStG): Gesamtbetrag der Einkünfte vermindert
um die Sonderausgaben (sonstige + abziehbare Spenden § 10b) und die
abziehbaren außergewöhnlichen Belastungen (§ 33).
@param gesamtbetrag Gesamtbetrag der Einkünfte (Stufe zuvor)
@param fall die Veranlagungseingaben
@rückgabe Einkommen in vollen Euro
--
@Quelle("§ 2 Absatz 4 EStG")
fn Einkommen(gesamtbetrag: Euro, fall: EinkommensteuerFall): Euro =
gesamtbetrag
- fall.sonstigeSonderausgaben
- AbziehbareSpenden(fall, gesamtbetrag)
- AbziehbareAussergewoehnlicheBelastungen(fall, gesamtbetrag)
--
Zu versteuerndes Einkommen (§ 2 Absatz 5 Satz 1 EStG): Einkommen
vermindert um die Freibeträge nach § 32 Absatz 6 (Kinder) und die
sonstigen vom Einkommen abzuziehenden Beträge.
@param einkommen Einkommen (Stufe zuvor)
@param fall die Veranlagungseingaben
@rückgabe zu versteuerndes Einkommen in vollen Euro (kann bei
Verlusten negativ sein — § 10d nicht modelliert)
--
@Quelle("§ 2 Absatz 5 Satz 1 EStG")
fn ZuVersteuerndesEinkommen(einkommen: Euro, fall: EinkommensteuerFall): Euro =
einkommen
- KinderfreibetragGesamt(fall.kinder)
- fall.sonstigeAbzuegeVomEinkommen
--
Tarifliche Einkommensteuer (§ 32a EStG): Grund- oder Splittingtarif.
Negatives zvE → 0 (§ 32a für negatives zvE nicht definiert; § 10d
Verlustabzug ist Verfahren, nicht modelliert).
@param zve zu versteuerndes Einkommen in vollen Euro
@param tarifart Grund- oder Splittingtarif
@rückgabe tarifliche Einkommensteuer in vollen Euro
--
@Quelle("§ 32a Absatz 1 und 5 EStG")
fn TariflicheEinkommensteuer(zve: Euro, tarifart: Tarifart): Euro = wähle (tarifart) {
falls Grundtarif -> EstGrundtarif(zve.mindestens(0))
falls Splitting -> EstSplitting(zve.mindestens(0))
}
--
Festzusetzende Einkommensteuer (§ 2 Absatz 6 EStG): tarifliche Steuer
vermindert um Anrechnungen/Steuerermäßigungen, vermehrt um
Hinzurechnungen (Komponenten + Kappungen = anderes Recht/Eingabe;
keine Untergrenze — der Wortlaut sieht keine vor).
@param tariflich tarifliche Einkommensteuer (Stufe zuvor)
@param fall die Veranlagungseingaben
@rückgabe festzusetzende Einkommensteuer in vollen Euro
--
@Quelle("§ 2 Absatz 6 EStG")
fn FestzusetzendeEinkommensteuer(tariflich: Euro, fall: EinkommensteuerFall): Euro =
tariflich
- fall.anrechnungenUndErmaessigungen
+ fall.hinzurechnungen
--
Orchestrator — vollständige Veranlagung in gesetzlicher Reihenfolge
(§ 2 EStG). Füllt jede Zwischengröße ins Ergebnis-Datensatz.
@param fall die Veranlagungseingaben
@rückgabe das Veranlagungsergebnis mit allen Zwischengrößen
--
@Quelle("§ 2 EStG, § 32a EStG")
fn BerechneEinkommensteuer(fall: EinkommensteuerFall): EinkommensteuerErgebnis = {
var sde: Euro = SummeDerEinkuenfte(fall)
var gde: Euro = GesamtbetragDerEinkuenfte(sde, fall)
var kfb: Euro = KinderfreibetragGesamt(fall.kinder)
var agb: Euro = AbziehbareAussergewoehnlicheBelastungen(fall, gde)
var ein: Euro = Einkommen(gde, fall)
var zve: Euro = ZuVersteuerndesEinkommen(ein, fall)
var tariflich: Euro = TariflicheEinkommensteuer(zve, fall.tarifart)
var fest: Euro = FestzusetzendeEinkommensteuer(tariflich, fall)
EinkommensteuerErgebnis(
summeDerEinkuenfte = sde,
gesamtbetragDerEinkuenfte = gde,
kinderfreibetraege = kfb,
abziehbareAussergewoehnlicheBelastungen = agb,
einkommen = ein,
zuVersteuerndesEinkommen = zve,
tariflicheEinkommensteuer = tariflich,
festzusetzendeEinkommensteuer = fest,
)
}examples/est Geprüft — die prüfe-Fälle
Die Sollwerte sind von Hand aus dem Wortlaut gerechnet — jede Tarifzone an ihren Grenzen, das Splitting-Verfahren und vier vollständige Veranlagungsfälle mit Kindern, außergewöhnlichen Belastungen und Spenden. Sie laufen im Editor mit einem Klick auf den Play-Pfeil.
Testdatei anzeigen est.test.findsl
--
# Akzeptanztests — Einkommensteuer § 2 + § 32a EStG (VZ 2026)
Sollwerte **von Hand aus dem Wortlaut** gerechnet (Quelle
`examples/est/estg.xml`, Fassung „ab Veranlagungszeitraum 2026").
§ 32a Satz 6: Steuerbetrag auf vollen Euro **abgerundet**.
Tarif-Größen: `y = (zvE − 12.348)/10.000`, `z = (zvE − 17.799)/10.000`.
Zonen: Nr. 2 `(914,51·y + 1.400)·y`; Nr. 3
`(173,10·z + 2.397)·z + 1.034,87`; Nr. 4 `0,42·x − 11.135,63`;
Nr. 5 `0,45·x − 19.470,38`. Splitting (Abs. 5) = 2·Grundtarif(⌊zvE/2⌋).
§ 32 Abs. 6: je Kind (3.414 + 1.464)·faktor·Monate/12·auslandsfaktor.
§ 33 Abs. 3 zumutbare Belastung **staffelweise** (Stufen 15.340 /
51.130; Sätze ohne Kind Grund 5/6/7 %, Splitting 4/5/6 %; 1–2 Kinder
2/3/4 %; ≥3 Kinder 1/1/2 %). § 10b: Spenden ≤ max(20 % GdE; 4 ‰
Umsätze+Löhne). Modellierungs-Entscheidung: Kategorie-Abzugssummen
auf volle Euro abgerundet (s. est.findsl Datei-Doc).
--
verwende {
EstGrundtarif,
EstSplitting,
BerechneEinkommensteuer,
EinkommensteuerFall,
EinkommensteuerErgebnis,
Kind,
} aus "./est"
prüfe "§ 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)" {
testfall "zvE = 0 → 0" {
EstGrundtarif(0) == 0
}
testfall "zvE = Grundfreibetrag 12.348 → 0 (bis-Grenze inklusiv)" {
EstGrundtarif(12.348) == 0
}
testfall "zvE = 12.349 (Zone-2-Beginn) → 0 (Steuer rundet auf 0 ab)" {
// y = 1/10000 = 0,0001 → (914,51·0,0001 + 1.400)·0,0001
// = 0,14000914… → abrunden 0
EstGrundtarif(12.349) == 0
}
}
prüfe "§ 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)" {
testfall "zvE = 15.000" {
// y = (15.000 − 12.348)/10.000 = 0,2652
// (914,51·0,2652 + 1.400)·0,2652 = 435,5984… → abrunden 435
EstGrundtarif(15.000) == 435
}
testfall "zvE = 17.799 (obere Grenze Zone 2)" {
// y = (17.799 − 12.348)/10.000 = 0,5451
// (914,51·0,5451 + 1.400)·0,5451 = 1.034,99… → abrunden 1.034
EstGrundtarif(17.799) == 1.034
}
}
prüfe "§ 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)" {
testfall "zvE = 17.800 (Zone-3-Beginn)" {
// z = (17.800 − 17.799)/10.000 = 0,0001
// (173,10·0,0001 + 2.397)·0,0001 + 1.034,87 = 1.035,109… → 1.035
EstGrundtarif(17.800) == 1.035
}
testfall "zvE = 50.000" {
// z = (50.000 − 17.799)/10.000 = 3,2201
// (173,10·3,2201 + 2.397)·3,2201 + 1.034,87 = 10.548,… → 10.548
EstGrundtarif(50.000) == 10.548
}
testfall "zvE = 69.878 (obere Grenze Zone 3)" {
EstGrundtarif(69.878) == 18.213
}
}
prüfe "§ 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)" {
testfall "zvE = 69.879 (Zone-4-Beginn, stetiger Anschluss)" {
// 0,42·69.879 − 11.135,63 = 18.213,55 → abrunden 18.213
EstGrundtarif(69.879) == 18.213
}
testfall "zvE = 100.000" {
// 0,42·100.000 − 11.135,63 = 30.864,37 → abrunden 30.864
EstGrundtarif(100.000) == 30.864
}
testfall "zvE = 277.825 (obere Grenze Zone 4)" {
// 0,42·277.825 − 11.135,63 = 105.550,87 → abrunden 105.550
EstGrundtarif(277.825) == 105.550
}
}
prüfe "§ 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)" {
testfall "zvE = 277.826 (Zone-5-Beginn)" {
// 0,45·277.826 − 19.470,38 = 105.551,32 → abrunden 105.551
EstGrundtarif(277.826) == 105.551
}
testfall "zvE = 300.000" {
// 0,45·300.000 − 19.470,38 = 115.529,62 → abrunden 115.529
EstGrundtarif(300.000) == 115.529
}
}
prüfe "§ 32a Abs. 5 EStG — Splitting-Verfahren" {
testfall "zvE = 200.000 → 2 · Grundtarif(100.000) = 2 · 30.864" {
EstSplitting(200.000) == 61.728
}
testfall "zvE = 100.001 → Hälfte 50.000 (abgerundet) → 2 · 10.548" {
EstSplitting(100.001) == 21.096
}
testfall "zvE = 150.000 → Hälfte 75.000 → 2 · Grundtarif(75.000)" {
// 0,42·75.000 − 11.135,63 = 20.364,37 → 20.364 ; 2·20.364
EstSplitting(150.000) == 40.728
}
}
prüfe "§ 32a EStG — unzulässige Eingaben (abbruch)" {
testfall "negatives zvE (Grundtarif) ist nicht definiert" erwartet abbruch {
var n: Euro = -1
EstGrundtarif(n)
}
testfall "negatives gemeinsames zvE (Splitting) ist nicht definiert" erwartet abbruch {
var n: Euro = -2
EstSplitting(n)
}
}
prüfe "§ 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)" {
testfall "Fall K — Single, 2 Kinder, agB- + Spenden-Posten" {
// GdE 60.000. zumutbare Belastung (2 Kinder, Stufen 2/3/4 %):
// 2%·15.340 + 3%·(51.130−15.340) + 4%·(60.000−51.130)
// = 306,80 + 1.073,70 + 354,80 = 1.735,30
// agB abziehbar = nichtNeg(5.000 − 1.735,30).abrunden() = 3.264
// Spenden abziehbar = min(2.000; 20%·60.000=12.000) = 2.000
// SA = 4.000 + 2.000 = 6.000
// KFB = ((3.414+1.464)·1·12/12·100% ·2 Kinder).abrunden() = 9.756
// Einkommen = 60.000 − 6.000 − 3.264 = 50.736
// zvE = 50.736 − 9.756 = 40.980 → Grundtarif = 7.521
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 60.000,
sonstigeSonderausgaben = 4.000,
spenden = [2.000],
aussergewoehnlicheAufwendungen = [5.000],
kinder = [Kind(), Kind()],
))
e.gesamtbetragDerEinkuenfte == 60.000
und e.kinderfreibetraege == 9.756
und e.abziehbareAussergewoehnlicheBelastungen == 3.264
und e.einkommen == 50.736
und e.zuVersteuerndesEinkommen == 40.980
und e.tariflicheEinkommensteuer == 7.521
und e.festzusetzendeEinkommensteuer == 7.521
}
testfall "Fall S — Splitting, 3 Kinder (eines halbjährig), Spenden gekappt" {
// SdE = 100.000 → GdE 100.000. zumutbar (3 Kinder, 1/1/2 %):
// 1%·15.340 + 1%·35.790 + 2%·48.870 = 153,40+357,90+977,40 = 1.488,70
// agB abziehbar = (8.000 − 1.488,70).abrunden() = 6.511
// Spenden abziehbar = min(30.000; max(20%·100.000=20.000; 0)) = 20.000
// KFB Splitting faktor 2: 2·4.878·2 + 4.878·2·6/12 = 19.512 + 4.878 = 24.390
// Einkommen = 100.000 − 20.000 − 6.511 = 73.489
// zvE = 73.489 − 24.390 = 49.099 → Splitting=2·Grundtarif(24.549)=5.462
// festzusetzend = 5.462 − 2.500 + 600 = 3.562
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 100.000,
spenden = [10.000, 20.000],
aussergewoehnlicheAufwendungen = [3.000, 5.000],
kinder = [
Kind(faktor = 2),
Kind(faktor = 2),
Kind(faktor = 2, berücksichtigteMonate = 6),
],
tarifart = Splitting,
anrechnungenUndErmaessigungen = 2.500,
hinzurechnungen = 600,
))
e.kinderfreibetraege == 24.390
und e.abziehbareAussergewoehnlicheBelastungen == 6.511
und e.einkommen == 73.489
und e.zuVersteuerndesEinkommen == 49.099
und e.tariflicheEinkommensteuer == 5.462
und e.festzusetzendeEinkommensteuer == 3.562
}
testfall "Fall L — agB unter zumutbarer Belastung → 0 abziehbar" {
// GdE 40.000, 0 Kinder, Grundtarif: zumutbar
// 5%·15.340 + 6%·(40.000−15.340) = 767 + 1.479,60 = 2.246,60
// 1.000 < 2.246,60 → abziehbare agB = 0
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 40.000,
aussergewoehnlicheAufwendungen = [1.000],
))
e.abziehbareAussergewoehnlicheBelastungen == 0
und e.einkommen == 40.000
und e.zuVersteuerndesEinkommen == 40.000
und e.tariflicheEinkommensteuer == 7.209
}
testfall "Fall 0 — leere Listen ≙ alte Skalar-0-Kaskade (Regressionsanker)" {
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 50.000,
))
e.kinderfreibetraege == 0
und e.abziehbareAussergewoehnlicheBelastungen == 0
und e.einkommen == 50.000
und e.zuVersteuerndesEinkommen == 50.000
und e.tariflicheEinkommensteuer == 10.548
}
}Generierte Artefakte
Aus demselben Modul erzeugt die Toolchain ohne weiteres Zutun ausführbaren Code, Dokumentation und Programmablaufpläne — die Steuerregel bleibt die einzige Quelle der Wahrheit.
-
findsl codegen→ typisierter Java-, TypeScript- oder JavaScript-Code mit exakter Dezimalarithmetik. -
findsl docgen→ HTML-, Markdown- und PDF-Doku mit Paragraphen-Verweisen aus den@Quelle-Annotationen. -
findsl papgen→ Programmablaufpläne je Funktion (Mermaid oder self-contained HTML).
Quelle und Generat
Alle Dateien dieses Beispiels nebeneinander: links die FinDSL-Module, daneben sämtliche Artefakte, die die Toolchain daraus erzeugt — Java, TypeScript, JavaScript, die Dokumentation (Markdown, HTML, PDF) und die Programmablaufpläne. Zum Editieren und Prüfen im Playground öffnen.
Quelle
Generiert
Java
TypeScript
JavaScript
Doku
Diagramm
--
# Einkommensteuer — Veranlagungsschema § 2 EStG + Tarif § 32a EStG (VZ 2026)
Bildet die **Einkommensteuer-Kaskade** nach § 2 EStG ab, schließt mit
dem tariflichen Einkommensteuerbetrag (§ 32a) und der festzusetzenden
Einkommensteuer (§ 2 Abs. 6). Maßgebliche Quelle:
`examples/est/estg.xml` (juris-Stand 2026-05-06), § 32a/§ 32 Abs. 6 in
der konsolidierten Fassung „ab Veranlagungszeitraum 2026".
Gesetzliche Reihenfolge (jede Stufe = eigene Funktion, auditierbar):
Summe der Einkünfte (§ 2 Abs. 1–3) → Gesamtbetrag der Einkünfte
(§ 2 Abs. 3) → Einkommen (§ 2 Abs. 4) → zu versteuerndes Einkommen
(§ 2 Abs. 5) → tarifliche Einkommensteuer (§ 32a) → festzusetzende
Einkommensteuer (§ 2 Abs. 6).
**Echte Rechenvorschrift (modelliert) — auch mehr-entitätig:**
- **§ 32 Abs. 6 Kinderfreibetrag/BEA je Kind** über `Liste<Kind>`
(3.414 € + 1.464 € je Kind, Verdopplung Satz 2/3 per Faktor,
Zwölftelung Satz 5, Auslandskürzung Satz 4) → aggregiert.
- **§ 33 Abs. 1/3 außergewöhnliche Belastungen**: Summe der
zwangsläufigen Aufwendungen abzüglich der **zumutbaren Belastung**
(§ 33 Abs. 3, **staffelweise** über die drei GdE-Stufen × vier
Personengruppen).
- **§ 10b Abs. 1 Spenden**: abziehbar bis zum Höchstbetrag
max(20 % GdE; 4 ‰ (Umsätze + Löhne)).
- Die gesamte § 2-Verknüpfungs-Arithmetik + § 32a-Tarif + § 2 Abs. 6.
**Geprüfte Eingabe, weil anderes Recht / Verfahren (nicht Tooling-
Grenze):**
- **Ermittlung der sieben Einkunftsarten** je Art (Gewinn §§ 4–7k/13a,
Überschuss §§ 8–9a, § 20 Abs. 9, AfA § 7 mehrperiodig) — saldierter
Betrag je Art als Eingabe.
- **§ 24a / § 24b / § 13 Abs. 3** — Beträge als Eingabe (eigene §§).
- **Übrige Sonderausgaben §§ 10–10c** außer § 10b (Vorsorgeaufwen-
dungen mit eigenen Höchstbeträgen/Günstigerprüfung) — Aggregat-
Eingabe `sonstigeSonderausgaben`.
- **Verlustabzug § 10d** (mehrperiodig) — negatives zvE → 0 tariflich,
Verlustabzug selbst nicht modelliert.
- **Sachverhalte je Kind** (Kindschaftsverhältnis → `faktor`,
Auslands-Ländergruppe → `auslandsfaktor`, Berücksichtigungsmonate)
und die § 33-Zwangsläufigkeit/Angemessenheit (§ 33 Abs. 2),
§ 10b-Empfänger-Voraussetzungen (§ 10b Abs. 2) — Sachverhalt.
- **§ 32a Abs. 6** Witwen-/Gnadensplitting; **§ 2 Abs. 6-Komponenten**
(§§ 34c/35/35a/32d Abs. 3/4 …) als zwei gerichtete Aggregat-Eingaben;
Annexsteuern (SolZ, KiSt). Verfahren/eigene Gesetze.
**Modellierungs-Entscheidung (Statut schweigt):** jede listen-
abgeleitete Kategorie-Abzugssumme (Kinderfreibetrag, abziehbare agB,
abziehbare Spenden) wird auf **volle Euro abgerundet** (`.abrunden()`
mit Euro-Kontext),
bevor sie in die Euro-Kaskade eingeht — deterministisch, konsistent mit
§ 32a Abs. 1 Satz 1 (zvE auf volle Euro), fiskuskonservativ.
--
// ===========================================================================
// Konstanten — § 32a Absatz 1 EStG (Fassung ab VZ 2026)
// ===========================================================================
--
Grundfreibetrag — bis zu diesem zu versteuernden Einkommen beträgt die
tarifliche Einkommensteuer 0 (§ 32a Absatz 1 Satz 2 Nummer 1).
--
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 1 EStG")
konst GFB: Euro = 12.348
-- Obere Grenze der Eingangs-Progressionszone (Zone 2). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 2 EStG")
konst ZONE_2_OBERGRENZE: Euro = 17.799
-- Obere Grenze der Hauptprogressionszone (Zone 3). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
konst ZONE_3_OBERGRENZE: Euro = 69.878
-- Obere Grenze der ersten Proportionalzone (Zone 4); darüber Zone 5. --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 4 EStG")
konst ZONE_4_OBERGRENZE: Euro = 277.825
--
Teiler für die Größen „y" und „z": ein Zehntausendstel des den
jeweiligen Sockel übersteigenden, auf vollen Euro abgerundeten zvE
(§ 32a Absatz 1 Satz 3 und 4).
--
@Quelle("§ 32a Absatz 1 Satz 3 und 4 EStG")
konst ZEHNTAUSEND: Ganzzahl = 10.000
-- Progressionskoeffizient der Zone 2 (Faktor vor y²). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 2 EStG")
konst ZONE_2_PROGRESSION: Dezimal = 914,51
-- Linearer Koeffizient der Zone 2 (Faktor vor y). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 2 EStG")
konst ZONE_2_LINEAR: Dezimal = 1.400
-- Progressionskoeffizient der Zone 3 (Faktor vor z²). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
konst ZONE_3_PROGRESSION: Dezimal = 173,10
-- Linearer Koeffizient der Zone 3 (Faktor vor z). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
konst ZONE_3_LINEAR: Dezimal = 2.397
-- Konstanter Summand der Zone 3 (Anschluss an Zone 2). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
konst ZONE_3_KONSTANTE: Dezimal = 1.034,87
-- Grenzsteuersatz der Proportionalzone 4 (Spitzensteuersatz). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 4 EStG")
konst ZONE_4_SATZ: Prozent = 42%
-- Abzugsbetrag der Zone 4 (0,42 · x − ZONE_4_ABZUG). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 4 EStG")
konst ZONE_4_ABZUG: EuroCent = 11.135,63
-- Grenzsteuersatz der Proportionalzone 5 („Reichensteuer"). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 5 EStG")
konst ZONE_5_SATZ: Prozent = 45%
-- Abzugsbetrag der Zone 5 (0,45 · x − ZONE_5_ABZUG). --
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 5 EStG")
konst ZONE_5_ABZUG: EuroCent = 19.470,38
// ===========================================================================
// Konstanten — § 32 Abs. 6 (Kinderfreibetrag), § 33 Abs. 3, § 10b
// ===========================================================================
-- Kinderfreibetrag (sächliches Existenzminimum) je Kind. --
@Quelle("§ 32 Absatz 6 Satz 1 EStG")
konst KINDERFREIBETRAG: Euro = 3.414
-- Freibetrag Betreuungs-/Erziehungs-/Ausbildungsbedarf (BEA) je Kind. --
@Quelle("§ 32 Absatz 6 Satz 1 EStG")
konst BEA_FREIBETRAG: Euro = 1.464
-- Teiler für die Zwölftelung je nicht erfüllten Kalendermonat. --
@Quelle("§ 32 Absatz 6 Satz 5 EStG")
konst ZWOELF: Ganzzahl = 12
-- Erste GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3). --
@Quelle("§ 33 Absatz 3 EStG")
konst ZMB_STUFE_1: Euro = 15.340
-- Zweite GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3). --
@Quelle("§ 33 Absatz 3 EStG")
konst ZMB_STUFE_2: Euro = 51.130
-- Zumutbare Belastung — keine Kinder, Grundtarif (§ 32a Abs. 1): Stufe 1/2/3. --
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG")
konst ZMB_OHNE_KIND_GRUND_1: Prozent = 5%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG")
konst ZMB_OHNE_KIND_GRUND_2: Prozent = 6%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG")
konst ZMB_OHNE_KIND_GRUND_3: Prozent = 7%
-- Zumutbare Belastung — keine Kinder, Splitting (§ 32a Abs. 5/6): Stufe 1/2/3. --
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG")
konst ZMB_OHNE_KIND_SPLIT_1: Prozent = 4%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG")
konst ZMB_OHNE_KIND_SPLIT_2: Prozent = 5%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG")
konst ZMB_OHNE_KIND_SPLIT_3: Prozent = 6%
-- Zumutbare Belastung — ein oder zwei Kinder: Stufe 1/2/3. --
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG")
konst ZMB_1_2_KINDER_1: Prozent = 2%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG")
konst ZMB_1_2_KINDER_2: Prozent = 3%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG")
konst ZMB_1_2_KINDER_3: Prozent = 4%
-- Zumutbare Belastung — drei oder mehr Kinder: Stufe 1/2/3. --
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG")
konst ZMB_AB_3_KINDER_1: Prozent = 1%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG")
konst ZMB_AB_3_KINDER_2: Prozent = 1%
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG")
konst ZMB_AB_3_KINDER_3: Prozent = 2%
-- Spenden-Höchstbetrag Variante 1: Anteil des Gesamtbetrags der Einkünfte. --
@Quelle("§ 10b Absatz 1 Satz 1 Nummer 1 EStG")
konst SPENDEN_HB_GDE: Prozent = 20%
-- Spenden-Höchstbetrag Variante 2: Promille der Umsätze + Löhne (4 ‰). --
@Quelle("§ 10b Absatz 1 Satz 1 Nummer 2 EStG")
konst SPENDEN_HB_UMSATZ: Prozent = 0,4%
// ===========================================================================
// Tarifformel — § 32a Absatz 1 EStG
// ===========================================================================
--
Tariflicher Einkommensteuerbetrag nach dem Grundtarif (§ 32a Absatz 1
EStG). Das zu versteuernde Einkommen ist nach Satz 1 auf volle Euro
abgerundet zu verstehen (durch den `Euro`-Typ bereits ganzzahlig). Der
sich ergebende Steuerbetrag wird nach Satz 6 auf den nächsten vollen
Euro abgerundet.
Mit den Hilfsgrößen $y = \frac{\text{zvE} - \text{GFB}}{10000}$ (Zone 2)
und $z = \frac{\text{zvE} - \text{ZONE\_2}}{10000}$ (Zone 3) lautet der
Tarif zonenweise:
$$
\text{ESt}(\text{zvE}) =
\begin{cases}
0 & \text{zvE} \le \text{GFB} \\
(a_2\,y + b_2)\,y & \text{Zone 2} \\
(a_3\,z + b_3)\,z + c_3 & \text{Zone 3} \\
0{,}42 \cdot \text{zvE} - C_4 & \text{Zone 4} \\
0{,}45 \cdot \text{zvE} - C_5 & \text{Zone 5}
\end{cases}
$$
@param zve zu versteuerndes Einkommen in vollen Euro (geprüfte
Eingabe, ≥ 0; negativ → `abbruch`)
@rückgabe tarifliche Einkommensteuer in vollen Euro (Grundtarif)
--
@Quelle("§ 32a Absatz 1 EStG")
fn EstGrundtarif(zve: Euro): Euro = wähle {
falls zve < 0 als Euro -> abbruch("§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve})")
falls zve < GFB + 1 -> 0
falls zve < ZONE_2_OBERGRENZE + 1 -> {
var y: Dezimal = (zve - GFB) / ZEHNTAUSEND
var roh: Dezimal = (ZONE_2_PROGRESSION * y + ZONE_2_LINEAR) * y
roh.abrunden() als Euro
}
falls zve < ZONE_3_OBERGRENZE + 1 -> {
var z: Dezimal = (zve - ZONE_2_OBERGRENZE) / ZEHNTAUSEND
var roh: Dezimal = (ZONE_3_PROGRESSION * z + ZONE_3_LINEAR) * z + ZONE_3_KONSTANTE
roh.abrunden() als Euro
}
falls zve < ZONE_4_OBERGRENZE + 1 -> (ZONE_4_SATZ * zve - ZONE_4_ABZUG).abrunden()
sonst -> (ZONE_5_SATZ * zve - ZONE_5_ABZUG).abrunden()
}
--
Tariflicher Einkommensteuerbetrag nach dem Splitting-Verfahren für
zusammen veranlagte Ehegatten (§ 32a Absatz 5 EStG): das Zweifache des
Steuerbetrags, der sich für die Hälfte des gemeinsam zu versteuernden
Einkommens nach Absatz 1 ergibt. Die Hälfte wird nach Absatz 1 Satz 1
auf volle Euro abgerundet.
@param zve gemeinsam zu versteuerndes Einkommen der Ehegatten in vollen
Euro (geprüfte Eingabe, ≥ 0; negativ → `abbruch`)
@rückgabe tarifliche Einkommensteuer in vollen Euro (Splitting)
--
@Quelle("§ 32a Absatz 5 EStG")
fn EstSplitting(zve: Euro): Euro = wähle {
falls zve < 0 als Euro -> abbruch("§ 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve})")
sonst -> {
var halbesZve: Euro = (zve / 2).abrunden() als Euro
2 * EstGrundtarif(halbesZve)
}
}
// ===========================================================================
// Allgemeine Helfer (modul-intern)
// ===========================================================================
-- Anteil eines Euro-Betrags in der Staffel-Spanne [von, obereGrenze]. --
fn _Spanne(betrag: Euro, von: Euro, obereGrenze: Euro): Euro =
(betrag.höchstens(obereGrenze) - von).mindestens(0)
// ===========================================================================
// Veranlagungsschema — § 2 EStG (Kaskade zu versteuerndes Einkommen)
// ===========================================================================
//
// Veranlagungsform = EINGEBAUTE Aufzählung `Tarifart`
// (`Grundtarif`/`Splitting`, SPEC § 8.5) — global, kein Import.
--
Sachverhalte je Kind (§ 32 Abs. 6). Die Beträge sind Gesetz; diese
Felder sind die Sachverhalts-Eingaben je Kind.
@param faktor 1 = einfacher Freibetrag; 2 = verdoppelt
(§ 32 Abs. 6 Satz 2/3 — Kind zu beiden
Ehegatten bzw. Satz-3-Fälle)
@param berücksichtigteMonate Monate mit erfüllten Voraussetzungen
(§ 32 Abs. 6 Satz 5: je fehlendem Monat 1/12)
@param auslandsfaktor Ländergruppen-Anteil für Auslandskinder
(§ 32 Abs. 6 Satz 4; 100 % = Inlandskind)
--
@Quelle("§ 32 Absatz 6 EStG")
datensatz Kind(
faktor: Ganzzahl = 1, // § 32 Abs. 6 Satz 2/3
berücksichtigteMonate: Ganzzahl = 12, // § 32 Abs. 6 Satz 5
auslandsfaktor: Prozent = 100%, // § 32 Abs. 6 Satz 4
)
--
Eingaben für die Einkommensteuer-Veranlagung.
@param einkuenfteLandUndForstwirtschaft Einkünfte § 2 Abs. 1 Nr. 1 (§§ 13–14)
@param einkuenfteGewerbebetrieb Einkünfte § 2 Abs. 1 Nr. 2 (§§ 15–17)
@param einkuenfteSelbstaendigeArbeit Einkünfte § 2 Abs. 1 Nr. 3 (§ 18)
@param einkuenfteNichtselbstaendigeArbeit Einkünfte § 2 Abs. 1 Nr. 4 (§ 19)
@param einkuenfteKapitalvermoegen veranlagte Einkünfte § 2 Abs. 1 Nr. 5 (§ 20)
@param einkuenfteVermietungVerpachtung Einkünfte § 2 Abs. 1 Nr. 6 (§ 21)
@param sonstigeEinkuenfte sonstige Einkünfte § 2 Abs. 1 Nr. 7 (§ 22)
@param altersentlastungsbetrag Altersentlastungsbetrag (§ 24a)
@param entlastungsbetragAlleinerziehende Entlastungsbetrag Alleinerziehende (§ 24b)
@param freibetragLandUndForstwirtschaft Abzug nach § 13 Absatz 3
@param sonstigeSonderausgaben Sonderausgaben §§ 10–10c ohne § 10b
(Vorsorge u. a. — anderes Recht)
@param spenden abziehbare Zuwendungen § 10b Abs. 1
(Voraussetzungen Abs. 2 = Sachverhalt)
@param umsaetzeUndLoehne Basis der 4-‰-Höchstbetrags-
Variante (§ 10b Abs. 1 Satz 1 Nr. 2)
@param aussergewoehnlicheAufwendungen zwangsläufige Aufwendungen § 33
(Abs. 2 = Sachverhalt), vor
zumutbarer Belastung
@param kinder zu berücksichtigende Kinder (§ 32 Abs. 6)
@param sonstigeAbzuegeVomEinkommen sonstige vom Einkommen abzuziehende
Beträge (§ 2 Abs. 5 Satz 1)
@param tarifart Grund- oder Splittingtarif (§§ 26, 26b)
@param anrechnungenUndErmaessigungen § 2 Abs. 6 „vermindert um"
@param hinzurechnungen § 2 Abs. 6 „vermehrt um" (S. 1–3)
--
@Quelle("§ 2 EStG")
datensatz EinkommensteuerFall(
einkuenfteLandUndForstwirtschaft: Euro = 0, // § 2 Abs. 1 Nr. 1
einkuenfteGewerbebetrieb: Euro = 0, // § 2 Abs. 1 Nr. 2
einkuenfteSelbstaendigeArbeit: Euro = 0, // § 2 Abs. 1 Nr. 3
einkuenfteNichtselbstaendigeArbeit: Euro = 0, // § 2 Abs. 1 Nr. 4
einkuenfteKapitalvermoegen: Euro = 0, // § 2 Abs. 1 Nr. 5
einkuenfteVermietungVerpachtung: Euro = 0, // § 2 Abs. 1 Nr. 6
sonstigeEinkuenfte: Euro = 0, // § 2 Abs. 1 Nr. 7
altersentlastungsbetrag: Euro = 0, // § 24a
entlastungsbetragAlleinerziehende: Euro = 0, // § 24b
freibetragLandUndForstwirtschaft: Euro = 0, // § 13 Abs. 3
sonstigeSonderausgaben: Euro = 0, // §§ 10–10c o. § 10b
spenden: Liste<Euro> = []<Euro>, // § 10b Abs. 1
umsaetzeUndLoehne: Euro = 0, // § 10b Abs. 1 S. 1 Nr. 2
aussergewoehnlicheAufwendungen: Liste<Euro> = []<Euro>, // § 33
kinder: Liste<Kind> = []<Kind>, // § 32 Abs. 6
sonstigeAbzuegeVomEinkommen: Euro = 0, // § 2 Abs. 5 S. 1
tarifart: Tarifart = Grundtarif, // §§ 26, 26b
anrechnungenUndErmaessigungen: Euro = 0, // § 2 Abs. 6 S. 1
hinzurechnungen: Euro = 0, // § 2 Abs. 6 S. 1–3
)
--
Ergebnis der Veranlagung — jede Zwischengröße der gesetzlichen
Reihenfolge des § 2 EStG als eigenes Feld (Schritt-für-Schritt-Audit).
@param summeDerEinkuenfte Summe der Einkünfte (§ 2 Abs. 1–3)
@param gesamtbetragDerEinkuenfte Gesamtbetrag der Einkünfte (§ 2 Abs. 3)
@param kinderfreibetraege Freibeträge § 32 Abs. 6 (aggregiert)
@param abziehbareAussergewoehnlicheBelastungen § 33 nach zumutbarer Belastung
@param einkommen Einkommen (§ 2 Abs. 4)
@param zuVersteuerndesEinkommen zu versteuerndes Einkommen (§ 2 Abs. 5)
@param tariflicheEinkommensteuer tarifliche Einkommensteuer (§ 32a)
@param festzusetzendeEinkommensteuer festzusetzende Einkommensteuer (§ 2 Abs. 6)
--
@Quelle("§ 2 EStG")
datensatz EinkommensteuerErgebnis(
summeDerEinkuenfte: Euro, // § 2 Abs. 1–3
gesamtbetragDerEinkuenfte: Euro, // § 2 Abs. 3
kinderfreibetraege: Euro, // § 32 Abs. 6
abziehbareAussergewoehnlicheBelastungen: Euro, // § 33
einkommen: Euro, // § 2 Abs. 4
zuVersteuerndesEinkommen: Euro, // § 2 Abs. 5
tariflicheEinkommensteuer: Euro, // § 32a
festzusetzendeEinkommensteuer: Euro, // § 2 Abs. 6
)
--
Summe der Einkünfte (§ 2 Absatz 1 und 2 EStG): Summe der sieben
Einkunftsarten. Negative Einkünfte einzelner Arten mindern die Summe
(einkunftsartübergreifende Verlustverrechnungsbeschränkungen sind
anderes Recht und in den Eingaben bereits berücksichtigt).
@param fall die Veranlagungseingaben
@rückgabe Summe der Einkünfte in vollen Euro
--
@Quelle("§ 2 Absatz 1 und 2 EStG")
fn SummeDerEinkuenfte(fall: EinkommensteuerFall): Euro =
fall.einkuenfteLandUndForstwirtschaft
+ fall.einkuenfteGewerbebetrieb
+ fall.einkuenfteSelbstaendigeArbeit
+ fall.einkuenfteNichtselbstaendigeArbeit
+ fall.einkuenfteKapitalvermoegen
+ fall.einkuenfteVermietungVerpachtung
+ fall.sonstigeEinkuenfte
--
Gesamtbetrag der Einkünfte (§ 2 Absatz 3 EStG): Summe der Einkünfte
vermindert um Altersentlastungsbetrag (§ 24a), Entlastungsbetrag für
Alleinerziehende (§ 24b) und Abzug nach § 13 Absatz 3.
@param summe Summe der Einkünfte (Stufe zuvor)
@param fall die Veranlagungseingaben
@rückgabe Gesamtbetrag der Einkünfte in vollen Euro
--
@Quelle("§ 2 Absatz 3 EStG")
fn GesamtbetragDerEinkuenfte(summe: Euro, fall: EinkommensteuerFall): Euro =
summe
- fall.altersentlastungsbetrag
- fall.entlastungsbetragAlleinerziehende
- fall.freibetragLandUndForstwirtschaft
--
Kinderfreibetrag + BEA-Freibetrag, aggregiert über alle Kinder
(§ 32 Absatz 6 EStG): je Kind `(3.414 + 1.464) · faktor ·
berücksichtigteMonate/12 · auslandsfaktor`; die Summe wird auf volle
Euro abgerundet (Modellierungs-Entscheidung, s. Datei-Doc).
@param kinder die zu berücksichtigenden Kinder
@rückgabe Gesamt-Freibetrag in vollen Euro
--
@Quelle("§ 32 Absatz 6 EStG")
fn KinderfreibetragGesamt(kinder: Liste<Kind>): Euro =
(
kinder.zuordnen( {
k ->
(KINDERFREIBETRAG + BEA_FREIBETRAG)
* k.faktor
* (k.berücksichtigteMonate / ZWOELF)
* k.auslandsfaktor
}
).summe()
).abrunden()
--
Zumutbare Belastung (§ 33 Absatz 3 EStG) — **staffelweise** über die
drei GdE-Stufen (bis 15.340 / bis 51.130 / darüber), mit den
Prozentsätzen der vier Personengruppen (keine Kinder Grund/Splitting,
1–2 Kinder, ≥ 3 Kinder). „Kinder" sind die mit Freibetrag § 32 Abs. 6
oder Kindergeld-Anspruch (§ 33 Abs. 3 Satz 2 — hier `kinderzahl`).
@param gde Gesamtbetrag der Einkünfte
@param kinderzahl Zahl der zu berücksichtigenden Kinder
@param tarifart Grund- oder Splittingtarif (nur bei 0 Kindern relevant)
@rückgabe zumutbare Belastung (EuroCent-genau)
--
@Quelle("§ 33 Absatz 3 EStG")
fn ZumutbareBelastung(gde: Euro, kinderzahl: Ganzzahl, tarifart: Tarifart): EuroCent =
_ZmbSatz(1, kinderzahl, tarifart)
* _Spanne(gde, 0, ZMB_STUFE_1)
+ _ZmbSatz(2, kinderzahl, tarifart)
* _Spanne(gde, ZMB_STUFE_1, ZMB_STUFE_2)
+ _ZmbSatz(3, kinderzahl, tarifart)
* (gde - ZMB_STUFE_2).mindestens(0)
-- Prozentsatz der zumutbaren Belastung für GdE-Stufe (1/2/3). --
@Quelle("§ 33 Absatz 3 Satz 1 EStG")
fn _ZmbSatz(stufe: Ganzzahl, kinderzahl: Ganzzahl, tarifart: Tarifart): Prozent = wähle {
falls kinderzahl < 1 -> wähle (tarifart) {
falls Grundtarif -> wähle {
falls stufe < 2 -> ZMB_OHNE_KIND_GRUND_1
falls stufe < 3 -> ZMB_OHNE_KIND_GRUND_2
sonst -> ZMB_OHNE_KIND_GRUND_3
}
falls Splitting -> wähle {
falls stufe < 2 -> ZMB_OHNE_KIND_SPLIT_1
falls stufe < 3 -> ZMB_OHNE_KIND_SPLIT_2
sonst -> ZMB_OHNE_KIND_SPLIT_3
}
}
falls kinderzahl < 3 -> wähle {
falls stufe < 2 -> ZMB_1_2_KINDER_1
falls stufe < 3 -> ZMB_1_2_KINDER_2
sonst -> ZMB_1_2_KINDER_3
}
sonst -> wähle {
falls stufe < 2 -> ZMB_AB_3_KINDER_1
falls stufe < 3 -> ZMB_AB_3_KINDER_2
sonst -> ZMB_AB_3_KINDER_3
}
}
--
Abziehbare außergewöhnliche Belastungen (§ 33 Absatz 1 EStG): Summe der
zwangsläufigen Aufwendungen, soweit sie die zumutbare Belastung
(§ 33 Abs. 3) übersteigt; nie negativ, auf volle Euro abgerundet.
@param fall die Veranlagungseingaben
@param gde Gesamtbetrag der Einkünfte (Bezugsgröße der zumutbaren Belastung)
@rückgabe abziehbarer Betrag in vollen Euro
--
@Quelle("§ 33 Absatz 1 EStG")
fn AbziehbareAussergewoehnlicheBelastungen(fall: EinkommensteuerFall, gde: Euro): Euro =
(
(fall.aussergewoehnlicheAufwendungen.summe() als EuroCent)
- ZumutbareBelastung(gde, fall.kinder.länge, fall.tarifart)
).mindestens(0,00).abrunden()
--
Abziehbare Spenden (§ 10b Absatz 1 EStG): Summe der Zuwendungen,
gedeckelt auf den Höchstbetrag = größerer Wert aus 20 % des
Gesamtbetrags der Einkünfte und 4 ‰ der Umsätze + Löhne; auf volle
Euro abgerundet.
@param fall die Veranlagungseingaben
@param gde Gesamtbetrag der Einkünfte (Bezugsgröße Variante 1)
@rückgabe abziehbare Spenden in vollen Euro
--
@Quelle("§ 10b Absatz 1 EStG")
fn AbziehbareSpenden(fall: EinkommensteuerFall, gde: Euro): Euro = {
var grenzeGde: Euro = (SPENDEN_HB_GDE * gde).abrunden()
var grenzeUmsatz: Euro = (SPENDEN_HB_UMSATZ * fall.umsaetzeUndLoehne).abrunden()
var hoechstbetrag: Euro = grenzeGde.mindestens(grenzeUmsatz)
fall.spenden.summe().höchstens(hoechstbetrag)
}
--
Einkommen (§ 2 Absatz 4 EStG): Gesamtbetrag der Einkünfte vermindert
um die Sonderausgaben (sonstige + abziehbare Spenden § 10b) und die
abziehbaren außergewöhnlichen Belastungen (§ 33).
@param gesamtbetrag Gesamtbetrag der Einkünfte (Stufe zuvor)
@param fall die Veranlagungseingaben
@rückgabe Einkommen in vollen Euro
--
@Quelle("§ 2 Absatz 4 EStG")
fn Einkommen(gesamtbetrag: Euro, fall: EinkommensteuerFall): Euro =
gesamtbetrag
- fall.sonstigeSonderausgaben
- AbziehbareSpenden(fall, gesamtbetrag)
- AbziehbareAussergewoehnlicheBelastungen(fall, gesamtbetrag)
--
Zu versteuerndes Einkommen (§ 2 Absatz 5 Satz 1 EStG): Einkommen
vermindert um die Freibeträge nach § 32 Absatz 6 (Kinder) und die
sonstigen vom Einkommen abzuziehenden Beträge.
@param einkommen Einkommen (Stufe zuvor)
@param fall die Veranlagungseingaben
@rückgabe zu versteuerndes Einkommen in vollen Euro (kann bei
Verlusten negativ sein — § 10d nicht modelliert)
--
@Quelle("§ 2 Absatz 5 Satz 1 EStG")
fn ZuVersteuerndesEinkommen(einkommen: Euro, fall: EinkommensteuerFall): Euro =
einkommen
- KinderfreibetragGesamt(fall.kinder)
- fall.sonstigeAbzuegeVomEinkommen
--
Tarifliche Einkommensteuer (§ 32a EStG): Grund- oder Splittingtarif.
Negatives zvE → 0 (§ 32a für negatives zvE nicht definiert; § 10d
Verlustabzug ist Verfahren, nicht modelliert).
@param zve zu versteuerndes Einkommen in vollen Euro
@param tarifart Grund- oder Splittingtarif
@rückgabe tarifliche Einkommensteuer in vollen Euro
--
@Quelle("§ 32a Absatz 1 und 5 EStG")
fn TariflicheEinkommensteuer(zve: Euro, tarifart: Tarifart): Euro = wähle (tarifart) {
falls Grundtarif -> EstGrundtarif(zve.mindestens(0))
falls Splitting -> EstSplitting(zve.mindestens(0))
}
--
Festzusetzende Einkommensteuer (§ 2 Absatz 6 EStG): tarifliche Steuer
vermindert um Anrechnungen/Steuerermäßigungen, vermehrt um
Hinzurechnungen (Komponenten + Kappungen = anderes Recht/Eingabe;
keine Untergrenze — der Wortlaut sieht keine vor).
@param tariflich tarifliche Einkommensteuer (Stufe zuvor)
@param fall die Veranlagungseingaben
@rückgabe festzusetzende Einkommensteuer in vollen Euro
--
@Quelle("§ 2 Absatz 6 EStG")
fn FestzusetzendeEinkommensteuer(tariflich: Euro, fall: EinkommensteuerFall): Euro =
tariflich
- fall.anrechnungenUndErmaessigungen
+ fall.hinzurechnungen
--
Orchestrator — vollständige Veranlagung in gesetzlicher Reihenfolge
(§ 2 EStG). Füllt jede Zwischengröße ins Ergebnis-Datensatz.
@param fall die Veranlagungseingaben
@rückgabe das Veranlagungsergebnis mit allen Zwischengrößen
--
@Quelle("§ 2 EStG, § 32a EStG")
fn BerechneEinkommensteuer(fall: EinkommensteuerFall): EinkommensteuerErgebnis = {
var sde: Euro = SummeDerEinkuenfte(fall)
var gde: Euro = GesamtbetragDerEinkuenfte(sde, fall)
var kfb: Euro = KinderfreibetragGesamt(fall.kinder)
var agb: Euro = AbziehbareAussergewoehnlicheBelastungen(fall, gde)
var ein: Euro = Einkommen(gde, fall)
var zve: Euro = ZuVersteuerndesEinkommen(ein, fall)
var tariflich: Euro = TariflicheEinkommensteuer(zve, fall.tarifart)
var fest: Euro = FestzusetzendeEinkommensteuer(tariflich, fall)
EinkommensteuerErgebnis(
summeDerEinkuenfte = sde,
gesamtbetragDerEinkuenfte = gde,
kinderfreibetraege = kfb,
abziehbareAussergewoehnlicheBelastungen = agb,
einkommen = ein,
zuVersteuerndesEinkommen = zve,
tariflicheEinkommensteuer = tariflich,
festzusetzendeEinkommensteuer = fest,
)
}--
# Akzeptanztests — Einkommensteuer § 2 + § 32a EStG (VZ 2026)
Sollwerte **von Hand aus dem Wortlaut** gerechnet (Quelle
`examples/est/estg.xml`, Fassung „ab Veranlagungszeitraum 2026").
§ 32a Satz 6: Steuerbetrag auf vollen Euro **abgerundet**.
Tarif-Größen: `y = (zvE − 12.348)/10.000`, `z = (zvE − 17.799)/10.000`.
Zonen: Nr. 2 `(914,51·y + 1.400)·y`; Nr. 3
`(173,10·z + 2.397)·z + 1.034,87`; Nr. 4 `0,42·x − 11.135,63`;
Nr. 5 `0,45·x − 19.470,38`. Splitting (Abs. 5) = 2·Grundtarif(⌊zvE/2⌋).
§ 32 Abs. 6: je Kind (3.414 + 1.464)·faktor·Monate/12·auslandsfaktor.
§ 33 Abs. 3 zumutbare Belastung **staffelweise** (Stufen 15.340 /
51.130; Sätze ohne Kind Grund 5/6/7 %, Splitting 4/5/6 %; 1–2 Kinder
2/3/4 %; ≥3 Kinder 1/1/2 %). § 10b: Spenden ≤ max(20 % GdE; 4 ‰
Umsätze+Löhne). Modellierungs-Entscheidung: Kategorie-Abzugssummen
auf volle Euro abgerundet (s. est.findsl Datei-Doc).
--
verwende {
EstGrundtarif,
EstSplitting,
BerechneEinkommensteuer,
EinkommensteuerFall,
EinkommensteuerErgebnis,
Kind,
} aus "./est"
prüfe "§ 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)" {
testfall "zvE = 0 → 0" {
EstGrundtarif(0) == 0
}
testfall "zvE = Grundfreibetrag 12.348 → 0 (bis-Grenze inklusiv)" {
EstGrundtarif(12.348) == 0
}
testfall "zvE = 12.349 (Zone-2-Beginn) → 0 (Steuer rundet auf 0 ab)" {
// y = 1/10000 = 0,0001 → (914,51·0,0001 + 1.400)·0,0001
// = 0,14000914… → abrunden 0
EstGrundtarif(12.349) == 0
}
}
prüfe "§ 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)" {
testfall "zvE = 15.000" {
// y = (15.000 − 12.348)/10.000 = 0,2652
// (914,51·0,2652 + 1.400)·0,2652 = 435,5984… → abrunden 435
EstGrundtarif(15.000) == 435
}
testfall "zvE = 17.799 (obere Grenze Zone 2)" {
// y = (17.799 − 12.348)/10.000 = 0,5451
// (914,51·0,5451 + 1.400)·0,5451 = 1.034,99… → abrunden 1.034
EstGrundtarif(17.799) == 1.034
}
}
prüfe "§ 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)" {
testfall "zvE = 17.800 (Zone-3-Beginn)" {
// z = (17.800 − 17.799)/10.000 = 0,0001
// (173,10·0,0001 + 2.397)·0,0001 + 1.034,87 = 1.035,109… → 1.035
EstGrundtarif(17.800) == 1.035
}
testfall "zvE = 50.000" {
// z = (50.000 − 17.799)/10.000 = 3,2201
// (173,10·3,2201 + 2.397)·3,2201 + 1.034,87 = 10.548,… → 10.548
EstGrundtarif(50.000) == 10.548
}
testfall "zvE = 69.878 (obere Grenze Zone 3)" {
EstGrundtarif(69.878) == 18.213
}
}
prüfe "§ 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)" {
testfall "zvE = 69.879 (Zone-4-Beginn, stetiger Anschluss)" {
// 0,42·69.879 − 11.135,63 = 18.213,55 → abrunden 18.213
EstGrundtarif(69.879) == 18.213
}
testfall "zvE = 100.000" {
// 0,42·100.000 − 11.135,63 = 30.864,37 → abrunden 30.864
EstGrundtarif(100.000) == 30.864
}
testfall "zvE = 277.825 (obere Grenze Zone 4)" {
// 0,42·277.825 − 11.135,63 = 105.550,87 → abrunden 105.550
EstGrundtarif(277.825) == 105.550
}
}
prüfe "§ 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)" {
testfall "zvE = 277.826 (Zone-5-Beginn)" {
// 0,45·277.826 − 19.470,38 = 105.551,32 → abrunden 105.551
EstGrundtarif(277.826) == 105.551
}
testfall "zvE = 300.000" {
// 0,45·300.000 − 19.470,38 = 115.529,62 → abrunden 115.529
EstGrundtarif(300.000) == 115.529
}
}
prüfe "§ 32a Abs. 5 EStG — Splitting-Verfahren" {
testfall "zvE = 200.000 → 2 · Grundtarif(100.000) = 2 · 30.864" {
EstSplitting(200.000) == 61.728
}
testfall "zvE = 100.001 → Hälfte 50.000 (abgerundet) → 2 · 10.548" {
EstSplitting(100.001) == 21.096
}
testfall "zvE = 150.000 → Hälfte 75.000 → 2 · Grundtarif(75.000)" {
// 0,42·75.000 − 11.135,63 = 20.364,37 → 20.364 ; 2·20.364
EstSplitting(150.000) == 40.728
}
}
prüfe "§ 32a EStG — unzulässige Eingaben (abbruch)" {
testfall "negatives zvE (Grundtarif) ist nicht definiert" erwartet abbruch {
var n: Euro = -1
EstGrundtarif(n)
}
testfall "negatives gemeinsames zvE (Splitting) ist nicht definiert" erwartet abbruch {
var n: Euro = -2
EstSplitting(n)
}
}
prüfe "§ 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)" {
testfall "Fall K — Single, 2 Kinder, agB- + Spenden-Posten" {
// GdE 60.000. zumutbare Belastung (2 Kinder, Stufen 2/3/4 %):
// 2%·15.340 + 3%·(51.130−15.340) + 4%·(60.000−51.130)
// = 306,80 + 1.073,70 + 354,80 = 1.735,30
// agB abziehbar = nichtNeg(5.000 − 1.735,30).abrunden() = 3.264
// Spenden abziehbar = min(2.000; 20%·60.000=12.000) = 2.000
// SA = 4.000 + 2.000 = 6.000
// KFB = ((3.414+1.464)·1·12/12·100% ·2 Kinder).abrunden() = 9.756
// Einkommen = 60.000 − 6.000 − 3.264 = 50.736
// zvE = 50.736 − 9.756 = 40.980 → Grundtarif = 7.521
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 60.000,
sonstigeSonderausgaben = 4.000,
spenden = [2.000],
aussergewoehnlicheAufwendungen = [5.000],
kinder = [Kind(), Kind()],
))
e.gesamtbetragDerEinkuenfte == 60.000
und e.kinderfreibetraege == 9.756
und e.abziehbareAussergewoehnlicheBelastungen == 3.264
und e.einkommen == 50.736
und e.zuVersteuerndesEinkommen == 40.980
und e.tariflicheEinkommensteuer == 7.521
und e.festzusetzendeEinkommensteuer == 7.521
}
testfall "Fall S — Splitting, 3 Kinder (eines halbjährig), Spenden gekappt" {
// SdE = 100.000 → GdE 100.000. zumutbar (3 Kinder, 1/1/2 %):
// 1%·15.340 + 1%·35.790 + 2%·48.870 = 153,40+357,90+977,40 = 1.488,70
// agB abziehbar = (8.000 − 1.488,70).abrunden() = 6.511
// Spenden abziehbar = min(30.000; max(20%·100.000=20.000; 0)) = 20.000
// KFB Splitting faktor 2: 2·4.878·2 + 4.878·2·6/12 = 19.512 + 4.878 = 24.390
// Einkommen = 100.000 − 20.000 − 6.511 = 73.489
// zvE = 73.489 − 24.390 = 49.099 → Splitting=2·Grundtarif(24.549)=5.462
// festzusetzend = 5.462 − 2.500 + 600 = 3.562
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 100.000,
spenden = [10.000, 20.000],
aussergewoehnlicheAufwendungen = [3.000, 5.000],
kinder = [
Kind(faktor = 2),
Kind(faktor = 2),
Kind(faktor = 2, berücksichtigteMonate = 6),
],
tarifart = Splitting,
anrechnungenUndErmaessigungen = 2.500,
hinzurechnungen = 600,
))
e.kinderfreibetraege == 24.390
und e.abziehbareAussergewoehnlicheBelastungen == 6.511
und e.einkommen == 73.489
und e.zuVersteuerndesEinkommen == 49.099
und e.tariflicheEinkommensteuer == 5.462
und e.festzusetzendeEinkommensteuer == 3.562
}
testfall "Fall L — agB unter zumutbarer Belastung → 0 abziehbar" {
// GdE 40.000, 0 Kinder, Grundtarif: zumutbar
// 5%·15.340 + 6%·(40.000−15.340) = 767 + 1.479,60 = 2.246,60
// 1.000 < 2.246,60 → abziehbare agB = 0
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 40.000,
aussergewoehnlicheAufwendungen = [1.000],
))
e.abziehbareAussergewoehnlicheBelastungen == 0
und e.einkommen == 40.000
und e.zuVersteuerndesEinkommen == 40.000
und e.tariflicheEinkommensteuer == 7.209
}
testfall "Fall 0 — leere Listen ≙ alte Skalar-0-Kaskade (Regressionsanker)" {
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 50.000,
))
e.kinderfreibetraege == 0
und e.abziehbareAussergewoehnlicheBelastungen == 0
und e.einkommen == 50.000
und e.zuVersteuerndesEinkommen == 50.000
und e.tariflicheEinkommensteuer == 10.548
}
}import org.findsl.runtime.FinDslNumber;
import org.findsl.runtime.FinDslListe;
import org.findsl.runtime.Tarifart;
import org.findsl.runtime.Euro;
import org.findsl.runtime.EuroCent;
import org.findsl.runtime.Prozent;
import org.findsl.runtime.Ganzzahl;
import org.findsl.runtime.Dezimal;
import org.findsl.runtime.Quelle;
import javax.annotation.processing.Generated;
/**
* Generiert aus FinDSL — NICHT manuell editieren.
* Semantik-Orakel: der FinDSL-Interpreter (bit-genau).
*
* # Einkommensteuer — Veranlagungsschema § 2 EStG + Tarif § 32a EStG (VZ 2026)
*
* Bildet die **Einkommensteuer-Kaskade** nach § 2 EStG ab, schließt mit
* dem tariflichen Einkommensteuerbetrag (§ 32a) und der festzusetzenden
* Einkommensteuer (§ 2 Abs. 6). Maßgebliche Quelle:
* `examples/est/estg.xml` (juris-Stand 2026-05-06), § 32a/§ 32 Abs. 6 in
* der konsolidierten Fassung „ab Veranlagungszeitraum 2026".
*
* Gesetzliche Reihenfolge (jede Stufe = eigene Funktion, auditierbar):
* Summe der Einkünfte (§ 2 Abs. 1–3) → Gesamtbetrag der Einkünfte
* (§ 2 Abs. 3) → Einkommen (§ 2 Abs. 4) → zu versteuerndes Einkommen
* (§ 2 Abs. 5) → tarifliche Einkommensteuer (§ 32a) → festzusetzende
* Einkommensteuer (§ 2 Abs. 6).
*
* **Echte Rechenvorschrift (modelliert) — auch mehr-entitätig:**
* - **§ 32 Abs. 6 Kinderfreibetrag/BEA je Kind** über `Liste<Kind>`
* (3.414 € + 1.464 € je Kind, Verdopplung Satz 2/3 per Faktor,
* Zwölftelung Satz 5, Auslandskürzung Satz 4) → aggregiert.
* - **§ 33 Abs. 1/3 außergewöhnliche Belastungen**: Summe der
* zwangsläufigen Aufwendungen abzüglich der **zumutbaren Belastung**
* (§ 33 Abs. 3, **staffelweise** über die drei GdE-Stufen × vier
* Personengruppen).
* - **§ 10b Abs. 1 Spenden**: abziehbar bis zum Höchstbetrag
* max(20 % GdE; 4 ‰ (Umsätze + Löhne)).
* - Die gesamte § 2-Verknüpfungs-Arithmetik + § 32a-Tarif + § 2 Abs. 6.
*
* **Geprüfte Eingabe, weil anderes Recht / Verfahren (nicht Tooling-
* Grenze):**
* - **Ermittlung der sieben Einkunftsarten** je Art (Gewinn §§ 4–7k/13a,
* Überschuss §§ 8–9a, § 20 Abs. 9, AfA § 7 mehrperiodig) — saldierter
* Betrag je Art als Eingabe.
* - **§ 24a / § 24b / § 13 Abs. 3** — Beträge als Eingabe (eigene §§).
* - **Übrige Sonderausgaben §§ 10–10c** außer § 10b (Vorsorgeaufwen-
* dungen mit eigenen Höchstbeträgen/Günstigerprüfung) — Aggregat-
* Eingabe `sonstigeSonderausgaben`.
* - **Verlustabzug § 10d** (mehrperiodig) — negatives zvE → 0 tariflich,
* Verlustabzug selbst nicht modelliert.
* - **Sachverhalte je Kind** (Kindschaftsverhältnis → `faktor`,
* Auslands-Ländergruppe → `auslandsfaktor`, Berücksichtigungsmonate)
* und die § 33-Zwangsläufigkeit/Angemessenheit (§ 33 Abs. 2),
* § 10b-Empfänger-Voraussetzungen (§ 10b Abs. 2) — Sachverhalt.
* - **§ 32a Abs. 6** Witwen-/Gnadensplitting; **§ 2 Abs. 6-Komponenten**
* (§§ 34c/35/35a/32d Abs. 3/4 …) als zwei gerichtete Aggregat-Eingaben;
* Annexsteuern (SolZ, KiSt). Verfahren/eigene Gesetze.
*
* **Modellierungs-Entscheidung (Statut schweigt):** jede listen-
* abgeleitete Kategorie-Abzugssumme (Kinderfreibetrag, abziehbare agB,
* abziehbare Spenden) wird auf **volle Euro abgerundet** (`.abrunden()`
* mit Euro-Kontext),
* bevor sie in die Euro-Kaskade eingeht — deterministisch, konsistent mit
* § 32a Abs. 1 Satz 1 (zvE auf volle Euro), fiskuskonservativ.
*/
@Generated(value = "findsl.Generator")
public interface Est {
/**
* Tariflicher Einkommensteuerbetrag nach dem Grundtarif (§ 32a Absatz 1
* EStG). Das zu versteuernde Einkommen ist nach Satz 1 auf volle Euro
* abgerundet zu verstehen (durch den `Euro`-Typ bereits ganzzahlig). Der
* sich ergebende Steuerbetrag wird nach Satz 6 auf den nächsten vollen
* Euro abgerundet.
*
* Mit den Hilfsgrößen $y = \frac{\text{zvE} - \text{GFB}}{10000}$ (Zone 2)
* und $z = \frac{\text{zvE} - \text{ZONE\_2}}{10000}$ (Zone 3) lautet der
* Tarif zonenweise:
*
* $$
* \text{ESt}(\text{zvE}) =
* \begin{cases}
* 0 & \text{zvE} \le \text{GFB} \\
* (a_2\,y + b_2)\,y & \text{Zone 2} \\
* (a_3\,z + b_3)\,z + c_3 & \text{Zone 3} \\
* 0{,}42 \cdot \text{zvE} - C_4 & \text{Zone 4} \\
* 0{,}45 \cdot \text{zvE} - C_5 & \text{Zone 5}
* \end{cases}
* $$
*
* @param zve zu versteuerndes Einkommen in vollen Euro (geprüfte
* Eingabe, ≥ 0; negativ → `abbruch`)
* @return tarifliche Einkommensteuer in vollen Euro (Grundtarif)
*/
@Quelle("§ 32a Absatz 1 EStG")
Euro estGrundtarif(Euro zve);
/**
* Tariflicher Einkommensteuerbetrag nach dem Splitting-Verfahren für
* zusammen veranlagte Ehegatten (§ 32a Absatz 5 EStG): das Zweifache des
* Steuerbetrags, der sich für die Hälfte des gemeinsam zu versteuernden
* Einkommens nach Absatz 1 ergibt. Die Hälfte wird nach Absatz 1 Satz 1
* auf volle Euro abgerundet.
*
* @param zve gemeinsam zu versteuerndes Einkommen der Ehegatten in vollen
* Euro (geprüfte Eingabe, ≥ 0; negativ → `abbruch`)
* @return tarifliche Einkommensteuer in vollen Euro (Splitting)
*/
@Quelle("§ 32a Absatz 5 EStG")
Euro estSplitting(Euro zve);
/**
* Summe der Einkünfte (§ 2 Absatz 1 und 2 EStG): Summe der sieben
* Einkunftsarten. Negative Einkünfte einzelner Arten mindern die Summe
* (einkunftsartübergreifende Verlustverrechnungsbeschränkungen sind
* anderes Recht und in den Eingaben bereits berücksichtigt).
*
* @param fall die Veranlagungseingaben
* @return Summe der Einkünfte in vollen Euro
*/
@Quelle("§ 2 Absatz 1 und 2 EStG")
Euro summeDerEinkuenfte(EinkommensteuerFall fall);
/**
* Gesamtbetrag der Einkünfte (§ 2 Absatz 3 EStG): Summe der Einkünfte
* vermindert um Altersentlastungsbetrag (§ 24a), Entlastungsbetrag für
* Alleinerziehende (§ 24b) und Abzug nach § 13 Absatz 3.
*
* @param summe Summe der Einkünfte (Stufe zuvor)
* @param fall die Veranlagungseingaben
* @return Gesamtbetrag der Einkünfte in vollen Euro
*/
@Quelle("§ 2 Absatz 3 EStG")
Euro gesamtbetragDerEinkuenfte(Euro summe, EinkommensteuerFall fall);
/**
* Kinderfreibetrag + BEA-Freibetrag, aggregiert über alle Kinder
* (§ 32 Absatz 6 EStG): je Kind `(3.414 + 1.464) · faktor ·
* berücksichtigteMonate/12 · auslandsfaktor`; die Summe wird auf volle
* Euro abgerundet (Modellierungs-Entscheidung, s. Datei-Doc).
*
* @param kinder die zu berücksichtigenden Kinder
* @return Gesamt-Freibetrag in vollen Euro
*/
@Quelle("§ 32 Absatz 6 EStG")
Euro kinderfreibetragGesamt(FinDslListe<Kind> kinder);
/**
* Zumutbare Belastung (§ 33 Absatz 3 EStG) — **staffelweise** über die
* drei GdE-Stufen (bis 15.340 / bis 51.130 / darüber), mit den
* Prozentsätzen der vier Personengruppen (keine Kinder Grund/Splitting,
* 1–2 Kinder, ≥ 3 Kinder). „Kinder" sind die mit Freibetrag § 32 Abs. 6
* oder Kindergeld-Anspruch (§ 33 Abs. 3 Satz 2 — hier `kinderzahl`).
*
* @param gde Gesamtbetrag der Einkünfte
* @param kinderzahl Zahl der zu berücksichtigenden Kinder
* @param tarifart Grund- oder Splittingtarif (nur bei 0 Kindern relevant)
* @return zumutbare Belastung (EuroCent-genau)
*/
@Quelle("§ 33 Absatz 3 EStG")
EuroCent zumutbareBelastung(Euro gde, Ganzzahl kinderzahl, Tarifart tarifart);
/**
* Abziehbare außergewöhnliche Belastungen (§ 33 Absatz 1 EStG): Summe der
* zwangsläufigen Aufwendungen, soweit sie die zumutbare Belastung
* (§ 33 Abs. 3) übersteigt; nie negativ, auf volle Euro abgerundet.
*
* @param fall die Veranlagungseingaben
* @param gde Gesamtbetrag der Einkünfte (Bezugsgröße der zumutbaren Belastung)
* @return abziehbarer Betrag in vollen Euro
*/
@Quelle("§ 33 Absatz 1 EStG")
Euro abziehbareAussergewoehnlicheBelastungen(EinkommensteuerFall fall, Euro gde);
/**
* Abziehbare Spenden (§ 10b Absatz 1 EStG): Summe der Zuwendungen,
* gedeckelt auf den Höchstbetrag = größerer Wert aus 20 % des
* Gesamtbetrags der Einkünfte und 4 ‰ der Umsätze + Löhne; auf volle
* Euro abgerundet.
*
* @param fall die Veranlagungseingaben
* @param gde Gesamtbetrag der Einkünfte (Bezugsgröße Variante 1)
* @return abziehbare Spenden in vollen Euro
*/
@Quelle("§ 10b Absatz 1 EStG")
Euro abziehbareSpenden(EinkommensteuerFall fall, Euro gde);
/**
* Einkommen (§ 2 Absatz 4 EStG): Gesamtbetrag der Einkünfte vermindert
* um die Sonderausgaben (sonstige + abziehbare Spenden § 10b) und die
* abziehbaren außergewöhnlichen Belastungen (§ 33).
*
* @param gesamtbetrag Gesamtbetrag der Einkünfte (Stufe zuvor)
* @param fall die Veranlagungseingaben
* @return Einkommen in vollen Euro
*/
@Quelle("§ 2 Absatz 4 EStG")
Euro einkommen(Euro gesamtbetrag, EinkommensteuerFall fall);
/**
* Zu versteuerndes Einkommen (§ 2 Absatz 5 Satz 1 EStG): Einkommen
* vermindert um die Freibeträge nach § 32 Absatz 6 (Kinder) und die
* sonstigen vom Einkommen abzuziehenden Beträge.
*
* @param einkommen Einkommen (Stufe zuvor)
* @param fall die Veranlagungseingaben
* @return zu versteuerndes Einkommen in vollen Euro (kann bei
* Verlusten negativ sein — § 10d nicht modelliert)
*/
@Quelle("§ 2 Absatz 5 Satz 1 EStG")
Euro zuVersteuerndesEinkommen(Euro einkommen, EinkommensteuerFall fall);
/**
* Tarifliche Einkommensteuer (§ 32a EStG): Grund- oder Splittingtarif.
* Negatives zvE → 0 (§ 32a für negatives zvE nicht definiert; § 10d
* Verlustabzug ist Verfahren, nicht modelliert).
*
* @param zve zu versteuerndes Einkommen in vollen Euro
* @param tarifart Grund- oder Splittingtarif
* @return tarifliche Einkommensteuer in vollen Euro
*/
@Quelle("§ 32a Absatz 1 und 5 EStG")
Euro tariflicheEinkommensteuer(Euro zve, Tarifart tarifart);
/**
* Festzusetzende Einkommensteuer (§ 2 Absatz 6 EStG): tarifliche Steuer
* vermindert um Anrechnungen/Steuerermäßigungen, vermehrt um
* Hinzurechnungen (Komponenten + Kappungen = anderes Recht/Eingabe;
* keine Untergrenze — der Wortlaut sieht keine vor).
*
* @param tariflich tarifliche Einkommensteuer (Stufe zuvor)
* @param fall die Veranlagungseingaben
* @return festzusetzende Einkommensteuer in vollen Euro
*/
@Quelle("§ 2 Absatz 6 EStG")
Euro festzusetzendeEinkommensteuer(Euro tariflich, EinkommensteuerFall fall);
/**
* Orchestrator — vollständige Veranlagung in gesetzlicher Reihenfolge
* (§ 2 EStG). Füllt jede Zwischengröße ins Ergebnis-Datensatz.
*
* @param fall die Veranlagungseingaben
* @return das Veranlagungsergebnis mit allen Zwischengrößen
*/
@Quelle("§ 2 EStG, § 32a EStG")
EinkommensteuerErgebnis berechneEinkommensteuer(EinkommensteuerFall fall);
/**
* Sachverhalte je Kind (§ 32 Abs. 6). Die Beträge sind Gesetz; diese
* Felder sind die Sachverhalts-Eingaben je Kind.
*
* @param faktor 1 = einfacher Freibetrag; 2 = verdoppelt
* (§ 32 Abs. 6 Satz 2/3 — Kind zu beiden
* Ehegatten bzw. Satz-3-Fälle)
* @param berücksichtigteMonate Monate mit erfüllten Voraussetzungen
* (§ 32 Abs. 6 Satz 5: je fehlendem Monat 1/12)
* @param auslandsfaktor Ländergruppen-Anteil für Auslandskinder
* (§ 32 Abs. 6 Satz 4; 100 % = Inlandskind)
*/
@Quelle("§ 32 Absatz 6 EStG")
public record Kind(
Ganzzahl faktor,
Ganzzahl berücksichtigteMonate,
Prozent auslandsfaktor
) {}
/**
* Eingaben für die Einkommensteuer-Veranlagung.
*
* @param einkuenfteLandUndForstwirtschaft Einkünfte § 2 Abs. 1 Nr. 1 (§§ 13–14)
* @param einkuenfteGewerbebetrieb Einkünfte § 2 Abs. 1 Nr. 2 (§§ 15–17)
* @param einkuenfteSelbstaendigeArbeit Einkünfte § 2 Abs. 1 Nr. 3 (§ 18)
* @param einkuenfteNichtselbstaendigeArbeit Einkünfte § 2 Abs. 1 Nr. 4 (§ 19)
* @param einkuenfteKapitalvermoegen veranlagte Einkünfte § 2 Abs. 1 Nr. 5 (§ 20)
* @param einkuenfteVermietungVerpachtung Einkünfte § 2 Abs. 1 Nr. 6 (§ 21)
* @param sonstigeEinkuenfte sonstige Einkünfte § 2 Abs. 1 Nr. 7 (§ 22)
* @param altersentlastungsbetrag Altersentlastungsbetrag (§ 24a)
* @param entlastungsbetragAlleinerziehende Entlastungsbetrag Alleinerziehende (§ 24b)
* @param freibetragLandUndForstwirtschaft Abzug nach § 13 Absatz 3
* @param sonstigeSonderausgaben Sonderausgaben §§ 10–10c ohne § 10b
* (Vorsorge u. a. — anderes Recht)
* @param spenden abziehbare Zuwendungen § 10b Abs. 1
* (Voraussetzungen Abs. 2 = Sachverhalt)
* @param umsaetzeUndLoehne Basis der 4-‰-Höchstbetrags-
* Variante (§ 10b Abs. 1 Satz 1 Nr. 2)
* @param aussergewoehnlicheAufwendungen zwangsläufige Aufwendungen § 33
* (Abs. 2 = Sachverhalt), vor
* zumutbarer Belastung
* @param kinder zu berücksichtigende Kinder (§ 32 Abs. 6)
* @param sonstigeAbzuegeVomEinkommen sonstige vom Einkommen abzuziehende
* Beträge (§ 2 Abs. 5 Satz 1)
* @param tarifart Grund- oder Splittingtarif (§§ 26, 26b)
* @param anrechnungenUndErmaessigungen § 2 Abs. 6 „vermindert um"
* @param hinzurechnungen § 2 Abs. 6 „vermehrt um" (S. 1–3)
*/
@Quelle("§ 2 EStG")
public record EinkommensteuerFall(
Euro einkuenfteLandUndForstwirtschaft,
Euro einkuenfteGewerbebetrieb,
Euro einkuenfteSelbstaendigeArbeit,
Euro einkuenfteNichtselbstaendigeArbeit,
Euro einkuenfteKapitalvermoegen,
Euro einkuenfteVermietungVerpachtung,
Euro sonstigeEinkuenfte,
Euro altersentlastungsbetrag,
Euro entlastungsbetragAlleinerziehende,
Euro freibetragLandUndForstwirtschaft,
Euro sonstigeSonderausgaben,
FinDslListe<FinDslNumber> spenden,
Euro umsaetzeUndLoehne,
FinDslListe<FinDslNumber> aussergewoehnlicheAufwendungen,
FinDslListe<Kind> kinder,
Euro sonstigeAbzuegeVomEinkommen,
Tarifart tarifart,
Euro anrechnungenUndErmaessigungen,
Euro hinzurechnungen
) {}
/**
* Ergebnis der Veranlagung — jede Zwischengröße der gesetzlichen
* Reihenfolge des § 2 EStG als eigenes Feld (Schritt-für-Schritt-Audit).
*
* @param summeDerEinkuenfte Summe der Einkünfte (§ 2 Abs. 1–3)
* @param gesamtbetragDerEinkuenfte Gesamtbetrag der Einkünfte (§ 2 Abs. 3)
* @param kinderfreibetraege Freibeträge § 32 Abs. 6 (aggregiert)
* @param abziehbareAussergewoehnlicheBelastungen § 33 nach zumutbarer Belastung
* @param einkommen Einkommen (§ 2 Abs. 4)
* @param zuVersteuerndesEinkommen zu versteuerndes Einkommen (§ 2 Abs. 5)
* @param tariflicheEinkommensteuer tarifliche Einkommensteuer (§ 32a)
* @param festzusetzendeEinkommensteuer festzusetzende Einkommensteuer (§ 2 Abs. 6)
*/
@Quelle("§ 2 EStG")
public record EinkommensteuerErgebnis(
Euro summeDerEinkuenfte,
Euro gesamtbetragDerEinkuenfte,
Euro kinderfreibetraege,
Euro abziehbareAussergewoehnlicheBelastungen,
Euro einkommen,
Euro zuVersteuerndesEinkommen,
Euro tariflicheEinkommensteuer,
Euro festzusetzendeEinkommensteuer
) {}
/**
* Grundfreibetrag — bis zu diesem zu versteuernden Einkommen beträgt die
* tarifliche Einkommensteuer 0 (§ 32a Absatz 1 Satz 2 Nummer 1).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 1 EStG")
public static final Euro GFB = Euro.von(
FinDslNumber.ganzzahl("12348").withMoneyAnnotation(FinDslNumber.Type.Euro, "Konstante \"GFB\""));
/**
* Obere Grenze der Eingangs-Progressionszone (Zone 2).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 2 EStG")
public static final Euro ZONE_2_OBERGRENZE = Euro.von(
FinDslNumber.ganzzahl("17799").withMoneyAnnotation(FinDslNumber.Type.Euro, "Konstante \"ZONE_2_OBERGRENZE\""));
/**
* Obere Grenze der Hauptprogressionszone (Zone 3).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
public static final Euro ZONE_3_OBERGRENZE = Euro.von(
FinDslNumber.ganzzahl("69878").withMoneyAnnotation(FinDslNumber.Type.Euro, "Konstante \"ZONE_3_OBERGRENZE\""));
/**
* Obere Grenze der ersten Proportionalzone (Zone 4); darüber Zone 5.
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 4 EStG")
public static final Euro ZONE_4_OBERGRENZE = Euro.von(
FinDslNumber.ganzzahl("277825").withMoneyAnnotation(FinDslNumber.Type.Euro, "Konstante \"ZONE_4_OBERGRENZE\""));
/**
* Teiler für die Größen „y" und „z": ein Zehntausendstel des den
* jeweiligen Sockel übersteigenden, auf vollen Euro abgerundeten zvE
* (§ 32a Absatz 1 Satz 3 und 4).
*/
@Quelle("§ 32a Absatz 1 Satz 3 und 4 EStG")
public static final Ganzzahl ZEHNTAUSEND = Ganzzahl.von(FinDslNumber.ganzzahl("10000"));
/**
* Progressionskoeffizient der Zone 2 (Faktor vor y²).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 2 EStG")
public static final Dezimal ZONE_2_PROGRESSION = Dezimal.von(FinDslNumber.dezimal("914.51"));
/**
* Linearer Koeffizient der Zone 2 (Faktor vor y).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 2 EStG")
public static final Dezimal ZONE_2_LINEAR = Dezimal.von(FinDslNumber.ganzzahl("1400"));
/**
* Progressionskoeffizient der Zone 3 (Faktor vor z²).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
public static final Dezimal ZONE_3_PROGRESSION = Dezimal.von(FinDslNumber.dezimal("173.10"));
/**
* Linearer Koeffizient der Zone 3 (Faktor vor z).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
public static final Dezimal ZONE_3_LINEAR = Dezimal.von(FinDslNumber.ganzzahl("2397"));
/**
* Konstanter Summand der Zone 3 (Anschluss an Zone 2).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 3 EStG")
public static final Dezimal ZONE_3_KONSTANTE = Dezimal.von(FinDslNumber.dezimal("1034.87"));
/**
* Grenzsteuersatz der Proportionalzone 4 (Spitzensteuersatz).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 4 EStG")
public static final Prozent ZONE_4_SATZ = Prozent.von(FinDslNumber.prozent("0.42"));
/**
* Abzugsbetrag der Zone 4 (0,42 · x − ZONE_4_ABZUG).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 4 EStG")
public static final EuroCent ZONE_4_ABZUG = EuroCent.von(
FinDslNumber.dezimal("11135.63").withMoneyAnnotation(FinDslNumber.Type.EuroCent, "Konstante \"ZONE_4_ABZUG\""));
/**
* Grenzsteuersatz der Proportionalzone 5 („Reichensteuer").
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 5 EStG")
public static final Prozent ZONE_5_SATZ = Prozent.von(FinDslNumber.prozent("0.45"));
/**
* Abzugsbetrag der Zone 5 (0,45 · x − ZONE_5_ABZUG).
*/
@Quelle("§ 32a Absatz 1 Satz 2 Nummer 5 EStG")
public static final EuroCent ZONE_5_ABZUG = EuroCent.von(
FinDslNumber.dezimal("19470.38").withMoneyAnnotation(FinDslNumber.Type.EuroCent, "Konstante \"ZONE_5_ABZUG\""));
/**
* Kinderfreibetrag (sächliches Existenzminimum) je Kind.
*/
@Quelle("§ 32 Absatz 6 Satz 1 EStG")
public static final Euro KINDERFREIBETRAG = Euro.von(
FinDslNumber.ganzzahl("3414").withMoneyAnnotation(FinDslNumber.Type.Euro, "Konstante \"KINDERFREIBETRAG\""));
/**
* Freibetrag Betreuungs-/Erziehungs-/Ausbildungsbedarf (BEA) je Kind.
*/
@Quelle("§ 32 Absatz 6 Satz 1 EStG")
public static final Euro BEA_FREIBETRAG = Euro.von(
FinDslNumber.ganzzahl("1464").withMoneyAnnotation(FinDslNumber.Type.Euro, "Konstante \"BEA_FREIBETRAG\""));
/**
* Teiler für die Zwölftelung je nicht erfüllten Kalendermonat.
*/
@Quelle("§ 32 Absatz 6 Satz 5 EStG")
public static final Ganzzahl ZWOELF = Ganzzahl.von(FinDslNumber.ganzzahl("12"));
/**
* Erste GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3).
*/
@Quelle("§ 33 Absatz 3 EStG")
public static final Euro ZMB_STUFE_1 = Euro.von(
FinDslNumber.ganzzahl("15340").withMoneyAnnotation(FinDslNumber.Type.Euro, "Konstante \"ZMB_STUFE_1\""));
/**
* Zweite GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3).
*/
@Quelle("§ 33 Absatz 3 EStG")
public static final Euro ZMB_STUFE_2 = Euro.von(
FinDslNumber.ganzzahl("51130").withMoneyAnnotation(FinDslNumber.Type.Euro, "Konstante \"ZMB_STUFE_2\""));
/**
* Zumutbare Belastung — keine Kinder, Grundtarif (§ 32a Abs. 1): Stufe 1/2/3.
*/
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG")
public static final Prozent ZMB_OHNE_KIND_GRUND_1 = Prozent.von(FinDslNumber.prozent("0.05"));
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG")
public static final Prozent ZMB_OHNE_KIND_GRUND_2 = Prozent.von(FinDslNumber.prozent("0.06"));
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG")
public static final Prozent ZMB_OHNE_KIND_GRUND_3 = Prozent.von(FinDslNumber.prozent("0.07"));
/**
* Zumutbare Belastung — keine Kinder, Splitting (§ 32a Abs. 5/6): Stufe 1/2/3.
*/
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG")
public static final Prozent ZMB_OHNE_KIND_SPLIT_1 = Prozent.von(FinDslNumber.prozent("0.04"));
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG")
public static final Prozent ZMB_OHNE_KIND_SPLIT_2 = Prozent.von(FinDslNumber.prozent("0.05"));
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG")
public static final Prozent ZMB_OHNE_KIND_SPLIT_3 = Prozent.von(FinDslNumber.prozent("0.06"));
/**
* Zumutbare Belastung — ein oder zwei Kinder: Stufe 1/2/3.
*/
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG")
public static final Prozent ZMB_1_2_KINDER_1 = Prozent.von(FinDslNumber.prozent("0.02"));
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG")
public static final Prozent ZMB_1_2_KINDER_2 = Prozent.von(FinDslNumber.prozent("0.03"));
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG")
public static final Prozent ZMB_1_2_KINDER_3 = Prozent.von(FinDslNumber.prozent("0.04"));
/**
* Zumutbare Belastung — drei oder mehr Kinder: Stufe 1/2/3.
*/
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG")
public static final Prozent ZMB_AB_3_KINDER_1 = Prozent.von(FinDslNumber.prozent("0.01"));
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG")
public static final Prozent ZMB_AB_3_KINDER_2 = Prozent.von(FinDslNumber.prozent("0.01"));
@Quelle("§ 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG")
public static final Prozent ZMB_AB_3_KINDER_3 = Prozent.von(FinDslNumber.prozent("0.02"));
/**
* Spenden-Höchstbetrag Variante 1: Anteil des Gesamtbetrags der Einkünfte.
*/
@Quelle("§ 10b Absatz 1 Satz 1 Nummer 1 EStG")
public static final Prozent SPENDEN_HB_GDE = Prozent.von(FinDslNumber.prozent("0.2"));
/**
* Spenden-Höchstbetrag Variante 2: Promille der Umsätze + Löhne (4 ‰).
*/
@Quelle("§ 10b Absatz 1 Satz 1 Nummer 2 EStG")
public static final Prozent SPENDEN_HB_UMSATZ = Prozent.von(FinDslNumber.prozent("0.004"));
}import org.findsl.runtime.FinDslNumber;
import org.findsl.runtime.FinDslListe;
import org.findsl.runtime.Tarifart;
import org.findsl.runtime.FinDslAbort;
import org.findsl.runtime.FinDslRuntimeError;
import org.findsl.runtime.Euro;
import org.findsl.runtime.EuroCent;
import org.findsl.runtime.Ganzzahl;
import org.findsl.runtime.Quelle;
import javax.annotation.processing.Generated;
/**
* Generiert aus FinDSL — NICHT manuell editieren.
* Semantik-Orakel: der FinDSL-Interpreter (bit-genau).
*
* # Einkommensteuer — Veranlagungsschema § 2 EStG + Tarif § 32a EStG (VZ 2026)
*
* Bildet die **Einkommensteuer-Kaskade** nach § 2 EStG ab, schließt mit
* dem tariflichen Einkommensteuerbetrag (§ 32a) und der festzusetzenden
* Einkommensteuer (§ 2 Abs. 6). Maßgebliche Quelle:
* `examples/est/estg.xml` (juris-Stand 2026-05-06), § 32a/§ 32 Abs. 6 in
* der konsolidierten Fassung „ab Veranlagungszeitraum 2026".
*
* Gesetzliche Reihenfolge (jede Stufe = eigene Funktion, auditierbar):
* Summe der Einkünfte (§ 2 Abs. 1–3) → Gesamtbetrag der Einkünfte
* (§ 2 Abs. 3) → Einkommen (§ 2 Abs. 4) → zu versteuerndes Einkommen
* (§ 2 Abs. 5) → tarifliche Einkommensteuer (§ 32a) → festzusetzende
* Einkommensteuer (§ 2 Abs. 6).
*
* **Echte Rechenvorschrift (modelliert) — auch mehr-entitätig:**
* - **§ 32 Abs. 6 Kinderfreibetrag/BEA je Kind** über `Liste<Kind>`
* (3.414 € + 1.464 € je Kind, Verdopplung Satz 2/3 per Faktor,
* Zwölftelung Satz 5, Auslandskürzung Satz 4) → aggregiert.
* - **§ 33 Abs. 1/3 außergewöhnliche Belastungen**: Summe der
* zwangsläufigen Aufwendungen abzüglich der **zumutbaren Belastung**
* (§ 33 Abs. 3, **staffelweise** über die drei GdE-Stufen × vier
* Personengruppen).
* - **§ 10b Abs. 1 Spenden**: abziehbar bis zum Höchstbetrag
* max(20 % GdE; 4 ‰ (Umsätze + Löhne)).
* - Die gesamte § 2-Verknüpfungs-Arithmetik + § 32a-Tarif + § 2 Abs. 6.
*
* **Geprüfte Eingabe, weil anderes Recht / Verfahren (nicht Tooling-
* Grenze):**
* - **Ermittlung der sieben Einkunftsarten** je Art (Gewinn §§ 4–7k/13a,
* Überschuss §§ 8–9a, § 20 Abs. 9, AfA § 7 mehrperiodig) — saldierter
* Betrag je Art als Eingabe.
* - **§ 24a / § 24b / § 13 Abs. 3** — Beträge als Eingabe (eigene §§).
* - **Übrige Sonderausgaben §§ 10–10c** außer § 10b (Vorsorgeaufwen-
* dungen mit eigenen Höchstbeträgen/Günstigerprüfung) — Aggregat-
* Eingabe `sonstigeSonderausgaben`.
* - **Verlustabzug § 10d** (mehrperiodig) — negatives zvE → 0 tariflich,
* Verlustabzug selbst nicht modelliert.
* - **Sachverhalte je Kind** (Kindschaftsverhältnis → `faktor`,
* Auslands-Ländergruppe → `auslandsfaktor`, Berücksichtigungsmonate)
* und die § 33-Zwangsläufigkeit/Angemessenheit (§ 33 Abs. 2),
* § 10b-Empfänger-Voraussetzungen (§ 10b Abs. 2) — Sachverhalt.
* - **§ 32a Abs. 6** Witwen-/Gnadensplitting; **§ 2 Abs. 6-Komponenten**
* (§§ 34c/35/35a/32d Abs. 3/4 …) als zwei gerichtete Aggregat-Eingaben;
* Annexsteuern (SolZ, KiSt). Verfahren/eigene Gesetze.
*
* **Modellierungs-Entscheidung (Statut schweigt):** jede listen-
* abgeleitete Kategorie-Abzugssumme (Kinderfreibetrag, abziehbare agB,
* abziehbare Spenden) wird auf **volle Euro abgerundet** (`.abrunden()`
* mit Euro-Kontext),
* bevor sie in die Euro-Kaskade eingeht — deterministisch, konsistent mit
* § 32a Abs. 1 Satz 1 (zvE auf volle Euro), fiskuskonservativ.
*/
@Generated(value = "findsl.Generator")
class EstImpl implements Est {
@Quelle("§ 32a Absatz 1 EStG")
@Override
public Euro estGrundtarif(Euro zve) {
if (zve.compareValue(FinDslNumber.ganzzahl("0").cast(FinDslNumber.Type.Euro)) < 0) {
throw new FinDslAbort(
"§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=" + zve.asText() + ")");
}
if (zve.compareValue(GFB.add(FinDslNumber.ganzzahl("1"))) < 0) {
return Euro.von(FinDslNumber.ganzzahl("0"));
}
if (zve.compareValue(ZONE_2_OBERGRENZE.add(FinDslNumber.ganzzahl("1"))) < 0) {
final FinDslNumber y = zve.sub(GFB).div(ZEHNTAUSEND);
final FinDslNumber roh = ZONE_2_PROGRESSION.mul(y).add(ZONE_2_LINEAR).mul(y);
return Euro.von(roh.abrunden(FinDslNumber.Type.Euro).cast(FinDslNumber.Type.Euro));
}
if (zve.compareValue(ZONE_3_OBERGRENZE.add(FinDslNumber.ganzzahl("1"))) < 0) {
final FinDslNumber z = zve.sub(ZONE_2_OBERGRENZE).div(ZEHNTAUSEND);
final FinDslNumber roh = ZONE_3_PROGRESSION.mul(z).add(ZONE_3_LINEAR).mul(z).add(ZONE_3_KONSTANTE);
return Euro.von(roh.abrunden(FinDslNumber.Type.Euro).cast(FinDslNumber.Type.Euro));
}
if (zve.compareValue(ZONE_4_OBERGRENZE.add(FinDslNumber.ganzzahl("1"))) < 0) {
return Euro.von(ZONE_4_SATZ.mul(zve).sub(ZONE_4_ABZUG).abrunden(FinDslNumber.Type.Euro));
}
return Euro.von(ZONE_5_SATZ.mul(zve).sub(ZONE_5_ABZUG).abrunden(FinDslNumber.Type.Euro));
}
@Quelle("§ 32a Absatz 5 EStG")
@Override
public Euro estSplitting(Euro zve) {
if (zve.compareValue(FinDslNumber.ganzzahl("0").cast(FinDslNumber.Type.Euro)) < 0) {
throw new FinDslAbort(
"§ 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen darf nicht negativ sein (zvE="
+ zve.asText()
+ ")");
}
final FinDslNumber halbesZve = zve.div(FinDslNumber.ganzzahl("2"))
.abrunden(FinDslNumber.Type.Euro)
.cast(FinDslNumber.Type.Euro)
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"halbesZve\"");
return Euro.von(FinDslNumber.ganzzahl("2").mul(estGrundtarif(Euro.von(halbesZve))));
}
/**
* Anteil eines Euro-Betrags in der Staffel-Spanne [von, obereGrenze].
*/
protected FinDslNumber _spanne(FinDslNumber betrag, FinDslNumber von, FinDslNumber obereGrenze) {
return betrag.hoechstens(obereGrenze).sub(von).mindestens(FinDslNumber.ganzzahl("0"));
}
@Quelle("§ 2 Absatz 1 und 2 EStG")
@Override
public Euro summeDerEinkuenfte(EinkommensteuerFall fall) {
return Euro.von(
fall.einkuenfteLandUndForstwirtschaft()
.add(fall.einkuenfteGewerbebetrieb())
.add(fall.einkuenfteSelbstaendigeArbeit())
.add(fall.einkuenfteNichtselbstaendigeArbeit())
.add(fall.einkuenfteKapitalvermoegen())
.add(fall.einkuenfteVermietungVerpachtung())
.add(fall.sonstigeEinkuenfte()));
}
@Quelle("§ 2 Absatz 3 EStG")
@Override
public Euro gesamtbetragDerEinkuenfte(Euro summe, EinkommensteuerFall fall) {
return Euro.von(
summe.sub(fall.altersentlastungsbetrag())
.sub(fall.entlastungsbetragAlleinerziehende())
.sub(fall.freibetragLandUndForstwirtschaft()));
}
@Quelle("§ 32 Absatz 6 EStG")
@Override
public Euro kinderfreibetragGesamt(FinDslListe<Kind> kinder) {
return Euro.von(
kinder.zuordnen(
(k) -> KINDERFREIBETRAG.add(BEA_FREIBETRAG)
.mul(k.faktor())
.mul(k.berücksichtigteMonate().div(ZWOELF))
.mul(k.auslandsfaktor()))
.summe()
.abrunden(FinDslNumber.Type.Euro));
}
@Quelle("§ 33 Absatz 3 EStG")
@Override
public EuroCent zumutbareBelastung(Euro gde, Ganzzahl kinderzahl, Tarifart tarifart) {
return EuroCent.von(
_zmbSatz(FinDslNumber.ganzzahl("1"), kinderzahl, tarifart)
.mul(_spanne(gde, FinDslNumber.ganzzahl("0"), ZMB_STUFE_1))
.add(
_zmbSatz(FinDslNumber.ganzzahl("2"), kinderzahl, tarifart)
.mul(_spanne(gde, ZMB_STUFE_1, ZMB_STUFE_2)))
.add(
_zmbSatz(FinDslNumber.ganzzahl("3"), kinderzahl, tarifart)
.mul(gde.sub(ZMB_STUFE_2).mindestens(FinDslNumber.ganzzahl("0")))));
}
/**
* Prozentsatz der zumutbaren Belastung für GdE-Stufe (1/2/3).
*/
@Quelle("§ 33 Absatz 3 Satz 1 EStG")
protected FinDslNumber _zmbSatz(FinDslNumber stufe, FinDslNumber kinderzahl, Tarifart tarifart) {
if (kinderzahl.compareValue(FinDslNumber.ganzzahl("1")) < 0) {
if (tarifart == Tarifart.Grundtarif) {
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_OHNE_KIND_GRUND_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_OHNE_KIND_GRUND_2;
}
return ZMB_OHNE_KIND_GRUND_3;
}
if (tarifart == Tarifart.Splitting) {
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_OHNE_KIND_SPLIT_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_OHNE_KIND_SPLIT_2;
}
return ZMB_OHNE_KIND_SPLIT_3;
}
throw new FinDslRuntimeError("Kein falls-Arm passte (wähle, Codegen).");
}
if (kinderzahl.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_1_2_KINDER_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_1_2_KINDER_2;
}
return ZMB_1_2_KINDER_3;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_AB_3_KINDER_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_AB_3_KINDER_2;
}
return ZMB_AB_3_KINDER_3;
}
@Quelle("§ 33 Absatz 1 EStG")
@Override
public Euro abziehbareAussergewoehnlicheBelastungen(EinkommensteuerFall fall, Euro gde) {
return Euro.von(
fall.aussergewoehnlicheAufwendungen()
.summe()
.cast(FinDslNumber.Type.EuroCent)
.sub(zumutbareBelastung(Euro.von(gde), Ganzzahl.von(fall.kinder().laenge()), fall.tarifart()))
.mindestens(FinDslNumber.dezimal("0.00"))
.abrunden(FinDslNumber.Type.Euro));
}
@Quelle("§ 10b Absatz 1 EStG")
@Override
public Euro abziehbareSpenden(EinkommensteuerFall fall, Euro gde) {
final FinDslNumber grenzeGde = SPENDEN_HB_GDE.mul(gde)
.abrunden(FinDslNumber.Type.Euro)
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"grenzeGde\"");
final FinDslNumber grenzeUmsatz = SPENDEN_HB_UMSATZ.mul(fall.umsaetzeUndLoehne())
.abrunden(FinDslNumber.Type.Euro)
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"grenzeUmsatz\"");
final FinDslNumber hoechstbetrag = grenzeGde.mindestens(grenzeUmsatz)
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"hoechstbetrag\"");
return Euro.von(fall.spenden().summe().hoechstens(hoechstbetrag));
}
@Quelle("§ 2 Absatz 4 EStG")
@Override
public Euro einkommen(Euro gesamtbetrag, EinkommensteuerFall fall) {
return Euro.von(
gesamtbetrag.sub(fall.sonstigeSonderausgaben())
.sub(abziehbareSpenden(fall, Euro.von(gesamtbetrag)))
.sub(abziehbareAussergewoehnlicheBelastungen(fall, Euro.von(gesamtbetrag))));
}
@Quelle("§ 2 Absatz 5 Satz 1 EStG")
@Override
public Euro zuVersteuerndesEinkommen(Euro einkommen, EinkommensteuerFall fall) {
return Euro.von(einkommen.sub(kinderfreibetragGesamt(fall.kinder())).sub(fall.sonstigeAbzuegeVomEinkommen()));
}
@Quelle("§ 32a Absatz 1 und 5 EStG")
@Override
public Euro tariflicheEinkommensteuer(Euro zve, Tarifart tarifart) {
if (tarifart == Tarifart.Grundtarif) {
return Euro.von(estGrundtarif(Euro.von(zve.mindestens(FinDslNumber.ganzzahl("0")))));
}
if (tarifart == Tarifart.Splitting) {
return Euro.von(estSplitting(Euro.von(zve.mindestens(FinDslNumber.ganzzahl("0")))));
}
throw new FinDslRuntimeError("Kein falls-Arm passte (wähle, Codegen).");
}
@Quelle("§ 2 Absatz 6 EStG")
@Override
public Euro festzusetzendeEinkommensteuer(Euro tariflich, EinkommensteuerFall fall) {
return Euro.von(tariflich.sub(fall.anrechnungenUndErmaessigungen()).add(fall.hinzurechnungen()));
}
@Quelle("§ 2 EStG, § 32a EStG")
@Override
public EinkommensteuerErgebnis berechneEinkommensteuer(EinkommensteuerFall fall) {
final FinDslNumber sde = summeDerEinkuenfte(fall).withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"sde\"");
final FinDslNumber gde = gesamtbetragDerEinkuenfte(Euro.von(sde), fall)
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"gde\"");
final FinDslNumber kfb = kinderfreibetragGesamt(fall.kinder())
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"kfb\"");
final FinDslNumber agb = abziehbareAussergewoehnlicheBelastungen(fall, Euro.von(gde))
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"agb\"");
final FinDslNumber ein = einkommen(Euro.von(gde), fall)
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"ein\"");
final FinDslNumber zve = zuVersteuerndesEinkommen(Euro.von(ein), fall)
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"zve\"");
final FinDslNumber tariflich = tariflicheEinkommensteuer(Euro.von(zve), fall.tarifart())
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"tariflich\"");
final FinDslNumber fest = festzusetzendeEinkommensteuer(Euro.von(tariflich), fall)
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"fest\"");
return new EinkommensteuerErgebnis(
Euro.von(sde),
Euro.von(gde),
Euro.von(kfb),
Euro.von(agb),
Euro.von(ein),
Euro.von(zve),
Euro.von(tariflich),
Euro.von(fest));
}
}import javax.annotation.processing.Generated;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Nested;
import org.junit.jupiter.api.Test;
import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.junit.jupiter.api.Assertions.assertThrows;
import org.findsl.runtime.FinDslNumber;
import org.findsl.runtime.FinDslListe;
import org.findsl.runtime.Tarifart;
import org.findsl.runtime.FinDslAbort;
import org.findsl.runtime.Euro;
import org.findsl.runtime.Prozent;
import org.findsl.runtime.Ganzzahl;
/**
* Generierte JUnit5-Akzeptanztests aus FinDSL-`prüfe` — NICHT
* manuell editieren. Soll-Verhalten = der FinDSL-Interpreter
* (`pruefe.ts runPruefeDecl`); pass/fail/abbruch bit-genau.
*
* # Akzeptanztests — Einkommensteuer § 2 + § 32a EStG (VZ 2026)
*
* Sollwerte **von Hand aus dem Wortlaut** gerechnet (Quelle
* `examples/est/estg.xml`, Fassung „ab Veranlagungszeitraum 2026").
* § 32a Satz 6: Steuerbetrag auf vollen Euro **abgerundet**.
*
* Tarif-Größen: `y = (zvE − 12.348)/10.000`, `z = (zvE − 17.799)/10.000`.
* Zonen: Nr. 2 `(914,51·y + 1.400)·y`; Nr. 3
* `(173,10·z + 2.397)·z + 1.034,87`; Nr. 4 `0,42·x − 11.135,63`;
* Nr. 5 `0,45·x − 19.470,38`. Splitting (Abs. 5) = 2·Grundtarif(⌊zvE/2⌋).
*
* § 32 Abs. 6: je Kind (3.414 + 1.464)·faktor·Monate/12·auslandsfaktor.
* § 33 Abs. 3 zumutbare Belastung **staffelweise** (Stufen 15.340 /
* 51.130; Sätze ohne Kind Grund 5/6/7 %, Splitting 4/5/6 %; 1–2 Kinder
* 2/3/4 %; ≥3 Kinder 1/1/2 %). § 10b: Spenden ≤ max(20 % GdE; 4 ‰
* Umsätze+Löhne). Modellierungs-Entscheidung: Kategorie-Abzugssummen
* auf volle Euro abgerundet (s. est.findsl Datei-Doc).
*/
@Generated(value = "findsl.Generator")
public final class EstTest {
private final Est est = Factory.createEst();
@Nested
@DisplayName("§ 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)")
class Pruefe_0 {
@Test
@DisplayName("zvE = 0 → 0")
void testfall_0() {
assertTrue(est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("0"))).equalsValue(FinDslNumber.ganzzahl("0")));
}
@Test
@DisplayName("zvE = Grundfreibetrag 12.348 → 0 (bis-Grenze inklusiv)")
void testfall_1() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("12348"))).equalsValue(FinDslNumber.ganzzahl("0")));
}
@Test
@DisplayName("zvE = 12.349 (Zone-2-Beginn) → 0 (Steuer rundet auf 0 ab)")
void testfall_2() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("12349"))).equalsValue(FinDslNumber.ganzzahl("0")));
}
}
@Nested
@DisplayName("§ 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)")
class Pruefe_1 {
@Test
@DisplayName("zvE = 15.000")
void testfall_0() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("15000"))).equalsValue(FinDslNumber.ganzzahl("435")));
}
@Test
@DisplayName("zvE = 17.799 (obere Grenze Zone 2)")
void testfall_1() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("17799"))).equalsValue(FinDslNumber.ganzzahl("1034")));
}
}
@Nested
@DisplayName("§ 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)")
class Pruefe_2 {
@Test
@DisplayName("zvE = 17.800 (Zone-3-Beginn)")
void testfall_0() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("17800"))).equalsValue(FinDslNumber.ganzzahl("1035")));
}
@Test
@DisplayName("zvE = 50.000")
void testfall_1() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("50000")))
.equalsValue(FinDslNumber.ganzzahl("10548")));
}
@Test
@DisplayName("zvE = 69.878 (obere Grenze Zone 3)")
void testfall_2() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("69878")))
.equalsValue(FinDslNumber.ganzzahl("18213")));
}
}
@Nested
@DisplayName("§ 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)")
class Pruefe_3 {
@Test
@DisplayName("zvE = 69.879 (Zone-4-Beginn, stetiger Anschluss)")
void testfall_0() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("69879")))
.equalsValue(FinDslNumber.ganzzahl("18213")));
}
@Test
@DisplayName("zvE = 100.000")
void testfall_1() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("100000")))
.equalsValue(FinDslNumber.ganzzahl("30864")));
}
@Test
@DisplayName("zvE = 277.825 (obere Grenze Zone 4)")
void testfall_2() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("277825")))
.equalsValue(FinDslNumber.ganzzahl("105550")));
}
}
@Nested
@DisplayName("§ 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)")
class Pruefe_4 {
@Test
@DisplayName("zvE = 277.826 (Zone-5-Beginn)")
void testfall_0() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("277826")))
.equalsValue(FinDslNumber.ganzzahl("105551")));
}
@Test
@DisplayName("zvE = 300.000")
void testfall_1() {
assertTrue(
est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("300000")))
.equalsValue(FinDslNumber.ganzzahl("115529")));
}
}
@Nested
@DisplayName("§ 32a Abs. 5 EStG — Splitting-Verfahren")
class Pruefe_5 {
@Test
@DisplayName("zvE = 200.000 → 2 · Grundtarif(100.000) = 2 · 30.864")
void testfall_0() {
assertTrue(
est.estSplitting(Euro.von(FinDslNumber.ganzzahl("200000")))
.equalsValue(FinDslNumber.ganzzahl("61728")));
}
@Test
@DisplayName("zvE = 100.001 → Hälfte 50.000 (abgerundet) → 2 · 10.548")
void testfall_1() {
assertTrue(
est.estSplitting(Euro.von(FinDslNumber.ganzzahl("100001")))
.equalsValue(FinDslNumber.ganzzahl("21096")));
}
@Test
@DisplayName("zvE = 150.000 → Hälfte 75.000 → 2 · Grundtarif(75.000)")
void testfall_2() {
assertTrue(
est.estSplitting(Euro.von(FinDslNumber.ganzzahl("150000")))
.equalsValue(FinDslNumber.ganzzahl("40728")));
}
}
@Nested
@DisplayName("§ 32a EStG — unzulässige Eingaben (abbruch)")
class Pruefe_6 {
@Test
@DisplayName("negatives zvE (Grundtarif) ist nicht definiert")
void testfall_0() {
assertThrows(FinDslAbort.class, () -> {
final FinDslNumber n = FinDslNumber.ganzzahl("1")
.neg()
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"n\"");
est.estGrundtarif(Euro.von(n));
});
}
@Test
@DisplayName("negatives gemeinsames zvE (Splitting) ist nicht definiert")
void testfall_1() {
assertThrows(FinDslAbort.class, () -> {
final FinDslNumber n = FinDslNumber.ganzzahl("2")
.neg()
.withMoneyAnnotation(FinDslNumber.Type.Euro, "var \"n\"");
est.estSplitting(Euro.von(n));
});
}
}
@Nested
@DisplayName("§ 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)")
class Pruefe_7 {
@Test
@DisplayName("Fall K — Single, 2 Kinder, agB- + Spenden-Posten")
void testfall_0() {
final Est.EinkommensteuerErgebnis e = est.berechneEinkommensteuer(
new Est.EinkommensteuerFall(
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("60000")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("4000")),
FinDslListe.of(java.util.List.of(FinDslNumber.ganzzahl("2000"))),
Euro.von(FinDslNumber.ganzzahl("0")),
FinDslListe.of(java.util.List.of(FinDslNumber.ganzzahl("5000"))),
FinDslListe.of(
java.util.List.of(
new Est.Kind(
Ganzzahl.von(FinDslNumber.ganzzahl("1")),
Ganzzahl.von(FinDslNumber.ganzzahl("12")),
Prozent.von(FinDslNumber.prozent("1"))),
new Est.Kind(
Ganzzahl.von(FinDslNumber.ganzzahl("1")),
Ganzzahl.von(FinDslNumber.ganzzahl("12")),
Prozent.von(FinDslNumber.prozent("1"))))),
Euro.von(FinDslNumber.ganzzahl("0")),
Tarifart.Grundtarif,
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0"))));
assertTrue(e.gesamtbetragDerEinkuenfte().equalsValue(FinDslNumber.ganzzahl("60000")));
assertTrue(e.kinderfreibetraege().equalsValue(FinDslNumber.ganzzahl("9756")));
assertTrue(e.abziehbareAussergewoehnlicheBelastungen().equalsValue(FinDslNumber.ganzzahl("3264")));
assertTrue(e.einkommen().equalsValue(FinDslNumber.ganzzahl("50736")));
assertTrue(e.zuVersteuerndesEinkommen().equalsValue(FinDslNumber.ganzzahl("40980")));
assertTrue(e.tariflicheEinkommensteuer().equalsValue(FinDslNumber.ganzzahl("7521")));
assertTrue(e.festzusetzendeEinkommensteuer().equalsValue(FinDslNumber.ganzzahl("7521")));
}
@Test
@DisplayName("Fall S — Splitting, 3 Kinder (eines halbjährig), Spenden gekappt")
void testfall_1() {
final Est.EinkommensteuerErgebnis e = est.berechneEinkommensteuer(
new Est.EinkommensteuerFall(
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("100000")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
FinDslListe.of(java.util.List.of(FinDslNumber.ganzzahl("10000"), FinDslNumber.ganzzahl("20000"))),
Euro.von(FinDslNumber.ganzzahl("0")),
FinDslListe.of(java.util.List.of(FinDslNumber.ganzzahl("3000"), FinDslNumber.ganzzahl("5000"))),
FinDslListe.of(
java.util.List.of(
new Est.Kind(
Ganzzahl.von(FinDslNumber.ganzzahl("2")),
Ganzzahl.von(FinDslNumber.ganzzahl("12")),
Prozent.von(FinDslNumber.prozent("1"))),
new Est.Kind(
Ganzzahl.von(FinDslNumber.ganzzahl("2")),
Ganzzahl.von(FinDslNumber.ganzzahl("12")),
Prozent.von(FinDslNumber.prozent("1"))),
new Est.Kind(
Ganzzahl.von(FinDslNumber.ganzzahl("2")),
Ganzzahl.von(FinDslNumber.ganzzahl("6")),
Prozent.von(FinDslNumber.prozent("1"))))),
Euro.von(FinDslNumber.ganzzahl("0")),
Tarifart.Splitting,
Euro.von(FinDslNumber.ganzzahl("2500")),
Euro.von(FinDslNumber.ganzzahl("600"))));
assertTrue(e.kinderfreibetraege().equalsValue(FinDslNumber.ganzzahl("24390")));
assertTrue(e.abziehbareAussergewoehnlicheBelastungen().equalsValue(FinDslNumber.ganzzahl("6511")));
assertTrue(e.einkommen().equalsValue(FinDslNumber.ganzzahl("73489")));
assertTrue(e.zuVersteuerndesEinkommen().equalsValue(FinDslNumber.ganzzahl("49099")));
assertTrue(e.tariflicheEinkommensteuer().equalsValue(FinDslNumber.ganzzahl("5462")));
assertTrue(e.festzusetzendeEinkommensteuer().equalsValue(FinDslNumber.ganzzahl("3562")));
}
@Test
@DisplayName("Fall L — agB unter zumutbarer Belastung → 0 abziehbar")
void testfall_2() {
final Est.EinkommensteuerErgebnis e = est.berechneEinkommensteuer(
new Est.EinkommensteuerFall(
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("40000")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
FinDslListe.<FinDslNumber>empty(),
Euro.von(FinDslNumber.ganzzahl("0")),
FinDslListe.of(java.util.List.of(FinDslNumber.ganzzahl("1000"))),
FinDslListe.<Est.Kind>empty(),
Euro.von(FinDslNumber.ganzzahl("0")),
Tarifart.Grundtarif,
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0"))));
assertTrue(e.abziehbareAussergewoehnlicheBelastungen().equalsValue(FinDslNumber.ganzzahl("0")));
assertTrue(e.einkommen().equalsValue(FinDslNumber.ganzzahl("40000")));
assertTrue(e.zuVersteuerndesEinkommen().equalsValue(FinDslNumber.ganzzahl("40000")));
assertTrue(e.tariflicheEinkommensteuer().equalsValue(FinDslNumber.ganzzahl("7209")));
}
@Test
@DisplayName("Fall 0 — leere Listen ≙ alte Skalar-0-Kaskade (Regressionsanker)")
void testfall_3() {
final Est.EinkommensteuerErgebnis e = est.berechneEinkommensteuer(
new Est.EinkommensteuerFall(
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("50000")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0")),
FinDslListe.<FinDslNumber>empty(),
Euro.von(FinDslNumber.ganzzahl("0")),
FinDslListe.<FinDslNumber>empty(),
FinDslListe.<Est.Kind>empty(),
Euro.von(FinDslNumber.ganzzahl("0")),
Tarifart.Grundtarif,
Euro.von(FinDslNumber.ganzzahl("0")),
Euro.von(FinDslNumber.ganzzahl("0"))));
assertTrue(e.kinderfreibetraege().equalsValue(FinDslNumber.ganzzahl("0")));
assertTrue(e.abziehbareAussergewoehnlicheBelastungen().equalsValue(FinDslNumber.ganzzahl("0")));
assertTrue(e.einkommen().equalsValue(FinDslNumber.ganzzahl("50000")));
assertTrue(e.zuVersteuerndesEinkommen().equalsValue(FinDslNumber.ganzzahl("50000")));
assertTrue(e.tariflicheEinkommensteuer().equalsValue(FinDslNumber.ganzzahl("10548")));
}
}
}import javax.annotation.processing.Generated;
/**
* Komposition-Wurzel (generiert) — erzeugt die Modul-Instanzen dieses
* Pakets und verdrahtet ihre Abhängigkeiten per Konstruktor-Injektion.
* Geteilte, prozessweite Singletons. NICHT manuell editieren.
*/
@Generated(value = "findsl.Generator")
public final class Factory {
private Factory() {}
private static final Est EST = new EstImpl();
public static Est createEst() {
return EST;
}
}import { FinDslNumber, FinDslRuntimeError, FinDslAbort, FinDslListe, Euro, EuroCent, Prozent, Ganzzahl, Dezimal, Tarifart } from './runtime/index.js';
/**
* Generiert aus FinDSL — NICHT manuell editieren.
* Semantik-Orakel: der FinDSL-Interpreter (bit-genau).
*
* # Einkommensteuer — Veranlagungsschema § 2 EStG + Tarif § 32a EStG (VZ 2026)
*
* Bildet die **Einkommensteuer-Kaskade** nach § 2 EStG ab, schließt mit
* dem tariflichen Einkommensteuerbetrag (§ 32a) und der festzusetzenden
* Einkommensteuer (§ 2 Abs. 6). Maßgebliche Quelle:
* `examples/est/estg.xml` (juris-Stand 2026-05-06), § 32a/§ 32 Abs. 6 in
* der konsolidierten Fassung „ab Veranlagungszeitraum 2026".
*
* Gesetzliche Reihenfolge (jede Stufe = eigene Funktion, auditierbar):
* Summe der Einkünfte (§ 2 Abs. 1–3) → Gesamtbetrag der Einkünfte
* (§ 2 Abs. 3) → Einkommen (§ 2 Abs. 4) → zu versteuerndes Einkommen
* (§ 2 Abs. 5) → tarifliche Einkommensteuer (§ 32a) → festzusetzende
* Einkommensteuer (§ 2 Abs. 6).
*
* **Echte Rechenvorschrift (modelliert) — auch mehr-entitätig:**
* - **§ 32 Abs. 6 Kinderfreibetrag/BEA je Kind** über `Liste<Kind>`
* (3.414 € + 1.464 € je Kind, Verdopplung Satz 2/3 per Faktor,
* Zwölftelung Satz 5, Auslandskürzung Satz 4) → aggregiert.
* - **§ 33 Abs. 1/3 außergewöhnliche Belastungen**: Summe der
* zwangsläufigen Aufwendungen abzüglich der **zumutbaren Belastung**
* (§ 33 Abs. 3, **staffelweise** über die drei GdE-Stufen × vier
* Personengruppen).
* - **§ 10b Abs. 1 Spenden**: abziehbar bis zum Höchstbetrag
* max(20 % GdE; 4 ‰ (Umsätze + Löhne)).
* - Die gesamte § 2-Verknüpfungs-Arithmetik + § 32a-Tarif + § 2 Abs. 6.
*
* **Geprüfte Eingabe, weil anderes Recht / Verfahren (nicht Tooling-
* Grenze):**
* - **Ermittlung der sieben Einkunftsarten** je Art (Gewinn §§ 4–7k/13a,
* Überschuss §§ 8–9a, § 20 Abs. 9, AfA § 7 mehrperiodig) — saldierter
* Betrag je Art als Eingabe.
* - **§ 24a / § 24b / § 13 Abs. 3** — Beträge als Eingabe (eigene §§).
* - **Übrige Sonderausgaben §§ 10–10c** außer § 10b (Vorsorgeaufwen-
* dungen mit eigenen Höchstbeträgen/Günstigerprüfung) — Aggregat-
* Eingabe `sonstigeSonderausgaben`.
* - **Verlustabzug § 10d** (mehrperiodig) — negatives zvE → 0 tariflich,
* Verlustabzug selbst nicht modelliert.
* - **Sachverhalte je Kind** (Kindschaftsverhältnis → `faktor`,
* Auslands-Ländergruppe → `auslandsfaktor`, Berücksichtigungsmonate)
* und die § 33-Zwangsläufigkeit/Angemessenheit (§ 33 Abs. 2),
* § 10b-Empfänger-Voraussetzungen (§ 10b Abs. 2) — Sachverhalt.
* - **§ 32a Abs. 6** Witwen-/Gnadensplitting; **§ 2 Abs. 6-Komponenten**
* (§§ 34c/35/35a/32d Abs. 3/4 …) als zwei gerichtete Aggregat-Eingaben;
* Annexsteuern (SolZ, KiSt). Verfahren/eigene Gesetze.
*
* **Modellierungs-Entscheidung (Statut schweigt):** jede listen-
* abgeleitete Kategorie-Abzugssumme (Kinderfreibetrag, abziehbare agB,
* abziehbare Spenden) wird auf **volle Euro abgerundet** (`.abrunden()`
* mit Euro-Kontext),
* bevor sie in die Euro-Kaskade eingeht — deterministisch, konsistent mit
* § 32a Abs. 1 Satz 1 (zvE auf volle Euro), fiskuskonservativ.
*/
/**
* Sachverhalte je Kind (§ 32 Abs. 6). Die Beträge sind Gesetz; diese
* Felder sind die Sachverhalts-Eingaben je Kind.
*
* @param faktor 1 = einfacher Freibetrag; 2 = verdoppelt
* (§ 32 Abs. 6 Satz 2/3 — Kind zu beiden
* Ehegatten bzw. Satz-3-Fälle)
* @param berücksichtigteMonate Monate mit erfüllten Voraussetzungen
* (§ 32 Abs. 6 Satz 5: je fehlendem Monat 1/12)
* @param auslandsfaktor Ländergruppen-Anteil für Auslandskinder
* (§ 32 Abs. 6 Satz 4; 100 % = Inlandskind)
* @Quelle § 32 Absatz 6 EStG
*/
export class Kind {
constructor(
readonly faktor: Ganzzahl,
readonly berücksichtigteMonate: Ganzzahl,
readonly auslandsfaktor: Prozent,
) {}
}
/**
* Eingaben für die Einkommensteuer-Veranlagung.
*
* @param einkuenfteLandUndForstwirtschaft Einkünfte § 2 Abs. 1 Nr. 1 (§§ 13–14)
* @param einkuenfteGewerbebetrieb Einkünfte § 2 Abs. 1 Nr. 2 (§§ 15–17)
* @param einkuenfteSelbstaendigeArbeit Einkünfte § 2 Abs. 1 Nr. 3 (§ 18)
* @param einkuenfteNichtselbstaendigeArbeit Einkünfte § 2 Abs. 1 Nr. 4 (§ 19)
* @param einkuenfteKapitalvermoegen veranlagte Einkünfte § 2 Abs. 1 Nr. 5 (§ 20)
* @param einkuenfteVermietungVerpachtung Einkünfte § 2 Abs. 1 Nr. 6 (§ 21)
* @param sonstigeEinkuenfte sonstige Einkünfte § 2 Abs. 1 Nr. 7 (§ 22)
* @param altersentlastungsbetrag Altersentlastungsbetrag (§ 24a)
* @param entlastungsbetragAlleinerziehende Entlastungsbetrag Alleinerziehende (§ 24b)
* @param freibetragLandUndForstwirtschaft Abzug nach § 13 Absatz 3
* @param sonstigeSonderausgaben Sonderausgaben §§ 10–10c ohne § 10b
* (Vorsorge u. a. — anderes Recht)
* @param spenden abziehbare Zuwendungen § 10b Abs. 1
* (Voraussetzungen Abs. 2 = Sachverhalt)
* @param umsaetzeUndLoehne Basis der 4-‰-Höchstbetrags-
* Variante (§ 10b Abs. 1 Satz 1 Nr. 2)
* @param aussergewoehnlicheAufwendungen zwangsläufige Aufwendungen § 33
* (Abs. 2 = Sachverhalt), vor
* zumutbarer Belastung
* @param kinder zu berücksichtigende Kinder (§ 32 Abs. 6)
* @param sonstigeAbzuegeVomEinkommen sonstige vom Einkommen abzuziehende
* Beträge (§ 2 Abs. 5 Satz 1)
* @param tarifart Grund- oder Splittingtarif (§§ 26, 26b)
* @param anrechnungenUndErmaessigungen § 2 Abs. 6 „vermindert um"
* @param hinzurechnungen § 2 Abs. 6 „vermehrt um" (S. 1–3)
* @Quelle § 2 EStG
*/
export class EinkommensteuerFall {
constructor(
readonly einkuenfteLandUndForstwirtschaft: Euro,
readonly einkuenfteGewerbebetrieb: Euro,
readonly einkuenfteSelbstaendigeArbeit: Euro,
readonly einkuenfteNichtselbstaendigeArbeit: Euro,
readonly einkuenfteKapitalvermoegen: Euro,
readonly einkuenfteVermietungVerpachtung: Euro,
readonly sonstigeEinkuenfte: Euro,
readonly altersentlastungsbetrag: Euro,
readonly entlastungsbetragAlleinerziehende: Euro,
readonly freibetragLandUndForstwirtschaft: Euro,
readonly sonstigeSonderausgaben: Euro,
readonly spenden: FinDslListe<FinDslNumber>,
readonly umsaetzeUndLoehne: Euro,
readonly aussergewoehnlicheAufwendungen: FinDslListe<FinDslNumber>,
readonly kinder: FinDslListe<Kind>,
readonly sonstigeAbzuegeVomEinkommen: Euro,
readonly tarifart: Tarifart,
readonly anrechnungenUndErmaessigungen: Euro,
readonly hinzurechnungen: Euro,
) {}
}
/**
* Ergebnis der Veranlagung — jede Zwischengröße der gesetzlichen
* Reihenfolge des § 2 EStG als eigenes Feld (Schritt-für-Schritt-Audit).
*
* @param summeDerEinkuenfte Summe der Einkünfte (§ 2 Abs. 1–3)
* @param gesamtbetragDerEinkuenfte Gesamtbetrag der Einkünfte (§ 2 Abs. 3)
* @param kinderfreibetraege Freibeträge § 32 Abs. 6 (aggregiert)
* @param abziehbareAussergewoehnlicheBelastungen § 33 nach zumutbarer Belastung
* @param einkommen Einkommen (§ 2 Abs. 4)
* @param zuVersteuerndesEinkommen zu versteuerndes Einkommen (§ 2 Abs. 5)
* @param tariflicheEinkommensteuer tarifliche Einkommensteuer (§ 32a)
* @param festzusetzendeEinkommensteuer festzusetzende Einkommensteuer (§ 2 Abs. 6)
* @Quelle § 2 EStG
*/
export class EinkommensteuerErgebnis {
constructor(
readonly summeDerEinkuenfte: Euro,
readonly gesamtbetragDerEinkuenfte: Euro,
readonly kinderfreibetraege: Euro,
readonly abziehbareAussergewoehnlicheBelastungen: Euro,
readonly einkommen: Euro,
readonly zuVersteuerndesEinkommen: Euro,
readonly tariflicheEinkommensteuer: Euro,
readonly festzusetzendeEinkommensteuer: Euro,
) {}
}
/**
* Grundfreibetrag — bis zu diesem zu versteuernden Einkommen beträgt die
* tarifliche Einkommensteuer 0 (§ 32a Absatz 1 Satz 2 Nummer 1).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 1 EStG
*/
export const GFB: Euro = Euro.von(FinDslNumber.ganzzahl("12348").withMoneyAnnotation("Euro", "Konstante \"GFB\""));
/**
* Obere Grenze der Eingangs-Progressionszone (Zone 2).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 2 EStG
*/
export const ZONE_2_OBERGRENZE: Euro = Euro.von(FinDslNumber.ganzzahl("17799").withMoneyAnnotation("Euro", "Konstante \"ZONE_2_OBERGRENZE\""));
/**
* Obere Grenze der Hauptprogressionszone (Zone 3).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 3 EStG
*/
export const ZONE_3_OBERGRENZE: Euro = Euro.von(FinDslNumber.ganzzahl("69878").withMoneyAnnotation("Euro", "Konstante \"ZONE_3_OBERGRENZE\""));
/**
* Obere Grenze der ersten Proportionalzone (Zone 4); darüber Zone 5.
* @Quelle § 32a Absatz 1 Satz 2 Nummer 4 EStG
*/
export const ZONE_4_OBERGRENZE: Euro = Euro.von(FinDslNumber.ganzzahl("277825").withMoneyAnnotation("Euro", "Konstante \"ZONE_4_OBERGRENZE\""));
/**
* Teiler für die Größen „y" und „z": ein Zehntausendstel des den
* jeweiligen Sockel übersteigenden, auf vollen Euro abgerundeten zvE
* (§ 32a Absatz 1 Satz 3 und 4).
* @Quelle § 32a Absatz 1 Satz 3 und 4 EStG
*/
export const ZEHNTAUSEND: Ganzzahl = Ganzzahl.von(FinDslNumber.ganzzahl("10000"));
/**
* Progressionskoeffizient der Zone 2 (Faktor vor y²).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 2 EStG
*/
export const ZONE_2_PROGRESSION: Dezimal = Dezimal.von(FinDslNumber.dezimal("914.51"));
/**
* Linearer Koeffizient der Zone 2 (Faktor vor y).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 2 EStG
*/
export const ZONE_2_LINEAR: Dezimal = Dezimal.von(FinDslNumber.ganzzahl("1400"));
/**
* Progressionskoeffizient der Zone 3 (Faktor vor z²).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 3 EStG
*/
export const ZONE_3_PROGRESSION: Dezimal = Dezimal.von(FinDslNumber.dezimal("173.10"));
/**
* Linearer Koeffizient der Zone 3 (Faktor vor z).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 3 EStG
*/
export const ZONE_3_LINEAR: Dezimal = Dezimal.von(FinDslNumber.ganzzahl("2397"));
/**
* Konstanter Summand der Zone 3 (Anschluss an Zone 2).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 3 EStG
*/
export const ZONE_3_KONSTANTE: Dezimal = Dezimal.von(FinDslNumber.dezimal("1034.87"));
/**
* Grenzsteuersatz der Proportionalzone 4 (Spitzensteuersatz).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 4 EStG
*/
export const ZONE_4_SATZ: Prozent = Prozent.von(FinDslNumber.prozent("0.42"));
/**
* Abzugsbetrag der Zone 4 (0,42 · x − ZONE_4_ABZUG).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 4 EStG
*/
export const ZONE_4_ABZUG: EuroCent = EuroCent.von(FinDslNumber.dezimal("11135.63").withMoneyAnnotation("EuroCent", "Konstante \"ZONE_4_ABZUG\""));
/**
* Grenzsteuersatz der Proportionalzone 5 („Reichensteuer").
* @Quelle § 32a Absatz 1 Satz 2 Nummer 5 EStG
*/
export const ZONE_5_SATZ: Prozent = Prozent.von(FinDslNumber.prozent("0.45"));
/**
* Abzugsbetrag der Zone 5 (0,45 · x − ZONE_5_ABZUG).
* @Quelle § 32a Absatz 1 Satz 2 Nummer 5 EStG
*/
export const ZONE_5_ABZUG: EuroCent = EuroCent.von(FinDslNumber.dezimal("19470.38").withMoneyAnnotation("EuroCent", "Konstante \"ZONE_5_ABZUG\""));
/**
* Kinderfreibetrag (sächliches Existenzminimum) je Kind.
* @Quelle § 32 Absatz 6 Satz 1 EStG
*/
export const KINDERFREIBETRAG: Euro = Euro.von(FinDslNumber.ganzzahl("3414").withMoneyAnnotation("Euro", "Konstante \"KINDERFREIBETRAG\""));
/**
* Freibetrag Betreuungs-/Erziehungs-/Ausbildungsbedarf (BEA) je Kind.
* @Quelle § 32 Absatz 6 Satz 1 EStG
*/
export const BEA_FREIBETRAG: Euro = Euro.von(FinDslNumber.ganzzahl("1464").withMoneyAnnotation("Euro", "Konstante \"BEA_FREIBETRAG\""));
/**
* Teiler für die Zwölftelung je nicht erfüllten Kalendermonat.
* @Quelle § 32 Absatz 6 Satz 5 EStG
*/
export const ZWOELF: Ganzzahl = Ganzzahl.von(FinDslNumber.ganzzahl("12"));
/**
* Erste GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3).
* @Quelle § 33 Absatz 3 EStG
*/
export const ZMB_STUFE_1: Euro = Euro.von(FinDslNumber.ganzzahl("15340").withMoneyAnnotation("Euro", "Konstante \"ZMB_STUFE_1\""));
/**
* Zweite GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3).
* @Quelle § 33 Absatz 3 EStG
*/
export const ZMB_STUFE_2: Euro = Euro.von(FinDslNumber.ganzzahl("51130").withMoneyAnnotation("Euro", "Konstante \"ZMB_STUFE_2\""));
/**
* Zumutbare Belastung — keine Kinder, Grundtarif (§ 32a Abs. 1): Stufe 1/2/3.
* @Quelle § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG
*/
export const ZMB_OHNE_KIND_GRUND_1: Prozent = Prozent.von(FinDslNumber.prozent("0.05"));
/**
* @Quelle § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG
*/
export const ZMB_OHNE_KIND_GRUND_2: Prozent = Prozent.von(FinDslNumber.prozent("0.06"));
/**
* @Quelle § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG
*/
export const ZMB_OHNE_KIND_GRUND_3: Prozent = Prozent.von(FinDslNumber.prozent("0.07"));
/**
* Zumutbare Belastung — keine Kinder, Splitting (§ 32a Abs. 5/6): Stufe 1/2/3.
* @Quelle § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG
*/
export const ZMB_OHNE_KIND_SPLIT_1: Prozent = Prozent.von(FinDslNumber.prozent("0.04"));
/**
* @Quelle § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG
*/
export const ZMB_OHNE_KIND_SPLIT_2: Prozent = Prozent.von(FinDslNumber.prozent("0.05"));
/**
* @Quelle § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG
*/
export const ZMB_OHNE_KIND_SPLIT_3: Prozent = Prozent.von(FinDslNumber.prozent("0.06"));
/**
* Zumutbare Belastung — ein oder zwei Kinder: Stufe 1/2/3.
* @Quelle § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG
*/
export const ZMB_1_2_KINDER_1: Prozent = Prozent.von(FinDslNumber.prozent("0.02"));
/**
* @Quelle § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG
*/
export const ZMB_1_2_KINDER_2: Prozent = Prozent.von(FinDslNumber.prozent("0.03"));
/**
* @Quelle § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG
*/
export const ZMB_1_2_KINDER_3: Prozent = Prozent.von(FinDslNumber.prozent("0.04"));
/**
* Zumutbare Belastung — drei oder mehr Kinder: Stufe 1/2/3.
* @Quelle § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG
*/
export const ZMB_AB_3_KINDER_1: Prozent = Prozent.von(FinDslNumber.prozent("0.01"));
/**
* @Quelle § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG
*/
export const ZMB_AB_3_KINDER_2: Prozent = Prozent.von(FinDslNumber.prozent("0.01"));
/**
* @Quelle § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG
*/
export const ZMB_AB_3_KINDER_3: Prozent = Prozent.von(FinDslNumber.prozent("0.02"));
/**
* Spenden-Höchstbetrag Variante 1: Anteil des Gesamtbetrags der Einkünfte.
* @Quelle § 10b Absatz 1 Satz 1 Nummer 1 EStG
*/
export const SPENDEN_HB_GDE: Prozent = Prozent.von(FinDslNumber.prozent("0.2"));
/**
* Spenden-Höchstbetrag Variante 2: Promille der Umsätze + Löhne (4 ‰).
* @Quelle § 10b Absatz 1 Satz 1 Nummer 2 EStG
*/
export const SPENDEN_HB_UMSATZ: Prozent = Prozent.von(FinDslNumber.prozent("0.004"));
/**
* Tariflicher Einkommensteuerbetrag nach dem Grundtarif (§ 32a Absatz 1
* EStG). Das zu versteuernde Einkommen ist nach Satz 1 auf volle Euro
* abgerundet zu verstehen (durch den `Euro`-Typ bereits ganzzahlig). Der
* sich ergebende Steuerbetrag wird nach Satz 6 auf den nächsten vollen
* Euro abgerundet.
*
* Mit den Hilfsgrößen $y = \frac{\text{zvE} - \text{GFB}}{10000}$ (Zone 2)
* und $z = \frac{\text{zvE} - \text{ZONE\_2}}{10000}$ (Zone 3) lautet der
* Tarif zonenweise:
*
* $$
* \text{ESt}(\text{zvE}) =
* \begin{cases}
* 0 & \text{zvE} \le \text{GFB} \\
* (a_2\,y + b_2)\,y & \text{Zone 2} \\
* (a_3\,z + b_3)\,z + c_3 & \text{Zone 3} \\
* 0{,}42 \cdot \text{zvE} - C_4 & \text{Zone 4} \\
* 0{,}45 \cdot \text{zvE} - C_5 & \text{Zone 5}
* \end{cases}
* $$
*
* @param zve zu versteuerndes Einkommen in vollen Euro (geprüfte
* Eingabe, ≥ 0; negativ → `abbruch`)
* @returns tarifliche Einkommensteuer in vollen Euro (Grundtarif)
* @Quelle § 32a Absatz 1 EStG
*/
export function estGrundtarif(zve: Euro): Euro {
if (zve.compareValue(FinDslNumber.ganzzahl("0").cast("Euro")) < 0) {
throw new FinDslAbort("§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=" + zve.asText() + ")");
}
if (zve.compareValue(GFB.add(FinDslNumber.ganzzahl("1"))) < 0) {
return Euro.von(FinDslNumber.ganzzahl("0"));
}
if (zve.compareValue(ZONE_2_OBERGRENZE.add(FinDslNumber.ganzzahl("1"))) < 0) {
const y: FinDslNumber = zve.sub(GFB).div(ZEHNTAUSEND);
const roh: FinDslNumber = ZONE_2_PROGRESSION.mul(y).add(ZONE_2_LINEAR).mul(y);
return Euro.von(roh.abrunden("Euro").cast("Euro"));
}
if (zve.compareValue(ZONE_3_OBERGRENZE.add(FinDslNumber.ganzzahl("1"))) < 0) {
const z: FinDslNumber = zve.sub(ZONE_2_OBERGRENZE).div(ZEHNTAUSEND);
const roh: FinDslNumber = ZONE_3_PROGRESSION.mul(z).add(ZONE_3_LINEAR).mul(z).add(ZONE_3_KONSTANTE);
return Euro.von(roh.abrunden("Euro").cast("Euro"));
}
if (zve.compareValue(ZONE_4_OBERGRENZE.add(FinDslNumber.ganzzahl("1"))) < 0) {
return Euro.von(ZONE_4_SATZ.mul(zve).sub(ZONE_4_ABZUG).abrunden("Euro"));
}
return Euro.von(ZONE_5_SATZ.mul(zve).sub(ZONE_5_ABZUG).abrunden("Euro"));
}
/**
* Tariflicher Einkommensteuerbetrag nach dem Splitting-Verfahren für
* zusammen veranlagte Ehegatten (§ 32a Absatz 5 EStG): das Zweifache des
* Steuerbetrags, der sich für die Hälfte des gemeinsam zu versteuernden
* Einkommens nach Absatz 1 ergibt. Die Hälfte wird nach Absatz 1 Satz 1
* auf volle Euro abgerundet.
*
* @param zve gemeinsam zu versteuerndes Einkommen der Ehegatten in vollen
* Euro (geprüfte Eingabe, ≥ 0; negativ → `abbruch`)
* @returns tarifliche Einkommensteuer in vollen Euro (Splitting)
* @Quelle § 32a Absatz 5 EStG
*/
export function estSplitting(zve: Euro): Euro {
if (zve.compareValue(FinDslNumber.ganzzahl("0").cast("Euro")) < 0) {
throw new FinDslAbort("§ 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen darf nicht negativ sein (zvE=" + zve.asText() + ")");
}
const halbesZve: FinDslNumber = zve.div(FinDslNumber.ganzzahl("2")).abrunden("Euro").cast("Euro").withMoneyAnnotation("Euro", "var \"halbesZve\"");
return Euro.von(FinDslNumber.ganzzahl("2").mul(estGrundtarif(Euro.von(halbesZve))));
}
/**
* Anteil eines Euro-Betrags in der Staffel-Spanne [von, obereGrenze].
*/
function _spanne(betrag: FinDslNumber, von: FinDslNumber, obereGrenze: FinDslNumber): FinDslNumber {
return betrag.hoechstens(obereGrenze).sub(von).mindestens(FinDslNumber.ganzzahl("0"));
}
/**
* Summe der Einkünfte (§ 2 Absatz 1 und 2 EStG): Summe der sieben
* Einkunftsarten. Negative Einkünfte einzelner Arten mindern die Summe
* (einkunftsartübergreifende Verlustverrechnungsbeschränkungen sind
* anderes Recht und in den Eingaben bereits berücksichtigt).
*
* @param fall die Veranlagungseingaben
* @returns Summe der Einkünfte in vollen Euro
* @Quelle § 2 Absatz 1 und 2 EStG
*/
export function summeDerEinkuenfte(fall: EinkommensteuerFall): Euro {
return Euro.von(fall.einkuenfteLandUndForstwirtschaft.add(fall.einkuenfteGewerbebetrieb).add(fall.einkuenfteSelbstaendigeArbeit).add(fall.einkuenfteNichtselbstaendigeArbeit).add(fall.einkuenfteKapitalvermoegen).add(fall.einkuenfteVermietungVerpachtung).add(fall.sonstigeEinkuenfte));
}
/**
* Gesamtbetrag der Einkünfte (§ 2 Absatz 3 EStG): Summe der Einkünfte
* vermindert um Altersentlastungsbetrag (§ 24a), Entlastungsbetrag für
* Alleinerziehende (§ 24b) und Abzug nach § 13 Absatz 3.
*
* @param summe Summe der Einkünfte (Stufe zuvor)
* @param fall die Veranlagungseingaben
* @returns Gesamtbetrag der Einkünfte in vollen Euro
* @Quelle § 2 Absatz 3 EStG
*/
export function gesamtbetragDerEinkuenfte(summe: Euro, fall: EinkommensteuerFall): Euro {
return Euro.von(summe.sub(fall.altersentlastungsbetrag).sub(fall.entlastungsbetragAlleinerziehende).sub(fall.freibetragLandUndForstwirtschaft));
}
/**
* Kinderfreibetrag + BEA-Freibetrag, aggregiert über alle Kinder
* (§ 32 Absatz 6 EStG): je Kind `(3.414 + 1.464) · faktor ·
* berücksichtigteMonate/12 · auslandsfaktor`; die Summe wird auf volle
* Euro abgerundet (Modellierungs-Entscheidung, s. Datei-Doc).
*
* @param kinder die zu berücksichtigenden Kinder
* @returns Gesamt-Freibetrag in vollen Euro
* @Quelle § 32 Absatz 6 EStG
*/
export function kinderfreibetragGesamt(kinder: FinDslListe<Kind>): Euro {
return Euro.von(kinder.zuordnen((k) => KINDERFREIBETRAG.add(BEA_FREIBETRAG).mul(k.faktor).mul(k.berücksichtigteMonate.div(ZWOELF)).mul(k.auslandsfaktor)).summe().abrunden("Euro"));
}
/**
* Zumutbare Belastung (§ 33 Absatz 3 EStG) — **staffelweise** über die
* drei GdE-Stufen (bis 15.340 / bis 51.130 / darüber), mit den
* Prozentsätzen der vier Personengruppen (keine Kinder Grund/Splitting,
* 1–2 Kinder, ≥ 3 Kinder). „Kinder" sind die mit Freibetrag § 32 Abs. 6
* oder Kindergeld-Anspruch (§ 33 Abs. 3 Satz 2 — hier `kinderzahl`).
*
* @param gde Gesamtbetrag der Einkünfte
* @param kinderzahl Zahl der zu berücksichtigenden Kinder
* @param tarifart Grund- oder Splittingtarif (nur bei 0 Kindern relevant)
* @returns zumutbare Belastung (EuroCent-genau)
* @Quelle § 33 Absatz 3 EStG
*/
export function zumutbareBelastung(gde: Euro, kinderzahl: Ganzzahl, tarifart: Tarifart): EuroCent {
return EuroCent.von(_zmbSatz(FinDslNumber.ganzzahl("1"), kinderzahl, tarifart).mul(_spanne(gde, FinDslNumber.ganzzahl("0"), ZMB_STUFE_1)).add(_zmbSatz(FinDslNumber.ganzzahl("2"), kinderzahl, tarifart).mul(_spanne(gde, ZMB_STUFE_1, ZMB_STUFE_2))).add(_zmbSatz(FinDslNumber.ganzzahl("3"), kinderzahl, tarifart).mul(gde.sub(ZMB_STUFE_2).mindestens(FinDslNumber.ganzzahl("0")))));
}
/**
* Prozentsatz der zumutbaren Belastung für GdE-Stufe (1/2/3).
* @Quelle § 33 Absatz 3 Satz 1 EStG
*/
function _zmbSatz(stufe: FinDslNumber, kinderzahl: FinDslNumber, tarifart: Tarifart): FinDslNumber {
if (kinderzahl.compareValue(FinDslNumber.ganzzahl("1")) < 0) {
if (tarifart === Tarifart.Grundtarif) {
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_OHNE_KIND_GRUND_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_OHNE_KIND_GRUND_2;
}
return ZMB_OHNE_KIND_GRUND_3;
}
if (tarifart === Tarifart.Splitting) {
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_OHNE_KIND_SPLIT_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_OHNE_KIND_SPLIT_2;
}
return ZMB_OHNE_KIND_SPLIT_3;
}
throw new FinDslRuntimeError("Kein falls-Arm passte (wähle, Codegen).");
}
if (kinderzahl.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_1_2_KINDER_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_1_2_KINDER_2;
}
return ZMB_1_2_KINDER_3;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_AB_3_KINDER_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_AB_3_KINDER_2;
}
return ZMB_AB_3_KINDER_3;
}
/**
* Abziehbare außergewöhnliche Belastungen (§ 33 Absatz 1 EStG): Summe der
* zwangsläufigen Aufwendungen, soweit sie die zumutbare Belastung
* (§ 33 Abs. 3) übersteigt; nie negativ, auf volle Euro abgerundet.
*
* @param fall die Veranlagungseingaben
* @param gde Gesamtbetrag der Einkünfte (Bezugsgröße der zumutbaren Belastung)
* @returns abziehbarer Betrag in vollen Euro
* @Quelle § 33 Absatz 1 EStG
*/
export function abziehbareAussergewoehnlicheBelastungen(fall: EinkommensteuerFall, gde: Euro): Euro {
return Euro.von(fall.aussergewoehnlicheAufwendungen.summe().cast("EuroCent").sub(zumutbareBelastung(Euro.von(gde), Ganzzahl.von(fall.kinder.laenge()), fall.tarifart)).mindestens(FinDslNumber.dezimal("0.00")).abrunden("Euro"));
}
/**
* Abziehbare Spenden (§ 10b Absatz 1 EStG): Summe der Zuwendungen,
* gedeckelt auf den Höchstbetrag = größerer Wert aus 20 % des
* Gesamtbetrags der Einkünfte und 4 ‰ der Umsätze + Löhne; auf volle
* Euro abgerundet.
*
* @param fall die Veranlagungseingaben
* @param gde Gesamtbetrag der Einkünfte (Bezugsgröße Variante 1)
* @returns abziehbare Spenden in vollen Euro
* @Quelle § 10b Absatz 1 EStG
*/
export function abziehbareSpenden(fall: EinkommensteuerFall, gde: Euro): Euro {
const grenzeGde: FinDslNumber = SPENDEN_HB_GDE.mul(gde).abrunden("Euro").withMoneyAnnotation("Euro", "var \"grenzeGde\"");
const grenzeUmsatz: FinDslNumber = SPENDEN_HB_UMSATZ.mul(fall.umsaetzeUndLoehne).abrunden("Euro").withMoneyAnnotation("Euro", "var \"grenzeUmsatz\"");
const hoechstbetrag: FinDslNumber = grenzeGde.mindestens(grenzeUmsatz).withMoneyAnnotation("Euro", "var \"hoechstbetrag\"");
return Euro.von(fall.spenden.summe().hoechstens(hoechstbetrag));
}
/**
* Einkommen (§ 2 Absatz 4 EStG): Gesamtbetrag der Einkünfte vermindert
* um die Sonderausgaben (sonstige + abziehbare Spenden § 10b) und die
* abziehbaren außergewöhnlichen Belastungen (§ 33).
*
* @param gesamtbetrag Gesamtbetrag der Einkünfte (Stufe zuvor)
* @param fall die Veranlagungseingaben
* @returns Einkommen in vollen Euro
* @Quelle § 2 Absatz 4 EStG
*/
export function einkommen(gesamtbetrag: Euro, fall: EinkommensteuerFall): Euro {
return Euro.von(gesamtbetrag.sub(fall.sonstigeSonderausgaben).sub(abziehbareSpenden(fall, Euro.von(gesamtbetrag))).sub(abziehbareAussergewoehnlicheBelastungen(fall, Euro.von(gesamtbetrag))));
}
/**
* Zu versteuerndes Einkommen (§ 2 Absatz 5 Satz 1 EStG): Einkommen
* vermindert um die Freibeträge nach § 32 Absatz 6 (Kinder) und die
* sonstigen vom Einkommen abzuziehenden Beträge.
*
* @param einkommen Einkommen (Stufe zuvor)
* @param fall die Veranlagungseingaben
* @returns zu versteuerndes Einkommen in vollen Euro (kann bei
* Verlusten negativ sein — § 10d nicht modelliert)
* @Quelle § 2 Absatz 5 Satz 1 EStG
*/
export function zuVersteuerndesEinkommen(einkommen: Euro, fall: EinkommensteuerFall): Euro {
return Euro.von(einkommen.sub(kinderfreibetragGesamt(fall.kinder)).sub(fall.sonstigeAbzuegeVomEinkommen));
}
/**
* Tarifliche Einkommensteuer (§ 32a EStG): Grund- oder Splittingtarif.
* Negatives zvE → 0 (§ 32a für negatives zvE nicht definiert; § 10d
* Verlustabzug ist Verfahren, nicht modelliert).
*
* @param zve zu versteuerndes Einkommen in vollen Euro
* @param tarifart Grund- oder Splittingtarif
* @returns tarifliche Einkommensteuer in vollen Euro
* @Quelle § 32a Absatz 1 und 5 EStG
*/
export function tariflicheEinkommensteuer(zve: Euro, tarifart: Tarifart): Euro {
if (tarifart === Tarifart.Grundtarif) {
return Euro.von(estGrundtarif(Euro.von(zve.mindestens(FinDslNumber.ganzzahl("0")))));
}
if (tarifart === Tarifart.Splitting) {
return Euro.von(estSplitting(Euro.von(zve.mindestens(FinDslNumber.ganzzahl("0")))));
}
throw new FinDslRuntimeError("Kein falls-Arm passte (wähle, Codegen).");
}
/**
* Festzusetzende Einkommensteuer (§ 2 Absatz 6 EStG): tarifliche Steuer
* vermindert um Anrechnungen/Steuerermäßigungen, vermehrt um
* Hinzurechnungen (Komponenten + Kappungen = anderes Recht/Eingabe;
* keine Untergrenze — der Wortlaut sieht keine vor).
*
* @param tariflich tarifliche Einkommensteuer (Stufe zuvor)
* @param fall die Veranlagungseingaben
* @returns festzusetzende Einkommensteuer in vollen Euro
* @Quelle § 2 Absatz 6 EStG
*/
export function festzusetzendeEinkommensteuer(tariflich: Euro, fall: EinkommensteuerFall): Euro {
return Euro.von(tariflich.sub(fall.anrechnungenUndErmaessigungen).add(fall.hinzurechnungen));
}
/**
* Orchestrator — vollständige Veranlagung in gesetzlicher Reihenfolge
* (§ 2 EStG). Füllt jede Zwischengröße ins Ergebnis-Datensatz.
*
* @param fall die Veranlagungseingaben
* @returns das Veranlagungsergebnis mit allen Zwischengrößen
* @Quelle § 2 EStG, § 32a EStG
*/
export function berechneEinkommensteuer(fall: EinkommensteuerFall): EinkommensteuerErgebnis {
const sde: FinDslNumber = summeDerEinkuenfte(fall).withMoneyAnnotation("Euro", "var \"sde\"");
const gde: FinDslNumber = gesamtbetragDerEinkuenfte(Euro.von(sde), fall).withMoneyAnnotation("Euro", "var \"gde\"");
const kfb: FinDslNumber = kinderfreibetragGesamt(fall.kinder).withMoneyAnnotation("Euro", "var \"kfb\"");
const agb: FinDslNumber = abziehbareAussergewoehnlicheBelastungen(fall, Euro.von(gde)).withMoneyAnnotation("Euro", "var \"agb\"");
const ein: FinDslNumber = einkommen(Euro.von(gde), fall).withMoneyAnnotation("Euro", "var \"ein\"");
const zve: FinDslNumber = zuVersteuerndesEinkommen(Euro.von(ein), fall).withMoneyAnnotation("Euro", "var \"zve\"");
const tariflich: FinDslNumber = tariflicheEinkommensteuer(Euro.von(zve), fall.tarifart).withMoneyAnnotation("Euro", "var \"tariflich\"");
const fest: FinDslNumber = festzusetzendeEinkommensteuer(Euro.von(tariflich), fall).withMoneyAnnotation("Euro", "var \"fest\"");
return new EinkommensteuerErgebnis(Euro.von(sde), Euro.von(gde), Euro.von(kfb), Euro.von(agb), Euro.von(ein), Euro.von(zve), Euro.von(tariflich), Euro.von(fest));
}import { describe, it, expect } from 'vitest';
import { FinDslNumber, FinDslAbort, FinDslListe, Euro, Prozent, Ganzzahl, Tarifart } from './runtime/index.js';
import * as Est from './Est.js';
/**
* Generiert aus FinDSL — NICHT manuell editieren.
* Semantik-Orakel: der FinDSL-Interpreter (bit-genau).
*
* # Akzeptanztests — Einkommensteuer § 2 + § 32a EStG (VZ 2026)
*
* Sollwerte **von Hand aus dem Wortlaut** gerechnet (Quelle
* `examples/est/estg.xml`, Fassung „ab Veranlagungszeitraum 2026").
* § 32a Satz 6: Steuerbetrag auf vollen Euro **abgerundet**.
*
* Tarif-Größen: `y = (zvE − 12.348)/10.000`, `z = (zvE − 17.799)/10.000`.
* Zonen: Nr. 2 `(914,51·y + 1.400)·y`; Nr. 3
* `(173,10·z + 2.397)·z + 1.034,87`; Nr. 4 `0,42·x − 11.135,63`;
* Nr. 5 `0,45·x − 19.470,38`. Splitting (Abs. 5) = 2·Grundtarif(⌊zvE/2⌋).
*
* § 32 Abs. 6: je Kind (3.414 + 1.464)·faktor·Monate/12·auslandsfaktor.
* § 33 Abs. 3 zumutbare Belastung **staffelweise** (Stufen 15.340 /
* 51.130; Sätze ohne Kind Grund 5/6/7 %, Splitting 4/5/6 %; 1–2 Kinder
* 2/3/4 %; ≥3 Kinder 1/1/2 %). § 10b: Spenden ≤ max(20 % GdE; 4 ‰
* Umsätze+Löhne). Modellierungs-Entscheidung: Kategorie-Abzugssummen
* auf volle Euro abgerundet (s. est.findsl Datei-Doc).
*/
describe("§ 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)", () => {
it("zvE = 0 → 0", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("0"))).equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
});
it("zvE = Grundfreibetrag 12.348 → 0 (bis-Grenze inklusiv)", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("12348"))).equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
});
it("zvE = 12.349 (Zone-2-Beginn) → 0 (Steuer rundet auf 0 ab)", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("12349"))).equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
});
});
describe("§ 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)", () => {
it("zvE = 15.000", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("15000"))).equalsValue(FinDslNumber.ganzzahl("435"))).toBe(true);
});
it("zvE = 17.799 (obere Grenze Zone 2)", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("17799"))).equalsValue(FinDslNumber.ganzzahl("1034"))).toBe(true);
});
});
describe("§ 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)", () => {
it("zvE = 17.800 (Zone-3-Beginn)", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("17800"))).equalsValue(FinDslNumber.ganzzahl("1035"))).toBe(true);
});
it("zvE = 50.000", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("50000"))).equalsValue(FinDslNumber.ganzzahl("10548"))).toBe(true);
});
it("zvE = 69.878 (obere Grenze Zone 3)", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("69878"))).equalsValue(FinDslNumber.ganzzahl("18213"))).toBe(true);
});
});
describe("§ 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)", () => {
it("zvE = 69.879 (Zone-4-Beginn, stetiger Anschluss)", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("69879"))).equalsValue(FinDslNumber.ganzzahl("18213"))).toBe(true);
});
it("zvE = 100.000", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("100000"))).equalsValue(FinDslNumber.ganzzahl("30864"))).toBe(true);
});
it("zvE = 277.825 (obere Grenze Zone 4)", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("277825"))).equalsValue(FinDslNumber.ganzzahl("105550"))).toBe(true);
});
});
describe("§ 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)", () => {
it("zvE = 277.826 (Zone-5-Beginn)", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("277826"))).equalsValue(FinDslNumber.ganzzahl("105551"))).toBe(true);
});
it("zvE = 300.000", () => {
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("300000"))).equalsValue(FinDslNumber.ganzzahl("115529"))).toBe(true);
});
});
describe("§ 32a Abs. 5 EStG — Splitting-Verfahren", () => {
it("zvE = 200.000 → 2 · Grundtarif(100.000) = 2 · 30.864", () => {
expect(Est.estSplitting(Euro.von(FinDslNumber.ganzzahl("200000"))).equalsValue(FinDslNumber.ganzzahl("61728"))).toBe(true);
});
it("zvE = 100.001 → Hälfte 50.000 (abgerundet) → 2 · 10.548", () => {
expect(Est.estSplitting(Euro.von(FinDslNumber.ganzzahl("100001"))).equalsValue(FinDslNumber.ganzzahl("21096"))).toBe(true);
});
it("zvE = 150.000 → Hälfte 75.000 → 2 · Grundtarif(75.000)", () => {
expect(Est.estSplitting(Euro.von(FinDslNumber.ganzzahl("150000"))).equalsValue(FinDslNumber.ganzzahl("40728"))).toBe(true);
});
});
describe("§ 32a EStG — unzulässige Eingaben (abbruch)", () => {
it("negatives zvE (Grundtarif) ist nicht definiert", () => {
expect(() => {
const n: FinDslNumber = FinDslNumber.ganzzahl("1").neg().withMoneyAnnotation("Euro", "var \"n\"");
Est.estGrundtarif(Euro.von(n));
}).toThrow(FinDslAbort);
});
it("negatives gemeinsames zvE (Splitting) ist nicht definiert", () => {
expect(() => {
const n: FinDslNumber = FinDslNumber.ganzzahl("2").neg().withMoneyAnnotation("Euro", "var \"n\"");
Est.estSplitting(Euro.von(n));
}).toThrow(FinDslAbort);
});
});
describe("§ 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)", () => {
it("Fall K — Single, 2 Kinder, agB- + Spenden-Posten", () => {
const e: Est.EinkommensteuerErgebnis = Est.berechneEinkommensteuer(new Est.EinkommensteuerFall(Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("60000")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("4000")), FinDslListe.of([FinDslNumber.ganzzahl("2000")]), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.of([FinDslNumber.ganzzahl("5000")]), FinDslListe.of([new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("1")), Ganzzahl.von(FinDslNumber.ganzzahl("12")), Prozent.von(FinDslNumber.prozent("1"))), new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("1")), Ganzzahl.von(FinDslNumber.ganzzahl("12")), Prozent.von(FinDslNumber.prozent("1")))]), Euro.von(FinDslNumber.ganzzahl("0")), Tarifart.Grundtarif, Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0"))));
expect(e.gesamtbetragDerEinkuenfte.equalsValue(FinDslNumber.ganzzahl("60000"))).toBe(true);
expect(e.kinderfreibetraege.equalsValue(FinDslNumber.ganzzahl("9756"))).toBe(true);
expect(e.abziehbareAussergewoehnlicheBelastungen.equalsValue(FinDslNumber.ganzzahl("3264"))).toBe(true);
expect(e.einkommen.equalsValue(FinDslNumber.ganzzahl("50736"))).toBe(true);
expect(e.zuVersteuerndesEinkommen.equalsValue(FinDslNumber.ganzzahl("40980"))).toBe(true);
expect(e.tariflicheEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("7521"))).toBe(true);
expect(e.festzusetzendeEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("7521"))).toBe(true);
});
it("Fall S — Splitting, 3 Kinder (eines halbjährig), Spenden gekappt", () => {
const e: Est.EinkommensteuerErgebnis = Est.berechneEinkommensteuer(new Est.EinkommensteuerFall(Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("100000")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.of([FinDslNumber.ganzzahl("10000"), FinDslNumber.ganzzahl("20000")]), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.of([FinDslNumber.ganzzahl("3000"), FinDslNumber.ganzzahl("5000")]), FinDslListe.of([new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("2")), Ganzzahl.von(FinDslNumber.ganzzahl("12")), Prozent.von(FinDslNumber.prozent("1"))), new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("2")), Ganzzahl.von(FinDslNumber.ganzzahl("12")), Prozent.von(FinDslNumber.prozent("1"))), new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("2")), Ganzzahl.von(FinDslNumber.ganzzahl("6")), Prozent.von(FinDslNumber.prozent("1")))]), Euro.von(FinDslNumber.ganzzahl("0")), Tarifart.Splitting, Euro.von(FinDslNumber.ganzzahl("2500")), Euro.von(FinDslNumber.ganzzahl("600"))));
expect(e.kinderfreibetraege.equalsValue(FinDslNumber.ganzzahl("24390"))).toBe(true);
expect(e.abziehbareAussergewoehnlicheBelastungen.equalsValue(FinDslNumber.ganzzahl("6511"))).toBe(true);
expect(e.einkommen.equalsValue(FinDslNumber.ganzzahl("73489"))).toBe(true);
expect(e.zuVersteuerndesEinkommen.equalsValue(FinDslNumber.ganzzahl("49099"))).toBe(true);
expect(e.tariflicheEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("5462"))).toBe(true);
expect(e.festzusetzendeEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("3562"))).toBe(true);
});
it("Fall L — agB unter zumutbarer Belastung → 0 abziehbar", () => {
const e: Est.EinkommensteuerErgebnis = Est.berechneEinkommensteuer(new Est.EinkommensteuerFall(Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("40000")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.empty<FinDslNumber>(), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.of([FinDslNumber.ganzzahl("1000")]), FinDslListe.empty<Est.Kind>(), Euro.von(FinDslNumber.ganzzahl("0")), Tarifart.Grundtarif, Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0"))));
expect(e.abziehbareAussergewoehnlicheBelastungen.equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
expect(e.einkommen.equalsValue(FinDslNumber.ganzzahl("40000"))).toBe(true);
expect(e.zuVersteuerndesEinkommen.equalsValue(FinDslNumber.ganzzahl("40000"))).toBe(true);
expect(e.tariflicheEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("7209"))).toBe(true);
});
it("Fall 0 — leere Listen ≙ alte Skalar-0-Kaskade (Regressionsanker)", () => {
const e: Est.EinkommensteuerErgebnis = Est.berechneEinkommensteuer(new Est.EinkommensteuerFall(Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("50000")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.empty<FinDslNumber>(), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.empty<FinDslNumber>(), FinDslListe.empty<Est.Kind>(), Euro.von(FinDslNumber.ganzzahl("0")), Tarifart.Grundtarif, Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0"))));
expect(e.kinderfreibetraege.equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
expect(e.abziehbareAussergewoehnlicheBelastungen.equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
expect(e.einkommen.equalsValue(FinDslNumber.ganzzahl("50000"))).toBe(true);
expect(e.zuVersteuerndesEinkommen.equalsValue(FinDslNumber.ganzzahl("50000"))).toBe(true);
expect(e.tariflicheEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("10548"))).toBe(true);
});
});import { FinDslNumber, FinDslRuntimeError, FinDslAbort, FinDslListe, Euro, EuroCent, Prozent, Ganzzahl, Dezimal, Tarifart } from './runtime/index.js';
export class Kind {
faktor;
berücksichtigteMonate;
auslandsfaktor;
constructor(faktor, berücksichtigteMonate, auslandsfaktor){
this.faktor = faktor;
this.berücksichtigteMonate = berücksichtigteMonate;
this.auslandsfaktor = auslandsfaktor;
}
}
export class EinkommensteuerFall {
einkuenfteLandUndForstwirtschaft;
einkuenfteGewerbebetrieb;
einkuenfteSelbstaendigeArbeit;
einkuenfteNichtselbstaendigeArbeit;
einkuenfteKapitalvermoegen;
einkuenfteVermietungVerpachtung;
sonstigeEinkuenfte;
altersentlastungsbetrag;
entlastungsbetragAlleinerziehende;
freibetragLandUndForstwirtschaft;
sonstigeSonderausgaben;
spenden;
umsaetzeUndLoehne;
aussergewoehnlicheAufwendungen;
kinder;
sonstigeAbzuegeVomEinkommen;
tarifart;
anrechnungenUndErmaessigungen;
hinzurechnungen;
constructor(einkuenfteLandUndForstwirtschaft, einkuenfteGewerbebetrieb, einkuenfteSelbstaendigeArbeit, einkuenfteNichtselbstaendigeArbeit, einkuenfteKapitalvermoegen, einkuenfteVermietungVerpachtung, sonstigeEinkuenfte, altersentlastungsbetrag, entlastungsbetragAlleinerziehende, freibetragLandUndForstwirtschaft, sonstigeSonderausgaben, spenden, umsaetzeUndLoehne, aussergewoehnlicheAufwendungen, kinder, sonstigeAbzuegeVomEinkommen, tarifart, anrechnungenUndErmaessigungen, hinzurechnungen){
this.einkuenfteLandUndForstwirtschaft = einkuenfteLandUndForstwirtschaft;
this.einkuenfteGewerbebetrieb = einkuenfteGewerbebetrieb;
this.einkuenfteSelbstaendigeArbeit = einkuenfteSelbstaendigeArbeit;
this.einkuenfteNichtselbstaendigeArbeit = einkuenfteNichtselbstaendigeArbeit;
this.einkuenfteKapitalvermoegen = einkuenfteKapitalvermoegen;
this.einkuenfteVermietungVerpachtung = einkuenfteVermietungVerpachtung;
this.sonstigeEinkuenfte = sonstigeEinkuenfte;
this.altersentlastungsbetrag = altersentlastungsbetrag;
this.entlastungsbetragAlleinerziehende = entlastungsbetragAlleinerziehende;
this.freibetragLandUndForstwirtschaft = freibetragLandUndForstwirtschaft;
this.sonstigeSonderausgaben = sonstigeSonderausgaben;
this.spenden = spenden;
this.umsaetzeUndLoehne = umsaetzeUndLoehne;
this.aussergewoehnlicheAufwendungen = aussergewoehnlicheAufwendungen;
this.kinder = kinder;
this.sonstigeAbzuegeVomEinkommen = sonstigeAbzuegeVomEinkommen;
this.tarifart = tarifart;
this.anrechnungenUndErmaessigungen = anrechnungenUndErmaessigungen;
this.hinzurechnungen = hinzurechnungen;
}
}
export class EinkommensteuerErgebnis {
summeDerEinkuenfte;
gesamtbetragDerEinkuenfte;
kinderfreibetraege;
abziehbareAussergewoehnlicheBelastungen;
einkommen;
zuVersteuerndesEinkommen;
tariflicheEinkommensteuer;
festzusetzendeEinkommensteuer;
constructor(summeDerEinkuenfte, gesamtbetragDerEinkuenfte, kinderfreibetraege, abziehbareAussergewoehnlicheBelastungen, einkommen, zuVersteuerndesEinkommen, tariflicheEinkommensteuer, festzusetzendeEinkommensteuer){
this.summeDerEinkuenfte = summeDerEinkuenfte;
this.gesamtbetragDerEinkuenfte = gesamtbetragDerEinkuenfte;
this.kinderfreibetraege = kinderfreibetraege;
this.abziehbareAussergewoehnlicheBelastungen = abziehbareAussergewoehnlicheBelastungen;
this.einkommen = einkommen;
this.zuVersteuerndesEinkommen = zuVersteuerndesEinkommen;
this.tariflicheEinkommensteuer = tariflicheEinkommensteuer;
this.festzusetzendeEinkommensteuer = festzusetzendeEinkommensteuer;
}
}
export const GFB = Euro.von(FinDslNumber.ganzzahl("12348").withMoneyAnnotation("Euro", "Konstante \"GFB\""));
export const ZONE_2_OBERGRENZE = Euro.von(FinDslNumber.ganzzahl("17799").withMoneyAnnotation("Euro", "Konstante \"ZONE_2_OBERGRENZE\""));
export const ZONE_3_OBERGRENZE = Euro.von(FinDslNumber.ganzzahl("69878").withMoneyAnnotation("Euro", "Konstante \"ZONE_3_OBERGRENZE\""));
export const ZONE_4_OBERGRENZE = Euro.von(FinDslNumber.ganzzahl("277825").withMoneyAnnotation("Euro", "Konstante \"ZONE_4_OBERGRENZE\""));
export const ZEHNTAUSEND = Ganzzahl.von(FinDslNumber.ganzzahl("10000"));
export const ZONE_2_PROGRESSION = Dezimal.von(FinDslNumber.dezimal("914.51"));
export const ZONE_2_LINEAR = Dezimal.von(FinDslNumber.ganzzahl("1400"));
export const ZONE_3_PROGRESSION = Dezimal.von(FinDslNumber.dezimal("173.10"));
export const ZONE_3_LINEAR = Dezimal.von(FinDslNumber.ganzzahl("2397"));
export const ZONE_3_KONSTANTE = Dezimal.von(FinDslNumber.dezimal("1034.87"));
export const ZONE_4_SATZ = Prozent.von(FinDslNumber.prozent("0.42"));
export const ZONE_4_ABZUG = EuroCent.von(FinDslNumber.dezimal("11135.63").withMoneyAnnotation("EuroCent", "Konstante \"ZONE_4_ABZUG\""));
export const ZONE_5_SATZ = Prozent.von(FinDslNumber.prozent("0.45"));
export const ZONE_5_ABZUG = EuroCent.von(FinDslNumber.dezimal("19470.38").withMoneyAnnotation("EuroCent", "Konstante \"ZONE_5_ABZUG\""));
export const KINDERFREIBETRAG = Euro.von(FinDslNumber.ganzzahl("3414").withMoneyAnnotation("Euro", "Konstante \"KINDERFREIBETRAG\""));
export const BEA_FREIBETRAG = Euro.von(FinDslNumber.ganzzahl("1464").withMoneyAnnotation("Euro", "Konstante \"BEA_FREIBETRAG\""));
export const ZWOELF = Ganzzahl.von(FinDslNumber.ganzzahl("12"));
export const ZMB_STUFE_1 = Euro.von(FinDslNumber.ganzzahl("15340").withMoneyAnnotation("Euro", "Konstante \"ZMB_STUFE_1\""));
export const ZMB_STUFE_2 = Euro.von(FinDslNumber.ganzzahl("51130").withMoneyAnnotation("Euro", "Konstante \"ZMB_STUFE_2\""));
export const ZMB_OHNE_KIND_GRUND_1 = Prozent.von(FinDslNumber.prozent("0.05"));
export const ZMB_OHNE_KIND_GRUND_2 = Prozent.von(FinDslNumber.prozent("0.06"));
export const ZMB_OHNE_KIND_GRUND_3 = Prozent.von(FinDslNumber.prozent("0.07"));
export const ZMB_OHNE_KIND_SPLIT_1 = Prozent.von(FinDslNumber.prozent("0.04"));
export const ZMB_OHNE_KIND_SPLIT_2 = Prozent.von(FinDslNumber.prozent("0.05"));
export const ZMB_OHNE_KIND_SPLIT_3 = Prozent.von(FinDslNumber.prozent("0.06"));
export const ZMB_1_2_KINDER_1 = Prozent.von(FinDslNumber.prozent("0.02"));
export const ZMB_1_2_KINDER_2 = Prozent.von(FinDslNumber.prozent("0.03"));
export const ZMB_1_2_KINDER_3 = Prozent.von(FinDslNumber.prozent("0.04"));
export const ZMB_AB_3_KINDER_1 = Prozent.von(FinDslNumber.prozent("0.01"));
export const ZMB_AB_3_KINDER_2 = Prozent.von(FinDslNumber.prozent("0.01"));
export const ZMB_AB_3_KINDER_3 = Prozent.von(FinDslNumber.prozent("0.02"));
export const SPENDEN_HB_GDE = Prozent.von(FinDslNumber.prozent("0.2"));
export const SPENDEN_HB_UMSATZ = Prozent.von(FinDslNumber.prozent("0.004"));
export function estGrundtarif(zve) {
if (zve.compareValue(FinDslNumber.ganzzahl("0").cast("Euro")) < 0) {
throw new FinDslAbort("§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=" + zve.asText() + ")");
}
if (zve.compareValue(GFB.add(FinDslNumber.ganzzahl("1"))) < 0) {
return Euro.von(FinDslNumber.ganzzahl("0"));
}
if (zve.compareValue(ZONE_2_OBERGRENZE.add(FinDslNumber.ganzzahl("1"))) < 0) {
const y = zve.sub(GFB).div(ZEHNTAUSEND);
const roh = ZONE_2_PROGRESSION.mul(y).add(ZONE_2_LINEAR).mul(y);
return Euro.von(roh.abrunden("Euro").cast("Euro"));
}
if (zve.compareValue(ZONE_3_OBERGRENZE.add(FinDslNumber.ganzzahl("1"))) < 0) {
const z = zve.sub(ZONE_2_OBERGRENZE).div(ZEHNTAUSEND);
const roh = ZONE_3_PROGRESSION.mul(z).add(ZONE_3_LINEAR).mul(z).add(ZONE_3_KONSTANTE);
return Euro.von(roh.abrunden("Euro").cast("Euro"));
}
if (zve.compareValue(ZONE_4_OBERGRENZE.add(FinDslNumber.ganzzahl("1"))) < 0) {
return Euro.von(ZONE_4_SATZ.mul(zve).sub(ZONE_4_ABZUG).abrunden("Euro"));
}
return Euro.von(ZONE_5_SATZ.mul(zve).sub(ZONE_5_ABZUG).abrunden("Euro"));
}
export function estSplitting(zve) {
if (zve.compareValue(FinDslNumber.ganzzahl("0").cast("Euro")) < 0) {
throw new FinDslAbort("§ 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen darf nicht negativ sein (zvE=" + zve.asText() + ")");
}
const halbesZve = zve.div(FinDslNumber.ganzzahl("2")).abrunden("Euro").cast("Euro").withMoneyAnnotation("Euro", "var \"halbesZve\"");
return Euro.von(FinDslNumber.ganzzahl("2").mul(estGrundtarif(Euro.von(halbesZve))));
}
function _spanne(betrag, von, obereGrenze) {
return betrag.hoechstens(obereGrenze).sub(von).mindestens(FinDslNumber.ganzzahl("0"));
}
export function summeDerEinkuenfte(fall) {
return Euro.von(fall.einkuenfteLandUndForstwirtschaft.add(fall.einkuenfteGewerbebetrieb).add(fall.einkuenfteSelbstaendigeArbeit).add(fall.einkuenfteNichtselbstaendigeArbeit).add(fall.einkuenfteKapitalvermoegen).add(fall.einkuenfteVermietungVerpachtung).add(fall.sonstigeEinkuenfte));
}
export function gesamtbetragDerEinkuenfte(summe, fall) {
return Euro.von(summe.sub(fall.altersentlastungsbetrag).sub(fall.entlastungsbetragAlleinerziehende).sub(fall.freibetragLandUndForstwirtschaft));
}
export function kinderfreibetragGesamt(kinder) {
return Euro.von(kinder.zuordnen((k)=>KINDERFREIBETRAG.add(BEA_FREIBETRAG).mul(k.faktor).mul(k.berücksichtigteMonate.div(ZWOELF)).mul(k.auslandsfaktor)).summe().abrunden("Euro"));
}
export function zumutbareBelastung(gde, kinderzahl, tarifart) {
return EuroCent.von(_zmbSatz(FinDslNumber.ganzzahl("1"), kinderzahl, tarifart).mul(_spanne(gde, FinDslNumber.ganzzahl("0"), ZMB_STUFE_1)).add(_zmbSatz(FinDslNumber.ganzzahl("2"), kinderzahl, tarifart).mul(_spanne(gde, ZMB_STUFE_1, ZMB_STUFE_2))).add(_zmbSatz(FinDslNumber.ganzzahl("3"), kinderzahl, tarifart).mul(gde.sub(ZMB_STUFE_2).mindestens(FinDslNumber.ganzzahl("0")))));
}
function _zmbSatz(stufe, kinderzahl, tarifart) {
if (kinderzahl.compareValue(FinDslNumber.ganzzahl("1")) < 0) {
if (tarifart === Tarifart.Grundtarif) {
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_OHNE_KIND_GRUND_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_OHNE_KIND_GRUND_2;
}
return ZMB_OHNE_KIND_GRUND_3;
}
if (tarifart === Tarifart.Splitting) {
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_OHNE_KIND_SPLIT_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_OHNE_KIND_SPLIT_2;
}
return ZMB_OHNE_KIND_SPLIT_3;
}
throw new FinDslRuntimeError("Kein falls-Arm passte (wähle, Codegen).");
}
if (kinderzahl.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_1_2_KINDER_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_1_2_KINDER_2;
}
return ZMB_1_2_KINDER_3;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("2")) < 0) {
return ZMB_AB_3_KINDER_1;
}
if (stufe.compareValue(FinDslNumber.ganzzahl("3")) < 0) {
return ZMB_AB_3_KINDER_2;
}
return ZMB_AB_3_KINDER_3;
}
export function abziehbareAussergewoehnlicheBelastungen(fall, gde) {
return Euro.von(fall.aussergewoehnlicheAufwendungen.summe().cast("EuroCent").sub(zumutbareBelastung(Euro.von(gde), Ganzzahl.von(fall.kinder.laenge()), fall.tarifart)).mindestens(FinDslNumber.dezimal("0.00")).abrunden("Euro"));
}
export function abziehbareSpenden(fall, gde) {
const grenzeGde = SPENDEN_HB_GDE.mul(gde).abrunden("Euro").withMoneyAnnotation("Euro", "var \"grenzeGde\"");
const grenzeUmsatz = SPENDEN_HB_UMSATZ.mul(fall.umsaetzeUndLoehne).abrunden("Euro").withMoneyAnnotation("Euro", "var \"grenzeUmsatz\"");
const hoechstbetrag = grenzeGde.mindestens(grenzeUmsatz).withMoneyAnnotation("Euro", "var \"hoechstbetrag\"");
return Euro.von(fall.spenden.summe().hoechstens(hoechstbetrag));
}
export function einkommen(gesamtbetrag, fall) {
return Euro.von(gesamtbetrag.sub(fall.sonstigeSonderausgaben).sub(abziehbareSpenden(fall, Euro.von(gesamtbetrag))).sub(abziehbareAussergewoehnlicheBelastungen(fall, Euro.von(gesamtbetrag))));
}
export function zuVersteuerndesEinkommen(einkommen, fall) {
return Euro.von(einkommen.sub(kinderfreibetragGesamt(fall.kinder)).sub(fall.sonstigeAbzuegeVomEinkommen));
}
export function tariflicheEinkommensteuer(zve, tarifart) {
if (tarifart === Tarifart.Grundtarif) {
return Euro.von(estGrundtarif(Euro.von(zve.mindestens(FinDslNumber.ganzzahl("0")))));
}
if (tarifart === Tarifart.Splitting) {
return Euro.von(estSplitting(Euro.von(zve.mindestens(FinDslNumber.ganzzahl("0")))));
}
throw new FinDslRuntimeError("Kein falls-Arm passte (wähle, Codegen).");
}
export function festzusetzendeEinkommensteuer(tariflich, fall) {
return Euro.von(tariflich.sub(fall.anrechnungenUndErmaessigungen).add(fall.hinzurechnungen));
}
export function berechneEinkommensteuer(fall) {
const sde = summeDerEinkuenfte(fall).withMoneyAnnotation("Euro", "var \"sde\"");
const gde = gesamtbetragDerEinkuenfte(Euro.von(sde), fall).withMoneyAnnotation("Euro", "var \"gde\"");
const kfb = kinderfreibetragGesamt(fall.kinder).withMoneyAnnotation("Euro", "var \"kfb\"");
const agb = abziehbareAussergewoehnlicheBelastungen(fall, Euro.von(gde)).withMoneyAnnotation("Euro", "var \"agb\"");
const ein = einkommen(Euro.von(gde), fall).withMoneyAnnotation("Euro", "var \"ein\"");
const zve = zuVersteuerndesEinkommen(Euro.von(ein), fall).withMoneyAnnotation("Euro", "var \"zve\"");
const tariflich = tariflicheEinkommensteuer(Euro.von(zve), fall.tarifart).withMoneyAnnotation("Euro", "var \"tariflich\"");
const fest = festzusetzendeEinkommensteuer(Euro.von(tariflich), fall).withMoneyAnnotation("Euro", "var \"fest\"");
return new EinkommensteuerErgebnis(Euro.von(sde), Euro.von(gde), Euro.von(kfb), Euro.von(agb), Euro.von(ein), Euro.von(zve), Euro.von(tariflich), Euro.von(fest));
}import { describe, it, expect } from 'vitest';
import { FinDslNumber, FinDslAbort, FinDslListe, Euro, Prozent, Ganzzahl, Tarifart } from './runtime/index.js';
import * as Est from './Est.js';
describe("§ 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)", ()=>{
it("zvE = 0 → 0", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("0"))).equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
});
it("zvE = Grundfreibetrag 12.348 → 0 (bis-Grenze inklusiv)", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("12348"))).equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
});
it("zvE = 12.349 (Zone-2-Beginn) → 0 (Steuer rundet auf 0 ab)", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("12349"))).equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
});
});
describe("§ 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)", ()=>{
it("zvE = 15.000", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("15000"))).equalsValue(FinDslNumber.ganzzahl("435"))).toBe(true);
});
it("zvE = 17.799 (obere Grenze Zone 2)", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("17799"))).equalsValue(FinDslNumber.ganzzahl("1034"))).toBe(true);
});
});
describe("§ 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)", ()=>{
it("zvE = 17.800 (Zone-3-Beginn)", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("17800"))).equalsValue(FinDslNumber.ganzzahl("1035"))).toBe(true);
});
it("zvE = 50.000", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("50000"))).equalsValue(FinDslNumber.ganzzahl("10548"))).toBe(true);
});
it("zvE = 69.878 (obere Grenze Zone 3)", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("69878"))).equalsValue(FinDslNumber.ganzzahl("18213"))).toBe(true);
});
});
describe("§ 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)", ()=>{
it("zvE = 69.879 (Zone-4-Beginn, stetiger Anschluss)", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("69879"))).equalsValue(FinDslNumber.ganzzahl("18213"))).toBe(true);
});
it("zvE = 100.000", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("100000"))).equalsValue(FinDslNumber.ganzzahl("30864"))).toBe(true);
});
it("zvE = 277.825 (obere Grenze Zone 4)", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("277825"))).equalsValue(FinDslNumber.ganzzahl("105550"))).toBe(true);
});
});
describe("§ 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)", ()=>{
it("zvE = 277.826 (Zone-5-Beginn)", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("277826"))).equalsValue(FinDslNumber.ganzzahl("105551"))).toBe(true);
});
it("zvE = 300.000", ()=>{
expect(Est.estGrundtarif(Euro.von(FinDslNumber.ganzzahl("300000"))).equalsValue(FinDslNumber.ganzzahl("115529"))).toBe(true);
});
});
describe("§ 32a Abs. 5 EStG — Splitting-Verfahren", ()=>{
it("zvE = 200.000 → 2 · Grundtarif(100.000) = 2 · 30.864", ()=>{
expect(Est.estSplitting(Euro.von(FinDslNumber.ganzzahl("200000"))).equalsValue(FinDslNumber.ganzzahl("61728"))).toBe(true);
});
it("zvE = 100.001 → Hälfte 50.000 (abgerundet) → 2 · 10.548", ()=>{
expect(Est.estSplitting(Euro.von(FinDslNumber.ganzzahl("100001"))).equalsValue(FinDslNumber.ganzzahl("21096"))).toBe(true);
});
it("zvE = 150.000 → Hälfte 75.000 → 2 · Grundtarif(75.000)", ()=>{
expect(Est.estSplitting(Euro.von(FinDslNumber.ganzzahl("150000"))).equalsValue(FinDslNumber.ganzzahl("40728"))).toBe(true);
});
});
describe("§ 32a EStG — unzulässige Eingaben (abbruch)", ()=>{
it("negatives zvE (Grundtarif) ist nicht definiert", ()=>{
expect(()=>{
const n = FinDslNumber.ganzzahl("1").neg().withMoneyAnnotation("Euro", "var \"n\"");
Est.estGrundtarif(Euro.von(n));
}).toThrow(FinDslAbort);
});
it("negatives gemeinsames zvE (Splitting) ist nicht definiert", ()=>{
expect(()=>{
const n = FinDslNumber.ganzzahl("2").neg().withMoneyAnnotation("Euro", "var \"n\"");
Est.estSplitting(Euro.von(n));
}).toThrow(FinDslAbort);
});
});
describe("§ 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)", ()=>{
it("Fall K — Single, 2 Kinder, agB- + Spenden-Posten", ()=>{
const e = Est.berechneEinkommensteuer(new Est.EinkommensteuerFall(Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("60000")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("4000")), FinDslListe.of([
FinDslNumber.ganzzahl("2000")
]), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.of([
FinDslNumber.ganzzahl("5000")
]), FinDslListe.of([
new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("1")), Ganzzahl.von(FinDslNumber.ganzzahl("12")), Prozent.von(FinDslNumber.prozent("1"))),
new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("1")), Ganzzahl.von(FinDslNumber.ganzzahl("12")), Prozent.von(FinDslNumber.prozent("1")))
]), Euro.von(FinDslNumber.ganzzahl("0")), Tarifart.Grundtarif, Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0"))));
expect(e.gesamtbetragDerEinkuenfte.equalsValue(FinDslNumber.ganzzahl("60000"))).toBe(true);
expect(e.kinderfreibetraege.equalsValue(FinDslNumber.ganzzahl("9756"))).toBe(true);
expect(e.abziehbareAussergewoehnlicheBelastungen.equalsValue(FinDslNumber.ganzzahl("3264"))).toBe(true);
expect(e.einkommen.equalsValue(FinDslNumber.ganzzahl("50736"))).toBe(true);
expect(e.zuVersteuerndesEinkommen.equalsValue(FinDslNumber.ganzzahl("40980"))).toBe(true);
expect(e.tariflicheEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("7521"))).toBe(true);
expect(e.festzusetzendeEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("7521"))).toBe(true);
});
it("Fall S — Splitting, 3 Kinder (eines halbjährig), Spenden gekappt", ()=>{
const e = Est.berechneEinkommensteuer(new Est.EinkommensteuerFall(Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("100000")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.of([
FinDslNumber.ganzzahl("10000"),
FinDslNumber.ganzzahl("20000")
]), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.of([
FinDslNumber.ganzzahl("3000"),
FinDslNumber.ganzzahl("5000")
]), FinDslListe.of([
new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("2")), Ganzzahl.von(FinDslNumber.ganzzahl("12")), Prozent.von(FinDslNumber.prozent("1"))),
new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("2")), Ganzzahl.von(FinDslNumber.ganzzahl("12")), Prozent.von(FinDslNumber.prozent("1"))),
new Est.Kind(Ganzzahl.von(FinDslNumber.ganzzahl("2")), Ganzzahl.von(FinDslNumber.ganzzahl("6")), Prozent.von(FinDslNumber.prozent("1")))
]), Euro.von(FinDslNumber.ganzzahl("0")), Tarifart.Splitting, Euro.von(FinDslNumber.ganzzahl("2500")), Euro.von(FinDslNumber.ganzzahl("600"))));
expect(e.kinderfreibetraege.equalsValue(FinDslNumber.ganzzahl("24390"))).toBe(true);
expect(e.abziehbareAussergewoehnlicheBelastungen.equalsValue(FinDslNumber.ganzzahl("6511"))).toBe(true);
expect(e.einkommen.equalsValue(FinDslNumber.ganzzahl("73489"))).toBe(true);
expect(e.zuVersteuerndesEinkommen.equalsValue(FinDslNumber.ganzzahl("49099"))).toBe(true);
expect(e.tariflicheEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("5462"))).toBe(true);
expect(e.festzusetzendeEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("3562"))).toBe(true);
});
it("Fall L — agB unter zumutbarer Belastung → 0 abziehbar", ()=>{
const e = Est.berechneEinkommensteuer(new Est.EinkommensteuerFall(Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("40000")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.empty(), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.of([
FinDslNumber.ganzzahl("1000")
]), FinDslListe.empty(), Euro.von(FinDslNumber.ganzzahl("0")), Tarifart.Grundtarif, Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0"))));
expect(e.abziehbareAussergewoehnlicheBelastungen.equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
expect(e.einkommen.equalsValue(FinDslNumber.ganzzahl("40000"))).toBe(true);
expect(e.zuVersteuerndesEinkommen.equalsValue(FinDslNumber.ganzzahl("40000"))).toBe(true);
expect(e.tariflicheEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("7209"))).toBe(true);
});
it("Fall 0 — leere Listen ≙ alte Skalar-0-Kaskade (Regressionsanker)", ()=>{
const e = Est.berechneEinkommensteuer(new Est.EinkommensteuerFall(Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("50000")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.empty(), Euro.von(FinDslNumber.ganzzahl("0")), FinDslListe.empty(), FinDslListe.empty(), Euro.von(FinDslNumber.ganzzahl("0")), Tarifart.Grundtarif, Euro.von(FinDslNumber.ganzzahl("0")), Euro.von(FinDslNumber.ganzzahl("0"))));
expect(e.kinderfreibetraege.equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
expect(e.abziehbareAussergewoehnlicheBelastungen.equalsValue(FinDslNumber.ganzzahl("0"))).toBe(true);
expect(e.einkommen.equalsValue(FinDslNumber.ganzzahl("50000"))).toBe(true);
expect(e.zuVersteuerndesEinkommen.equalsValue(FinDslNumber.ganzzahl("50000"))).toBe(true);
expect(e.tariflicheEinkommensteuer.equalsValue(FinDslNumber.ganzzahl("10548"))).toBe(true);
});
});Einkommensteuer — Veranlagungsschema § 2 EStG + Tarif § 32a EStG (VZ 2026)
Bildet die Einkommensteuer-Kaskade nach § 2 EStG ab, schließt mit dem tariflichen Einkommensteuerbetrag (§ 32a) und der festzusetzenden Einkommensteuer (§ 2 Abs.
Inhalt
- est
- Konstanten
- konst GFB
- konst ZONE_2_OBERGRENZE
- konst ZONE_3_OBERGRENZE
- konst ZONE_4_OBERGRENZE
- konst ZEHNTAUSEND
- konst ZONE_2_PROGRESSION
- konst ZONE_2_LINEAR
- konst ZONE_3_PROGRESSION
- konst ZONE_3_LINEAR
- konst ZONE_3_KONSTANTE
- konst ZONE_4_SATZ
- konst ZONE_4_ABZUG
- konst ZONE_5_SATZ
- konst ZONE_5_ABZUG
- konst KINDERFREIBETRAG
- konst BEA_FREIBETRAG
- konst ZWOELF
- konst ZMB_STUFE_1
- konst ZMB_STUFE_2
- konst ZMB_OHNE_KIND_GRUND_1
- konst ZMB_OHNE_KIND_GRUND_2
- konst ZMB_OHNE_KIND_GRUND_3
- konst ZMB_OHNE_KIND_SPLIT_1
- konst ZMB_OHNE_KIND_SPLIT_2
- konst ZMB_OHNE_KIND_SPLIT_3
- konst ZMB_1_2_KINDER_1
- konst ZMB_1_2_KINDER_2
- konst ZMB_1_2_KINDER_3
- konst ZMB_AB_3_KINDER_1
- konst ZMB_AB_3_KINDER_2
- konst ZMB_AB_3_KINDER_3
- konst SPENDEN_HB_GDE
- konst SPENDEN_HB_UMSATZ
- Datensätze
- Funktionen
- fn EstGrundtarif
- fn EstSplitting
- fn SummeDerEinkuenfte
- fn GesamtbetragDerEinkuenfte
- fn KinderfreibetragGesamt
- fn ZumutbareBelastung
- fn AbziehbareAussergewoehnlicheBelastungen
- fn AbziehbareSpenden
- fn Einkommen
- fn ZuVersteuerndesEinkommen
- fn TariflicheEinkommensteuer
- fn FestzusetzendeEinkommensteuer
- fn BerechneEinkommensteuer
- Konstanten
- est.test
- Prüfungen
- prüfe § 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)
- prüfe § 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)
- prüfe § 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)
- prüfe § 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)
- prüfe § 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)
- prüfe § 32a Abs. 5 EStG — Splitting-Verfahren
- prüfe § 32a EStG — unzulässige Eingaben (abbruch)
- prüfe § 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)
- Prüfungen
est
est.findsl
Einkommensteuer — Veranlagungsschema § 2 EStG + Tarif § 32a EStG (VZ 2026)
Bildet die Einkommensteuer-Kaskade nach § 2 EStG ab, schließt mit
dem tariflichen Einkommensteuerbetrag (§ 32a) und der festzusetzenden
Einkommensteuer (§ 2 Abs. 6). Maßgebliche Quelle:
examples/est/estg.xml (juris-Stand 2026-05-06), § 32a/§ 32 Abs. 6 in
der konsolidierten Fassung „ab Veranlagungszeitraum 2026".
Gesetzliche Reihenfolge (jede Stufe = eigene Funktion, auditierbar): Summe der Einkünfte (§ 2 Abs. 1–3) → Gesamtbetrag der Einkünfte (§ 2 Abs. 3) → Einkommen (§ 2 Abs. 4) → zu versteuerndes Einkommen (§ 2 Abs. 5) → tarifliche Einkommensteuer (§ 32a) → festzusetzende Einkommensteuer (§ 2 Abs. 6).
Echte Rechenvorschrift (modelliert) — auch mehr-entitätig:
- § 32 Abs. 6 Kinderfreibetrag/BEA je Kind über
Liste<Kind>(3.414 € + 1.464 € je Kind, Verdopplung Satz 2/3 per Faktor, Zwölftelung Satz 5, Auslandskürzung Satz 4) → aggregiert. - § 33 Abs. 1/3 außergewöhnliche Belastungen: Summe der zwangsläufigen Aufwendungen abzüglich der zumutbaren Belastung (§ 33 Abs. 3, staffelweise über die drei GdE-Stufen × vier Personengruppen).
- § 10b Abs. 1 Spenden: abziehbar bis zum Höchstbetrag max(20 % GdE; 4 ‰ (Umsätze + Löhne)).
- Die gesamte § 2-Verknüpfungs-Arithmetik + § 32a-Tarif + § 2 Abs. 6.
Geprüfte Eingabe, weil anderes Recht / Verfahren (nicht Tooling- Grenze):
- Ermittlung der sieben Einkunftsarten je Art (Gewinn §§ 4–7k/13a, Überschuss §§ 8–9a, § 20 Abs. 9, AfA § 7 mehrperiodig) — saldierter Betrag je Art als Eingabe.
- § 24a / § 24b / § 13 Abs. 3 — Beträge als Eingabe (eigene §§).
- Übrige Sonderausgaben §§ 10–10c außer § 10b (Vorsorgeaufwen-
dungen mit eigenen Höchstbeträgen/Günstigerprüfung) — Aggregat-
Eingabe
sonstigeSonderausgaben. - Verlustabzug § 10d (mehrperiodig) — negatives zvE → 0 tariflich, Verlustabzug selbst nicht modelliert.
- Sachverhalte je Kind (Kindschaftsverhältnis →
faktor, Auslands-Ländergruppe →auslandsfaktor, Berücksichtigungsmonate) und die § 33-Zwangsläufigkeit/Angemessenheit (§ 33 Abs. 2), § 10b-Empfänger-Voraussetzungen (§ 10b Abs. 2) — Sachverhalt. - § 32a Abs. 6 Witwen-/Gnadensplitting; § 2 Abs. 6-Komponenten (§§ 34c/35/35a/32d Abs. 3/4 …) als zwei gerichtete Aggregat-Eingaben; Annexsteuern (SolZ, KiSt). Verfahren/eigene Gesetze.
Modellierungs-Entscheidung (Statut schweigt): jede listen-
abgeleitete Kategorie-Abzugssumme (Kinderfreibetrag, abziehbare agB,
abziehbare Spenden) wird auf volle Euro abgerundet (.abrunden()
mit Euro-Kontext),
bevor sie in die Euro-Kaskade eingeht — deterministisch, konsistent mit
§ 32a Abs. 1 Satz 1 (zvE auf volle Euro), fiskuskonservativ.
Konstanten
konst GFB
konst GFB: Euro = 12.348
Grundfreibetrag — bis zu diesem zu versteuernden Einkommen beträgt die tarifliche Einkommensteuer 0 (§ 32a Absatz 1 Satz 2 Nummer 1).
Quelle: § 32a Absatz 1 Satz 2 Nummer 1 EStG — § 32a EStG
konst ZONE_2_OBERGRENZE
konst ZONE_2_OBERGRENZE: Euro = 17.799
Obere Grenze der Eingangs-Progressionszone (Zone 2).
Quelle: § 32a Absatz 1 Satz 2 Nummer 2 EStG — § 32a EStG
konst ZONE_3_OBERGRENZE
konst ZONE_3_OBERGRENZE: Euro = 69.878
Obere Grenze der Hauptprogressionszone (Zone 3).
Quelle: § 32a Absatz 1 Satz 2 Nummer 3 EStG — § 32a EStG
konst ZONE_4_OBERGRENZE
konst ZONE_4_OBERGRENZE: Euro = 277.825
Obere Grenze der ersten Proportionalzone (Zone 4); darüber Zone 5.
Quelle: § 32a Absatz 1 Satz 2 Nummer 4 EStG — § 32a EStG
konst ZEHNTAUSEND
konst ZEHNTAUSEND: Ganzzahl = 10.000
Teiler für die Größen „y" und „z": ein Zehntausendstel des den jeweiligen Sockel übersteigenden, auf vollen Euro abgerundeten zvE (§ 32a Absatz 1 Satz 3 und 4).
Quelle: § 32a Absatz 1 Satz 3 und 4 EStG — § 32a EStG
konst ZONE_2_PROGRESSION
konst ZONE_2_PROGRESSION: Dezimal = 914,51
Progressionskoeffizient der Zone 2 (Faktor vor y²).
Quelle: § 32a Absatz 1 Satz 2 Nummer 2 EStG — § 32a EStG
konst ZONE_2_LINEAR
konst ZONE_2_LINEAR: Dezimal = 1.400
Linearer Koeffizient der Zone 2 (Faktor vor y).
Quelle: § 32a Absatz 1 Satz 2 Nummer 2 EStG — § 32a EStG
konst ZONE_3_PROGRESSION
konst ZONE_3_PROGRESSION: Dezimal = 173,10
Progressionskoeffizient der Zone 3 (Faktor vor z²).
Quelle: § 32a Absatz 1 Satz 2 Nummer 3 EStG — § 32a EStG
konst ZONE_3_LINEAR
konst ZONE_3_LINEAR: Dezimal = 2.397
Linearer Koeffizient der Zone 3 (Faktor vor z).
Quelle: § 32a Absatz 1 Satz 2 Nummer 3 EStG — § 32a EStG
konst ZONE_3_KONSTANTE
konst ZONE_3_KONSTANTE: Dezimal = 1.034,87
Konstanter Summand der Zone 3 (Anschluss an Zone 2).
Quelle: § 32a Absatz 1 Satz 2 Nummer 3 EStG — § 32a EStG
konst ZONE_4_SATZ
konst ZONE_4_SATZ: Prozent = 42%
Grenzsteuersatz der Proportionalzone 4 (Spitzensteuersatz).
Quelle: § 32a Absatz 1 Satz 2 Nummer 4 EStG — § 32a EStG
konst ZONE_4_ABZUG
konst ZONE_4_ABZUG: EuroCent = 11.135,63
Abzugsbetrag der Zone 4 (0,42 · x − ZONE_4_ABZUG).
Quelle: § 32a Absatz 1 Satz 2 Nummer 4 EStG — § 32a EStG
konst ZONE_5_SATZ
konst ZONE_5_SATZ: Prozent = 45%
Grenzsteuersatz der Proportionalzone 5 („Reichensteuer").
Quelle: § 32a Absatz 1 Satz 2 Nummer 5 EStG — § 32a EStG
konst ZONE_5_ABZUG
konst ZONE_5_ABZUG: EuroCent = 19.470,38
Abzugsbetrag der Zone 5 (0,45 · x − ZONE_5_ABZUG).
Quelle: § 32a Absatz 1 Satz 2 Nummer 5 EStG — § 32a EStG
konst KINDERFREIBETRAG
konst KINDERFREIBETRAG: Euro = 3.414
Kinderfreibetrag (sächliches Existenzminimum) je Kind.
Quelle: § 32 Absatz 6 Satz 1 EStG — § 32 EStG
konst BEA_FREIBETRAG
konst BEA_FREIBETRAG: Euro = 1.464
Freibetrag Betreuungs-/Erziehungs-/Ausbildungsbedarf (BEA) je Kind.
Quelle: § 32 Absatz 6 Satz 1 EStG — § 32 EStG
konst ZWOELF
konst ZWOELF: Ganzzahl = 12
Teiler für die Zwölftelung je nicht erfüllten Kalendermonat.
Quelle: § 32 Absatz 6 Satz 5 EStG — § 32 EStG
konst ZMB_STUFE_1
konst ZMB_STUFE_1: Euro = 15.340
Erste GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3).
Quelle: § 33 Absatz 3 EStG — § 33 EStG
konst ZMB_STUFE_2
konst ZMB_STUFE_2: Euro = 51.130
Zweite GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3).
Quelle: § 33 Absatz 3 EStG — § 33 EStG
konst ZMB_OHNE_KIND_GRUND_1
konst ZMB_OHNE_KIND_GRUND_1: Prozent = 5%
Zumutbare Belastung — keine Kinder, Grundtarif (§ 32a Abs. 1): Stufe 1/2/3.
Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG — § 33 EStG
konst ZMB_OHNE_KIND_GRUND_2
konst ZMB_OHNE_KIND_GRUND_2: Prozent = 6%
Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG — § 33 EStG
konst ZMB_OHNE_KIND_GRUND_3
konst ZMB_OHNE_KIND_GRUND_3: Prozent = 7%
Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG — § 33 EStG
konst ZMB_OHNE_KIND_SPLIT_1
konst ZMB_OHNE_KIND_SPLIT_1: Prozent = 4%
Zumutbare Belastung — keine Kinder, Splitting (§ 32a Abs. 5/6): Stufe 1/2/3.
Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG — § 33 EStG
konst ZMB_OHNE_KIND_SPLIT_2
konst ZMB_OHNE_KIND_SPLIT_2: Prozent = 5%
Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG — § 33 EStG
konst ZMB_OHNE_KIND_SPLIT_3
konst ZMB_OHNE_KIND_SPLIT_3: Prozent = 6%
Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG — § 33 EStG
konst ZMB_1_2_KINDER_1
konst ZMB_1_2_KINDER_1: Prozent = 2%
Zumutbare Belastung — ein oder zwei Kinder: Stufe 1/2/3.
Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG — § 33 EStG
konst ZMB_1_2_KINDER_2
konst ZMB_1_2_KINDER_2: Prozent = 3%
Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG — § 33 EStG
konst ZMB_1_2_KINDER_3
konst ZMB_1_2_KINDER_3: Prozent = 4%
Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG — § 33 EStG
konst ZMB_AB_3_KINDER_1
konst ZMB_AB_3_KINDER_1: Prozent = 1%
Zumutbare Belastung — drei oder mehr Kinder: Stufe 1/2/3.
Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG — § 33 EStG
konst ZMB_AB_3_KINDER_2
konst ZMB_AB_3_KINDER_2: Prozent = 1%
Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG — § 33 EStG
konst ZMB_AB_3_KINDER_3
konst ZMB_AB_3_KINDER_3: Prozent = 2%
Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG — § 33 EStG
konst SPENDEN_HB_GDE
konst SPENDEN_HB_GDE: Prozent = 20%
Spenden-Höchstbetrag Variante 1: Anteil des Gesamtbetrags der Einkünfte.
Quelle: § 10b Absatz 1 Satz 1 Nummer 1 EStG — § 10b EStG
konst SPENDEN_HB_UMSATZ
konst SPENDEN_HB_UMSATZ: Prozent = 0,4%
Spenden-Höchstbetrag Variante 2: Promille der Umsätze + Löhne (4 ‰).
Quelle: § 10b Absatz 1 Satz 1 Nummer 2 EStG — § 10b EStG
Datensätze
datensatz Kind
datensatz Kind(
faktor: Ganzzahl = 1, // § 32 Abs. 6 Satz 2/3
berücksichtigteMonate: Ganzzahl = 12, // § 32 Abs. 6 Satz 5
auslandsfaktor: Prozent = 100%, // § 32 Abs. 6 Satz 4
)
Sachverhalte je Kind (§ 32 Abs. 6). Die Beträge sind Gesetz; diese Felder sind die Sachverhalts-Eingaben je Kind.
| Feld | Typ | Bedeutung |
|---|---|---|
faktor |
Ganzzahl |
1 = einfacher Freibetrag; 2 = verdoppelt (§ 32 Abs. 6 Satz 2/3 — Kind zu beiden Ehegatten bzw. Satz-3-Fälle) |
berücksichtigteMonate |
Ganzzahl |
Monate mit erfüllten Voraussetzungen (§ 32 Abs. 6 Satz 5: je fehlendem Monat 1/12) |
auslandsfaktor |
Prozent |
Ländergruppen-Anteil für Auslandskinder (§ 32 Abs. 6 Satz 4; 100 % = Inlandskind) |
Quelle: § 32 Absatz 6 EStG — § 32 EStG
datensatz EinkommensteuerFall
datensatz EinkommensteuerFall(
einkuenfteLandUndForstwirtschaft: Euro = 0, // § 2 Abs. 1 Nr. 1
einkuenfteGewerbebetrieb: Euro = 0, // § 2 Abs. 1 Nr. 2
einkuenfteSelbstaendigeArbeit: Euro = 0, // § 2 Abs. 1 Nr. 3
einkuenfteNichtselbstaendigeArbeit: Euro = 0, // § 2 Abs. 1 Nr. 4
einkuenfteKapitalvermoegen: Euro = 0, // § 2 Abs. 1 Nr. 5
einkuenfteVermietungVerpachtung: Euro = 0, // § 2 Abs. 1 Nr. 6
sonstigeEinkuenfte: Euro = 0, // § 2 Abs. 1 Nr. 7
altersentlastungsbetrag: Euro = 0, // § 24a
entlastungsbetragAlleinerziehende: Euro = 0, // § 24b
freibetragLandUndForstwirtschaft: Euro = 0, // § 13 Abs. 3
sonstigeSonderausgaben: Euro = 0, // §§ 10–10c o. § 10b
spenden: Liste<Euro> = []<Euro>, // § 10b Abs. 1
umsaetzeUndLoehne: Euro = 0, // § 10b Abs. 1 S. 1 Nr. 2
aussergewoehnlicheAufwendungen: Liste<Euro> = []<Euro>, // § 33
kinder: Liste<Kind> = []<Kind>, // § 32 Abs. 6
sonstigeAbzuegeVomEinkommen: Euro = 0, // § 2 Abs. 5 S. 1
tarifart: Tarifart = Grundtarif, // §§ 26, 26b
anrechnungenUndErmaessigungen: Euro = 0, // § 2 Abs. 6 S. 1
hinzurechnungen: Euro = 0, // § 2 Abs. 6 S. 1–3
)
Eingaben für die Einkommensteuer-Veranlagung.
| Feld | Typ | Bedeutung |
|---|---|---|
einkuenfteLandUndForstwirtschaft |
Euro |
Einkünfte § 2 Abs. 1 Nr. 1 (§§ 13–14) |
einkuenfteGewerbebetrieb |
Euro |
Einkünfte § 2 Abs. 1 Nr. 2 (§§ 15–17) |
einkuenfteSelbstaendigeArbeit |
Euro |
Einkünfte § 2 Abs. 1 Nr. 3 (§ 18) |
einkuenfteNichtselbstaendigeArbeit |
Euro |
Einkünfte § 2 Abs. 1 Nr. 4 (§ 19) |
einkuenfteKapitalvermoegen |
Euro |
veranlagte Einkünfte § 2 Abs. 1 Nr. 5 (§ 20) |
einkuenfteVermietungVerpachtung |
Euro |
Einkünfte § 2 Abs. 1 Nr. 6 (§ 21) |
sonstigeEinkuenfte |
Euro |
sonstige Einkünfte § 2 Abs. 1 Nr. 7 (§ 22) |
altersentlastungsbetrag |
Euro |
Altersentlastungsbetrag (§ 24a) |
entlastungsbetragAlleinerziehende |
Euro |
Entlastungsbetrag Alleinerziehende (§ 24b) |
freibetragLandUndForstwirtschaft |
Euro |
Abzug nach § 13 Absatz 3 |
sonstigeSonderausgaben |
Euro |
Sonderausgaben §§ 10–10c ohne § 10b (Vorsorge u. a. — anderes Recht) |
spenden |
Liste<Euro> |
abziehbare Zuwendungen § 10b Abs. 1 (Voraussetzungen Abs. 2 = Sachverhalt) |
umsaetzeUndLoehne |
Euro |
Basis der 4-‰-Höchstbetrags- Variante (§ 10b Abs. 1 Satz 1 Nr. 2) |
aussergewoehnlicheAufwendungen |
Liste<Euro> |
zwangsläufige Aufwendungen § 33 (Abs. 2 = Sachverhalt), vor zumutbarer Belastung |
kinder |
Liste<Kind> |
zu berücksichtigende Kinder (§ 32 Abs. 6) |
sonstigeAbzuegeVomEinkommen |
Euro |
sonstige vom Einkommen abzuziehende Beträge (§ 2 Abs. 5 Satz 1) |
tarifart |
Tarifart |
Grund- oder Splittingtarif (§§ 26, 26b) |
anrechnungenUndErmaessigungen |
Euro |
§ 2 Abs. 6 „vermindert um" |
hinzurechnungen |
Euro |
§ 2 Abs. 6 „vermehrt um" (S. 1–3) |
Quelle: § 2 EStG — § 2 EStG
datensatz EinkommensteuerErgebnis
datensatz EinkommensteuerErgebnis(
summeDerEinkuenfte: Euro, // § 2 Abs. 1–3
gesamtbetragDerEinkuenfte: Euro, // § 2 Abs. 3
kinderfreibetraege: Euro, // § 32 Abs. 6
abziehbareAussergewoehnlicheBelastungen: Euro, // § 33
einkommen: Euro, // § 2 Abs. 4
zuVersteuerndesEinkommen: Euro, // § 2 Abs. 5
tariflicheEinkommensteuer: Euro, // § 32a
festzusetzendeEinkommensteuer: Euro, // § 2 Abs. 6
)
Ergebnis der Veranlagung — jede Zwischengröße der gesetzlichen Reihenfolge des § 2 EStG als eigenes Feld (Schritt-für-Schritt-Audit).
| Feld | Typ | Bedeutung |
|---|---|---|
summeDerEinkuenfte |
Euro |
Summe der Einkünfte (§ 2 Abs. 1–3) |
gesamtbetragDerEinkuenfte |
Euro |
Gesamtbetrag der Einkünfte (§ 2 Abs. 3) |
kinderfreibetraege |
Euro |
Freibeträge § 32 Abs. 6 (aggregiert) |
abziehbareAussergewoehnlicheBelastungen |
Euro |
§ 33 nach zumutbarer Belastung |
einkommen |
Euro |
Einkommen (§ 2 Abs. 4) |
zuVersteuerndesEinkommen |
Euro |
zu versteuerndes Einkommen (§ 2 Abs. 5) |
tariflicheEinkommensteuer |
Euro |
tarifliche Einkommensteuer (§ 32a) |
festzusetzendeEinkommensteuer |
Euro |
festzusetzende Einkommensteuer (§ 2 Abs. 6) |
Quelle: § 2 EStG — § 2 EStG
Funktionen
fn EstGrundtarif
fn EstGrundtarif(zve: Euro): Euro
Tariflicher Einkommensteuerbetrag nach dem Grundtarif (§ 32a Absatz 1 EStG). Das zu versteuernde Einkommen ist nach Satz 1 auf volle Euro
abgerundet zu verstehen (durch den Euro-Typ bereits ganzzahlig). Der
sich ergebende Steuerbetrag wird nach Satz 6 auf den nächsten vollen
Euro abgerundet.
Mit den Hilfsgrößen $y = \frac{\text{zvE} - \text{GFB}}{10000}$ (Zone 2) und $z = \frac{\text{zvE} - \text{ZONE_2}}{10000}$ (Zone 3) lautet der Tarif zonenweise:
$$ \text{ESt}(\text{zvE}) = \begin{cases} 0 & \text{zvE} \le \text{GFB} \ (a_2,y + b_2),y & \text{Zone 2} \ (a_3,z + b_3),z + c_3 & \text{Zone 3} \ 0{,}42 \cdot \text{zvE} - C_4 & \text{Zone 4} \ 0{,}45 \cdot \text{zvE} - C_5 & \text{Zone 5} \end{cases} $$
Parameter
| Name | Beschreibung |
|---|---|
zve |
zu versteuerndes Einkommen in vollen Euro (geprüfte Eingabe, ≥ 0; negativ → abbruch) |
Rückgabe — tarifliche Einkommensteuer in vollen Euro (Grundtarif)
Quelle: § 32a Absatz 1 EStG — § 32a EStG
fn EstSplitting
fn EstSplitting(zve: Euro): Euro
Tariflicher Einkommensteuerbetrag nach dem Splitting-Verfahren für zusammen veranlagte Ehegatten (§ 32a Absatz 5 EStG): das Zweifache des Steuerbetrags, der sich für die Hälfte des gemeinsam zu versteuernden Einkommens nach Absatz 1 ergibt. Die Hälfte wird nach Absatz 1 Satz 1 auf volle Euro abgerundet.
Parameter
| Name | Beschreibung |
|---|---|
zve |
gemeinsam zu versteuerndes Einkommen der Ehegatten in vollen Euro (geprüfte Eingabe, ≥ 0; negativ → abbruch) |
Rückgabe — tarifliche Einkommensteuer in vollen Euro (Splitting)
Quelle: § 32a Absatz 5 EStG — § 32a EStG
fn SummeDerEinkuenfte
fn SummeDerEinkuenfte(fall: EinkommensteuerFall): Euro
Summe der Einkünfte (§ 2 Absatz 1 und 2 EStG): Summe der sieben Einkunftsarten. Negative Einkünfte einzelner Arten mindern die Summe (einkunftsartübergreifende Verlustverrechnungsbeschränkungen sind anderes Recht und in den Eingaben bereits berücksichtigt).
Parameter
| Name | Beschreibung |
|---|---|
fall |
die Veranlagungseingaben |
Rückgabe — Summe der Einkünfte in vollen Euro
Quelle: § 2 Absatz 1 und 2 EStG — § 2 EStG
fn GesamtbetragDerEinkuenfte
fn GesamtbetragDerEinkuenfte(summe: Euro, fall: EinkommensteuerFall): Euro
Gesamtbetrag der Einkünfte (§ 2 Absatz 3 EStG): Summe der Einkünfte vermindert um Altersentlastungsbetrag (§ 24a), Entlastungsbetrag für Alleinerziehende (§ 24b) und Abzug nach § 13 Absatz 3.
Parameter
| Name | Beschreibung |
|---|---|
summe |
Summe der Einkünfte (Stufe zuvor) |
fall |
die Veranlagungseingaben |
Rückgabe — Gesamtbetrag der Einkünfte in vollen Euro
Quelle: § 2 Absatz 3 EStG — § 2 EStG
fn KinderfreibetragGesamt
fn KinderfreibetragGesamt(kinder: Liste<Kind>): Euro
Kinderfreibetrag + BEA-Freibetrag, aggregiert über alle Kinder
(§ 32 Absatz 6 EStG): je Kind (3.414 + 1.464) · faktor · berücksichtigteMonate/12 · auslandsfaktor; die Summe wird auf volle
Euro abgerundet (Modellierungs-Entscheidung, s. Datei-Doc).
Parameter
| Name | Beschreibung |
|---|---|
kinder |
die zu berücksichtigenden Kinder |
Rückgabe — Gesamt-Freibetrag in vollen Euro
Quelle: § 32 Absatz 6 EStG — § 32 EStG
fn ZumutbareBelastung
fn ZumutbareBelastung(gde: Euro, kinderzahl: Ganzzahl, tarifart: Tarifart): EuroCent
Zumutbare Belastung (§ 33 Absatz 3 EStG) — staffelweise über die
drei GdE-Stufen (bis 15.340 / bis 51.130 / darüber), mit den
Prozentsätzen der vier Personengruppen (keine Kinder Grund/Splitting,
1–2 Kinder, ≥ 3 Kinder). „Kinder" sind die mit Freibetrag § 32 Abs. 6
oder Kindergeld-Anspruch (§ 33 Abs. 3 Satz 2 — hier kinderzahl).
Parameter
| Name | Beschreibung |
|---|---|
gde |
Gesamtbetrag der Einkünfte |
kinderzahl |
Zahl der zu berücksichtigenden Kinder |
tarifart |
Grund- oder Splittingtarif (nur bei 0 Kindern relevant) |
Rückgabe — zumutbare Belastung (EuroCent-genau)
Quelle: § 33 Absatz 3 EStG — § 33 EStG
fn AbziehbareAussergewoehnlicheBelastungen
fn AbziehbareAussergewoehnlicheBelastungen(fall: EinkommensteuerFall, gde: Euro): Euro
Abziehbare außergewöhnliche Belastungen (§ 33 Absatz 1 EStG): Summe der zwangsläufigen Aufwendungen, soweit sie die zumutbare Belastung (§ 33 Abs. 3) übersteigt; nie negativ, auf volle Euro abgerundet.
Parameter
| Name | Beschreibung |
|---|---|
fall |
die Veranlagungseingaben |
gde |
Gesamtbetrag der Einkünfte (Bezugsgröße der zumutbaren Belastung) |
Rückgabe — abziehbarer Betrag in vollen Euro
Quelle: § 33 Absatz 1 EStG — § 33 EStG
fn AbziehbareSpenden
fn AbziehbareSpenden(fall: EinkommensteuerFall, gde: Euro): Euro
Abziehbare Spenden (§ 10b Absatz 1 EStG): Summe der Zuwendungen, gedeckelt auf den Höchstbetrag = größerer Wert aus 20 % des Gesamtbetrags der Einkünfte und 4 ‰ der Umsätze + Löhne; auf volle Euro abgerundet.
Parameter
| Name | Beschreibung |
|---|---|
fall |
die Veranlagungseingaben |
gde |
Gesamtbetrag der Einkünfte (Bezugsgröße Variante 1) |
Rückgabe — abziehbare Spenden in vollen Euro
Quelle: § 10b Absatz 1 EStG — § 10b EStG
fn Einkommen
fn Einkommen(gesamtbetrag: Euro, fall: EinkommensteuerFall): Euro
Einkommen (§ 2 Absatz 4 EStG): Gesamtbetrag der Einkünfte vermindert um die Sonderausgaben (sonstige + abziehbare Spenden § 10b) und die abziehbaren außergewöhnlichen Belastungen (§ 33).
Parameter
| Name | Beschreibung |
|---|---|
gesamtbetrag |
Gesamtbetrag der Einkünfte (Stufe zuvor) |
fall |
die Veranlagungseingaben |
Rückgabe — Einkommen in vollen Euro
Quelle: § 2 Absatz 4 EStG — § 2 EStG
fn ZuVersteuerndesEinkommen
fn ZuVersteuerndesEinkommen(einkommen: Euro, fall: EinkommensteuerFall): Euro
Zu versteuerndes Einkommen (§ 2 Absatz 5 Satz 1 EStG): Einkommen vermindert um die Freibeträge nach § 32 Absatz 6 (Kinder) und die sonstigen vom Einkommen abzuziehenden Beträge.
Parameter
| Name | Beschreibung |
|---|---|
einkommen |
Einkommen (Stufe zuvor) |
fall |
die Veranlagungseingaben |
Rückgabe — zu versteuerndes Einkommen in vollen Euro (kann bei Verlusten negativ sein — § 10d nicht modelliert)
Quelle: § 2 Absatz 5 Satz 1 EStG — § 2 EStG
fn TariflicheEinkommensteuer
fn TariflicheEinkommensteuer(zve: Euro, tarifart: Tarifart): Euro
Tarifliche Einkommensteuer (§ 32a EStG): Grund- oder Splittingtarif. Negatives zvE → 0 (§ 32a für negatives zvE nicht definiert; § 10d Verlustabzug ist Verfahren, nicht modelliert).
Parameter
| Name | Beschreibung |
|---|---|
zve |
zu versteuerndes Einkommen in vollen Euro |
tarifart |
Grund- oder Splittingtarif |
Rückgabe — tarifliche Einkommensteuer in vollen Euro
Quelle: § 32a Absatz 1 und 5 EStG — § 32a EStG
fn FestzusetzendeEinkommensteuer
fn FestzusetzendeEinkommensteuer(tariflich: Euro, fall: EinkommensteuerFall): Euro
Festzusetzende Einkommensteuer (§ 2 Absatz 6 EStG): tarifliche Steuer vermindert um Anrechnungen/Steuerermäßigungen, vermehrt um Hinzurechnungen (Komponenten + Kappungen = anderes Recht/Eingabe; keine Untergrenze — der Wortlaut sieht keine vor).
Parameter
| Name | Beschreibung |
|---|---|
tariflich |
tarifliche Einkommensteuer (Stufe zuvor) |
fall |
die Veranlagungseingaben |
Rückgabe — festzusetzende Einkommensteuer in vollen Euro
Quelle: § 2 Absatz 6 EStG — § 2 EStG
fn BerechneEinkommensteuer
fn BerechneEinkommensteuer(fall: EinkommensteuerFall): EinkommensteuerErgebnis
Orchestrator — vollständige Veranlagung in gesetzlicher Reihenfolge (§ 2 EStG). Füllt jede Zwischengröße ins Ergebnis-Datensatz.
Parameter
| Name | Beschreibung |
|---|---|
fall |
die Veranlagungseingaben |
Rückgabe — das Veranlagungsergebnis mit allen Zwischengrößen
Quelle: § 2 EStG, § 32a EStG — § 2 EStG, § 32a EStG
Explizit ausgeschlossene Konstellationen
| In | Stelle | Begründung |
|---|---|---|
EstGrundtarif |
Z. 218 | § 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve}) · Quelle: § 32a Absatz 1 EStG |
EstSplitting |
Z. 247 | § 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve}) · Quelle: § 32a Absatz 5 EStG |
est.test
est.test.findsl
Akzeptanztests — Einkommensteuer § 2 + § 32a EStG (VZ 2026)
Sollwerte von Hand aus dem Wortlaut gerechnet (Quelle
examples/est/estg.xml, Fassung „ab Veranlagungszeitraum 2026").
§ 32a Satz 6: Steuerbetrag auf vollen Euro abgerundet.
Tarif-Größen: y = (zvE − 12.348)/10.000, z = (zvE − 17.799)/10.000.
Zonen: Nr. 2 (914,51·y + 1.400)·y; Nr. 3
(173,10·z + 2.397)·z + 1.034,87; Nr. 4 0,42·x − 11.135,63;
Nr. 5 0,45·x − 19.470,38. Splitting (Abs. 5) = 2·Grundtarif(⌊zvE/2⌋).
§ 32 Abs. 6: je Kind (3.414 + 1.464)·faktor·Monate/12·auslandsfaktor. § 33 Abs. 3 zumutbare Belastung staffelweise (Stufen 15.340 / 51.130; Sätze ohne Kind Grund 5/6/7 %, Splitting 4/5/6 %; 1–2 Kinder 2/3/4 %; ≥3 Kinder 1/1/2 %). § 10b: Spenden ≤ max(20 % GdE; 4 ‰ Umsätze+Löhne). Modellierungs-Entscheidung: Kategorie-Abzugssummen auf volle Euro abgerundet (s. est.findsl Datei-Doc).
Prüfungen
prüfe § 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)
prüfe "§ 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)"
Testfall — zvE = 0 → 0
EstGrundtarif(0) == 0
Testfall — zvE = Grundfreibetrag 12.348 → 0 (bis-Grenze inklusiv)
EstGrundtarif(12.348) == 0
Testfall — zvE = 12.349 (Zone-2-Beginn) → 0 (Steuer rundet auf 0 ab)
// y = 1/10000 = 0,0001 → (914,51·0,0001 + 1.400)·0,0001
// = 0,14000914… → abrunden 0
EstGrundtarif(12.349) == 0
prüfe § 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)
prüfe "§ 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)"
Testfall — zvE = 15.000
// y = (15.000 − 12.348)/10.000 = 0,2652
// (914,51·0,2652 + 1.400)·0,2652 = 435,5984… → abrunden 435
EstGrundtarif(15.000) == 435
Testfall — zvE = 17.799 (obere Grenze Zone 2)
// y = (17.799 − 12.348)/10.000 = 0,5451
// (914,51·0,5451 + 1.400)·0,5451 = 1.034,99… → abrunden 1.034
EstGrundtarif(17.799) == 1.034
prüfe § 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)
prüfe "§ 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)"
Testfall — zvE = 17.800 (Zone-3-Beginn)
// z = (17.800 − 17.799)/10.000 = 0,0001
// (173,10·0,0001 + 2.397)·0,0001 + 1.034,87 = 1.035,109… → 1.035
EstGrundtarif(17.800) == 1.035
Testfall — zvE = 50.000
// z = (50.000 − 17.799)/10.000 = 3,2201
// (173,10·3,2201 + 2.397)·3,2201 + 1.034,87 = 10.548,… → 10.548
EstGrundtarif(50.000) == 10.548
Testfall — zvE = 69.878 (obere Grenze Zone 3)
EstGrundtarif(69.878) == 18.213
prüfe § 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)
prüfe "§ 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)"
Testfall — zvE = 69.879 (Zone-4-Beginn, stetiger Anschluss)
// 0,42·69.879 − 11.135,63 = 18.213,55 → abrunden 18.213
EstGrundtarif(69.879) == 18.213
Testfall — zvE = 100.000
// 0,42·100.000 − 11.135,63 = 30.864,37 → abrunden 30.864
EstGrundtarif(100.000) == 30.864
Testfall — zvE = 277.825 (obere Grenze Zone 4)
// 0,42·277.825 − 11.135,63 = 105.550,87 → abrunden 105.550
EstGrundtarif(277.825) == 105.550
prüfe § 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)
prüfe "§ 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)"
Testfall — zvE = 277.826 (Zone-5-Beginn)
// 0,45·277.826 − 19.470,38 = 105.551,32 → abrunden 105.551
EstGrundtarif(277.826) == 105.551
Testfall — zvE = 300.000
// 0,45·300.000 − 19.470,38 = 115.529,62 → abrunden 115.529
EstGrundtarif(300.000) == 115.529
prüfe § 32a Abs. 5 EStG — Splitting-Verfahren
prüfe "§ 32a Abs. 5 EStG — Splitting-Verfahren"
Testfall — zvE = 200.000 → 2 · Grundtarif(100.000) = 2 · 30.864
EstSplitting(200.000) == 61.728
Testfall — zvE = 100.001 → Hälfte 50.000 (abgerundet) → 2 · 10.548
EstSplitting(100.001) == 21.096
Testfall — zvE = 150.000 → Hälfte 75.000 → 2 · Grundtarif(75.000)
// 0,42·75.000 − 11.135,63 = 20.364,37 → 20.364 ; 2·20.364
EstSplitting(150.000) == 40.728
prüfe § 32a EStG — unzulässige Eingaben (abbruch)
prüfe "§ 32a EStG — unzulässige Eingaben (abbruch)"
Testfall — negatives zvE (Grundtarif) ist nicht definiert (erwartet abbruch)
var n: Euro = -1
EstGrundtarif(n)
Testfall — negatives gemeinsames zvE (Splitting) ist nicht definiert (erwartet abbruch)
var n: Euro = -2
EstSplitting(n)
prüfe § 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)
prüfe "§ 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)"
Testfall — Fall K — Single, 2 Kinder, agB- + Spenden-Posten
// GdE 60.000. zumutbare Belastung (2 Kinder, Stufen 2/3/4 %):
// 2%·15.340 + 3%·(51.130−15.340) + 4%·(60.000−51.130)
// = 306,80 + 1.073,70 + 354,80 = 1.735,30
// agB abziehbar = nichtNeg(5.000 − 1.735,30).abrunden() = 3.264
// Spenden abziehbar = min(2.000; 20%·60.000=12.000) = 2.000
// SA = 4.000 + 2.000 = 6.000
// KFB = ((3.414+1.464)·1·12/12·100% ·2 Kinder).abrunden() = 9.756
// Einkommen = 60.000 − 6.000 − 3.264 = 50.736
// zvE = 50.736 − 9.756 = 40.980 → Grundtarif = 7.521
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 60.000,
sonstigeSonderausgaben = 4.000,
spenden = [2.000],
aussergewoehnlicheAufwendungen = [5.000],
kinder = [Kind(), Kind()],
))
e.gesamtbetragDerEinkuenfte == 60.000
und e.kinderfreibetraege == 9.756
und e.abziehbareAussergewoehnlicheBelastungen == 3.264
und e.einkommen == 50.736
und e.zuVersteuerndesEinkommen == 40.980
und e.tariflicheEinkommensteuer == 7.521
und e.festzusetzendeEinkommensteuer == 7.521
Testfall — Fall S — Splitting, 3 Kinder (eines halbjährig), Spenden gekappt
// SdE = 100.000 → GdE 100.000. zumutbar (3 Kinder, 1/1/2 %):
// 1%·15.340 + 1%·35.790 + 2%·48.870 = 153,40+357,90+977,40 = 1.488,70
// agB abziehbar = (8.000 − 1.488,70).abrunden() = 6.511
// Spenden abziehbar = min(30.000; max(20%·100.000=20.000; 0)) = 20.000
// KFB Splitting faktor 2: 2·4.878·2 + 4.878·2·6/12 = 19.512 + 4.878 = 24.390
// Einkommen = 100.000 − 20.000 − 6.511 = 73.489
// zvE = 73.489 − 24.390 = 49.099 → Splitting=2·Grundtarif(24.549)=5.462
// festzusetzend = 5.462 − 2.500 + 600 = 3.562
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 100.000,
spenden = [10.000, 20.000],
aussergewoehnlicheAufwendungen = [3.000, 5.000],
kinder = [
Kind(faktor = 2),
Kind(faktor = 2),
Kind(faktor = 2, berücksichtigteMonate = 6),
],
tarifart = Splitting,
anrechnungenUndErmaessigungen = 2.500,
hinzurechnungen = 600,
))
e.kinderfreibetraege == 24.390
und e.abziehbareAussergewoehnlicheBelastungen == 6.511
und e.einkommen == 73.489
und e.zuVersteuerndesEinkommen == 49.099
und e.tariflicheEinkommensteuer == 5.462
und e.festzusetzendeEinkommensteuer == 3.562
Testfall — Fall L — agB unter zumutbarer Belastung → 0 abziehbar
// GdE 40.000, 0 Kinder, Grundtarif: zumutbar
// 5%·15.340 + 6%·(40.000−15.340) = 767 + 1.479,60 = 2.246,60
// 1.000 < 2.246,60 → abziehbare agB = 0
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 40.000,
aussergewoehnlicheAufwendungen = [1.000],
))
e.abziehbareAussergewoehnlicheBelastungen == 0
und e.einkommen == 40.000
und e.zuVersteuerndesEinkommen == 40.000
und e.tariflicheEinkommensteuer == 7.209
Testfall — Fall 0 — leere Listen ≙ alte Skalar-0-Kaskade (Regressionsanker)
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 50.000,
))
e.kinderfreibetraege == 0
und e.abziehbareAussergewoehnlicheBelastungen == 0
und e.einkommen == 50.000
und e.zuVersteuerndesEinkommen == 50.000
und e.tariflicheEinkommensteuer == 10.548
# Einkommensteuer — Veranlagungsschema § 2 EStG + Tarif § 32a EStG (VZ 2026)
*Bildet die Einkommensteuer-Kaskade nach § 2 EStG ab, schließt mit dem tariflichen Einkommensteuerbetrag (§ 32a) und der festzusetzenden Einkommensteuer (§ 2 Abs.*
## Inhalt
- [est](#est)
- Konstanten
- [konst GFB](#konst-gfb)
- [konst ZONE_2_OBERGRENZE](#konst-zone-2-obergrenze)
- [konst ZONE_3_OBERGRENZE](#konst-zone-3-obergrenze)
- [konst ZONE_4_OBERGRENZE](#konst-zone-4-obergrenze)
- [konst ZEHNTAUSEND](#konst-zehntausend)
- [konst ZONE_2_PROGRESSION](#konst-zone-2-progression)
- [konst ZONE_2_LINEAR](#konst-zone-2-linear)
- [konst ZONE_3_PROGRESSION](#konst-zone-3-progression)
- [konst ZONE_3_LINEAR](#konst-zone-3-linear)
- [konst ZONE_3_KONSTANTE](#konst-zone-3-konstante)
- [konst ZONE_4_SATZ](#konst-zone-4-satz)
- [konst ZONE_4_ABZUG](#konst-zone-4-abzug)
- [konst ZONE_5_SATZ](#konst-zone-5-satz)
- [konst ZONE_5_ABZUG](#konst-zone-5-abzug)
- [konst KINDERFREIBETRAG](#konst-kinderfreibetrag)
- [konst BEA_FREIBETRAG](#konst-bea-freibetrag)
- [konst ZWOELF](#konst-zwoelf)
- [konst ZMB_STUFE_1](#konst-zmb-stufe-1)
- [konst ZMB_STUFE_2](#konst-zmb-stufe-2)
- [konst ZMB_OHNE_KIND_GRUND_1](#konst-zmb-ohne-kind-grund-1)
- [konst ZMB_OHNE_KIND_GRUND_2](#konst-zmb-ohne-kind-grund-2)
- [konst ZMB_OHNE_KIND_GRUND_3](#konst-zmb-ohne-kind-grund-3)
- [konst ZMB_OHNE_KIND_SPLIT_1](#konst-zmb-ohne-kind-split-1)
- [konst ZMB_OHNE_KIND_SPLIT_2](#konst-zmb-ohne-kind-split-2)
- [konst ZMB_OHNE_KIND_SPLIT_3](#konst-zmb-ohne-kind-split-3)
- [konst ZMB_1_2_KINDER_1](#konst-zmb-1-2-kinder-1)
- [konst ZMB_1_2_KINDER_2](#konst-zmb-1-2-kinder-2)
- [konst ZMB_1_2_KINDER_3](#konst-zmb-1-2-kinder-3)
- [konst ZMB_AB_3_KINDER_1](#konst-zmb-ab-3-kinder-1)
- [konst ZMB_AB_3_KINDER_2](#konst-zmb-ab-3-kinder-2)
- [konst ZMB_AB_3_KINDER_3](#konst-zmb-ab-3-kinder-3)
- [konst SPENDEN_HB_GDE](#konst-spenden-hb-gde)
- [konst SPENDEN_HB_UMSATZ](#konst-spenden-hb-umsatz)
- Datensätze
- [datensatz Kind](#datensatz-kind)
- [datensatz EinkommensteuerFall](#datensatz-einkommensteuerfall)
- [datensatz EinkommensteuerErgebnis](#datensatz-einkommensteuerergebnis)
- Funktionen
- [fn EstGrundtarif](#fn-estgrundtarif)
- [fn EstSplitting](#fn-estsplitting)
- [fn SummeDerEinkuenfte](#fn-summedereinkuenfte)
- [fn GesamtbetragDerEinkuenfte](#fn-gesamtbetragdereinkuenfte)
- [fn KinderfreibetragGesamt](#fn-kinderfreibetraggesamt)
- [fn ZumutbareBelastung](#fn-zumutbarebelastung)
- [fn AbziehbareAussergewoehnlicheBelastungen](#fn-abziehbareaussergewoehnlichebelastungen)
- [fn AbziehbareSpenden](#fn-abziehbarespenden)
- [fn Einkommen](#fn-einkommen)
- [fn ZuVersteuerndesEinkommen](#fn-zuversteuerndeseinkommen)
- [fn TariflicheEinkommensteuer](#fn-tariflicheeinkommensteuer)
- [fn FestzusetzendeEinkommensteuer](#fn-festzusetzendeeinkommensteuer)
- [fn BerechneEinkommensteuer](#fn-berechneeinkommensteuer)
- [est.test](#est-test)
- Prüfungen
- [prüfe § 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)](#prüfe-32a-abs-1-nr-1-estg-zone-1-grundfreibetrag)
- [prüfe § 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)](#prüfe-32a-abs-1-nr-2-estg-zone-2-eingangsprogression)
- [prüfe § 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)](#prüfe-32a-abs-1-nr-3-estg-zone-3-hauptprogression)
- [prüfe § 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)](#prüfe-32a-abs-1-nr-4-estg-zone-4-proportionalzone-42)
- [prüfe § 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)](#prüfe-32a-abs-1-nr-5-estg-zone-5-proportionalzone-45)
- [prüfe § 32a Abs. 5 EStG — Splitting-Verfahren](#prüfe-32a-abs-5-estg-splitting-verfahren)
- [prüfe § 32a EStG — unzulässige Eingaben (abbruch)](#prüfe-32a-estg-unzulässige-eingaben-abbruch)
- [prüfe § 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)](#prüfe-2-estg-kaskade-mit-32-abs-6-33-10b-listen)
## `est`
*`est.findsl`*
#### Einkommensteuer — Veranlagungsschema [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html) + Tarif [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html) (VZ 2026)
Bildet die **Einkommensteuer-Kaskade** nach [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html) ab, schließt mit
dem tariflichen Einkommensteuerbetrag (§ 32a) und der festzusetzenden
Einkommensteuer (§ 2 Abs. 6). Maßgebliche Quelle:
`examples/est/estg.xml` (juris-Stand 2026-05-06), § 32a/§ 32 Abs. 6 in
der konsolidierten Fassung „ab Veranlagungszeitraum 2026".
Gesetzliche Reihenfolge (jede Stufe = eigene Funktion, auditierbar):
Summe der Einkünfte (§ 2 Abs. 1–3) → Gesamtbetrag der Einkünfte
(§ 2 Abs. 3) → Einkommen (§ 2 Abs. 4) → zu versteuerndes Einkommen
(§ 2 Abs. 5) → tarifliche Einkommensteuer (§ 32a) → festzusetzende
Einkommensteuer (§ 2 Abs. 6).
**Echte Rechenvorschrift (modelliert) — auch mehr-entitätig:**
- **§ 32 Abs. 6 Kinderfreibetrag/BEA je Kind** über `Liste<Kind>`
(3.414 € + 1.464 € je Kind, Verdopplung Satz 2/3 per Faktor,
Zwölftelung Satz 5, Auslandskürzung Satz 4) → aggregiert.
- **§ 33 Abs. 1/3 außergewöhnliche Belastungen**: Summe der
zwangsläufigen Aufwendungen abzüglich der **zumutbaren Belastung**
(§ 33 Abs. 3, **staffelweise** über die drei GdE-Stufen × vier
Personengruppen).
- **§ 10b Abs. 1 Spenden**: abziehbar bis zum Höchstbetrag
max(20 % GdE; 4 ‰ (Umsätze + Löhne)).
- Die gesamte § 2-Verknüpfungs-Arithmetik + § 32a-Tarif + § 2 Abs. 6.
**Geprüfte Eingabe, weil anderes Recht / Verfahren (nicht Tooling-
Grenze):**
- **Ermittlung der sieben Einkunftsarten** je Art (Gewinn §§ 4–7k/13a,
Überschuss §§ 8–9a, § 20 Abs. 9, AfA § 7 mehrperiodig) — saldierter
Betrag je Art als Eingabe.
- **§ 24a / § 24b / § 13 Abs. 3** — Beträge als Eingabe (eigene §§).
- **Übrige Sonderausgaben §§ 10–10c** außer § 10b (Vorsorgeaufwen-
dungen mit eigenen Höchstbeträgen/Günstigerprüfung) — Aggregat-
Eingabe `sonstigeSonderausgaben`.
- **Verlustabzug § 10d** (mehrperiodig) — negatives zvE → 0 tariflich,
Verlustabzug selbst nicht modelliert.
- **Sachverhalte je Kind** (Kindschaftsverhältnis → `faktor`,
Auslands-Ländergruppe → `auslandsfaktor`, Berücksichtigungsmonate)
und die § 33-Zwangsläufigkeit/Angemessenheit (§ 33 Abs. 2),
§ 10b-Empfänger-Voraussetzungen (§ 10b Abs. 2) — Sachverhalt.
- **§ 32a Abs. 6** Witwen-/Gnadensplitting; **§ 2 Abs. 6-Komponenten**
(§§ 34c/35/35a/32d Abs. 3/4 …) als zwei gerichtete Aggregat-Eingaben;
Annexsteuern (SolZ, KiSt). Verfahren/eigene Gesetze.
**Modellierungs-Entscheidung (Statut schweigt):** jede listen-
abgeleitete Kategorie-Abzugssumme (Kinderfreibetrag, abziehbare agB,
abziehbare Spenden) wird auf **volle Euro abgerundet** (`.abrunden()`
mit Euro-Kontext),
bevor sie in die Euro-Kaskade eingeht — deterministisch, konsistent mit
§ 32a Abs. 1 Satz 1 (zvE auf volle Euro), fiskuskonservativ.
### Konstanten
#### konst `GFB`
```findsl
konst GFB: Euro = 12.348
```
Grundfreibetrag — bis zu diesem zu versteuernden Einkommen beträgt die
tarifliche Einkommensteuer 0 (§ 32a Absatz 1 Satz 2 Nummer 1).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 1 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_2_OBERGRENZE`
```findsl
konst ZONE_2_OBERGRENZE: Euro = 17.799
```
Obere Grenze der Eingangs-Progressionszone (Zone 2).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 2 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_3_OBERGRENZE`
```findsl
konst ZONE_3_OBERGRENZE: Euro = 69.878
```
Obere Grenze der Hauptprogressionszone (Zone 3).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 3 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_4_OBERGRENZE`
```findsl
konst ZONE_4_OBERGRENZE: Euro = 277.825
```
Obere Grenze der ersten Proportionalzone (Zone 4); darüber Zone 5.
> Quelle: § 32a Absatz 1 Satz 2 Nummer 4 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZEHNTAUSEND`
```findsl
konst ZEHNTAUSEND: Ganzzahl = 10.000
```
Teiler für die Größen „y" und „z": ein Zehntausendstel des den
jeweiligen Sockel übersteigenden, auf vollen Euro abgerundeten zvE
(§ 32a Absatz 1 Satz 3 und 4).
> Quelle: § 32a Absatz 1 Satz 3 und 4 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_2_PROGRESSION`
```findsl
konst ZONE_2_PROGRESSION: Dezimal = 914,51
```
Progressionskoeffizient der Zone 2 (Faktor vor y²).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 2 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_2_LINEAR`
```findsl
konst ZONE_2_LINEAR: Dezimal = 1.400
```
Linearer Koeffizient der Zone 2 (Faktor vor y).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 2 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_3_PROGRESSION`
```findsl
konst ZONE_3_PROGRESSION: Dezimal = 173,10
```
Progressionskoeffizient der Zone 3 (Faktor vor z²).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 3 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_3_LINEAR`
```findsl
konst ZONE_3_LINEAR: Dezimal = 2.397
```
Linearer Koeffizient der Zone 3 (Faktor vor z).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 3 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_3_KONSTANTE`
```findsl
konst ZONE_3_KONSTANTE: Dezimal = 1.034,87
```
Konstanter Summand der Zone 3 (Anschluss an Zone 2).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 3 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_4_SATZ`
```findsl
konst ZONE_4_SATZ: Prozent = 42%
```
Grenzsteuersatz der Proportionalzone 4 (Spitzensteuersatz).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 4 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_4_ABZUG`
```findsl
konst ZONE_4_ABZUG: EuroCent = 11.135,63
```
Abzugsbetrag der Zone 4 (0,42 · x − ZONE_4_ABZUG).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 4 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_5_SATZ`
```findsl
konst ZONE_5_SATZ: Prozent = 45%
```
Grenzsteuersatz der Proportionalzone 5 („Reichensteuer").
> Quelle: § 32a Absatz 1 Satz 2 Nummer 5 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `ZONE_5_ABZUG`
```findsl
konst ZONE_5_ABZUG: EuroCent = 19.470,38
```
Abzugsbetrag der Zone 5 (0,45 · x − ZONE_5_ABZUG).
> Quelle: § 32a Absatz 1 Satz 2 Nummer 5 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### konst `KINDERFREIBETRAG`
```findsl
konst KINDERFREIBETRAG: Euro = 3.414
```
Kinderfreibetrag (sächliches Existenzminimum) je Kind.
> Quelle: § 32 Absatz 6 Satz 1 EStG — [§ 32 EStG](https://www.gesetze-im-internet.de/estg/__32.html)
#### konst `BEA_FREIBETRAG`
```findsl
konst BEA_FREIBETRAG: Euro = 1.464
```
Freibetrag Betreuungs-/Erziehungs-/Ausbildungsbedarf (BEA) je Kind.
> Quelle: § 32 Absatz 6 Satz 1 EStG — [§ 32 EStG](https://www.gesetze-im-internet.de/estg/__32.html)
#### konst `ZWOELF`
```findsl
konst ZWOELF: Ganzzahl = 12
```
Teiler für die Zwölftelung je nicht erfüllten Kalendermonat.
> Quelle: § 32 Absatz 6 Satz 5 EStG — [§ 32 EStG](https://www.gesetze-im-internet.de/estg/__32.html)
#### konst `ZMB_STUFE_1`
```findsl
konst ZMB_STUFE_1: Euro = 15.340
```
Erste GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3).
> Quelle: § 33 Absatz 3 EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_STUFE_2`
```findsl
konst ZMB_STUFE_2: Euro = 51.130
```
Zweite GdE-Stufe der zumutbaren Belastung (§ 33 Abs. 3).
> Quelle: § 33 Absatz 3 EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_OHNE_KIND_GRUND_1`
```findsl
konst ZMB_OHNE_KIND_GRUND_1: Prozent = 5%
```
Zumutbare Belastung — keine Kinder, Grundtarif (§ 32a Abs. 1): Stufe 1/2/3.
> Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_OHNE_KIND_GRUND_2`
```findsl
konst ZMB_OHNE_KIND_GRUND_2: Prozent = 6%
```
> Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_OHNE_KIND_GRUND_3`
```findsl
konst ZMB_OHNE_KIND_GRUND_3: Prozent = 7%
```
> Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe a EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_OHNE_KIND_SPLIT_1`
```findsl
konst ZMB_OHNE_KIND_SPLIT_1: Prozent = 4%
```
Zumutbare Belastung — keine Kinder, Splitting (§ 32a Abs. 5/6): Stufe 1/2/3.
> Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_OHNE_KIND_SPLIT_2`
```findsl
konst ZMB_OHNE_KIND_SPLIT_2: Prozent = 5%
```
> Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_OHNE_KIND_SPLIT_3`
```findsl
konst ZMB_OHNE_KIND_SPLIT_3: Prozent = 6%
```
> Quelle: § 33 Absatz 3 Satz 1 Nummer 1 Buchstabe b EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_1_2_KINDER_1`
```findsl
konst ZMB_1_2_KINDER_1: Prozent = 2%
```
Zumutbare Belastung — ein oder zwei Kinder: Stufe 1/2/3.
> Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_1_2_KINDER_2`
```findsl
konst ZMB_1_2_KINDER_2: Prozent = 3%
```
> Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_1_2_KINDER_3`
```findsl
konst ZMB_1_2_KINDER_3: Prozent = 4%
```
> Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe a EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_AB_3_KINDER_1`
```findsl
konst ZMB_AB_3_KINDER_1: Prozent = 1%
```
Zumutbare Belastung — drei oder mehr Kinder: Stufe 1/2/3.
> Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_AB_3_KINDER_2`
```findsl
konst ZMB_AB_3_KINDER_2: Prozent = 1%
```
> Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `ZMB_AB_3_KINDER_3`
```findsl
konst ZMB_AB_3_KINDER_3: Prozent = 2%
```
> Quelle: § 33 Absatz 3 Satz 1 Nummer 2 Buchstabe b EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### konst `SPENDEN_HB_GDE`
```findsl
konst SPENDEN_HB_GDE: Prozent = 20%
```
Spenden-Höchstbetrag Variante 1: Anteil des Gesamtbetrags der Einkünfte.
> Quelle: § 10b Absatz 1 Satz 1 Nummer 1 EStG — [§ 10b EStG](https://www.gesetze-im-internet.de/estg/__10b.html)
#### konst `SPENDEN_HB_UMSATZ`
```findsl
konst SPENDEN_HB_UMSATZ: Prozent = 0,4%
```
Spenden-Höchstbetrag Variante 2: Promille der Umsätze + Löhne (4 ‰).
> Quelle: § 10b Absatz 1 Satz 1 Nummer 2 EStG — [§ 10b EStG](https://www.gesetze-im-internet.de/estg/__10b.html)
### Datensätze
#### datensatz `Kind`
```findsl
datensatz Kind(
faktor: Ganzzahl = 1, // § 32 Abs. 6 Satz 2/3
berücksichtigteMonate: Ganzzahl = 12, // § 32 Abs. 6 Satz 5
auslandsfaktor: Prozent = 100%, // § 32 Abs. 6 Satz 4
)
```
Sachverhalte je Kind (§ 32 Abs. 6). Die Beträge sind Gesetz; diese
Felder sind die Sachverhalts-Eingaben je Kind.
| Feld | Typ | Bedeutung |
| --- | --- | --- |
| `faktor` | `Ganzzahl` | 1 = einfacher Freibetrag; 2 = verdoppelt (§ 32 Abs. 6 Satz 2/3 — Kind zu beiden Ehegatten bzw. Satz-3-Fälle) |
| `berücksichtigteMonate` | `Ganzzahl` | Monate mit erfüllten Voraussetzungen (§ 32 Abs. 6 Satz 5: je fehlendem Monat 1/12) |
| `auslandsfaktor` | `Prozent` | Ländergruppen-Anteil für Auslandskinder (§ 32 Abs. 6 Satz 4; 100 % = Inlandskind) |
> Quelle: § 32 Absatz 6 EStG — [§ 32 EStG](https://www.gesetze-im-internet.de/estg/__32.html)
#### datensatz `EinkommensteuerFall`
```findsl
datensatz EinkommensteuerFall(
einkuenfteLandUndForstwirtschaft: Euro = 0, // § 2 Abs. 1 Nr. 1
einkuenfteGewerbebetrieb: Euro = 0, // § 2 Abs. 1 Nr. 2
einkuenfteSelbstaendigeArbeit: Euro = 0, // § 2 Abs. 1 Nr. 3
einkuenfteNichtselbstaendigeArbeit: Euro = 0, // § 2 Abs. 1 Nr. 4
einkuenfteKapitalvermoegen: Euro = 0, // § 2 Abs. 1 Nr. 5
einkuenfteVermietungVerpachtung: Euro = 0, // § 2 Abs. 1 Nr. 6
sonstigeEinkuenfte: Euro = 0, // § 2 Abs. 1 Nr. 7
altersentlastungsbetrag: Euro = 0, // § 24a
entlastungsbetragAlleinerziehende: Euro = 0, // § 24b
freibetragLandUndForstwirtschaft: Euro = 0, // § 13 Abs. 3
sonstigeSonderausgaben: Euro = 0, // §§ 10–10c o. § 10b
spenden: Liste<Euro> = []<Euro>, // § 10b Abs. 1
umsaetzeUndLoehne: Euro = 0, // § 10b Abs. 1 S. 1 Nr. 2
aussergewoehnlicheAufwendungen: Liste<Euro> = []<Euro>, // § 33
kinder: Liste<Kind> = []<Kind>, // § 32 Abs. 6
sonstigeAbzuegeVomEinkommen: Euro = 0, // § 2 Abs. 5 S. 1
tarifart: Tarifart = Grundtarif, // §§ 26, 26b
anrechnungenUndErmaessigungen: Euro = 0, // § 2 Abs. 6 S. 1
hinzurechnungen: Euro = 0, // § 2 Abs. 6 S. 1–3
)
```
Eingaben für die Einkommensteuer-Veranlagung.
| Feld | Typ | Bedeutung |
| --- | --- | --- |
| `einkuenfteLandUndForstwirtschaft` | `Euro` | Einkünfte § 2 Abs. 1 Nr. 1 (§§ 13–14) |
| `einkuenfteGewerbebetrieb` | `Euro` | Einkünfte § 2 Abs. 1 Nr. 2 (§§ 15–17) |
| `einkuenfteSelbstaendigeArbeit` | `Euro` | Einkünfte § 2 Abs. 1 Nr. 3 (§ 18) |
| `einkuenfteNichtselbstaendigeArbeit` | `Euro` | Einkünfte § 2 Abs. 1 Nr. 4 (§ 19) |
| `einkuenfteKapitalvermoegen` | `Euro` | veranlagte Einkünfte § 2 Abs. 1 Nr. 5 (§ 20) |
| `einkuenfteVermietungVerpachtung` | `Euro` | Einkünfte § 2 Abs. 1 Nr. 6 (§ 21) |
| `sonstigeEinkuenfte` | `Euro` | sonstige Einkünfte § 2 Abs. 1 Nr. 7 (§ 22) |
| `altersentlastungsbetrag` | `Euro` | Altersentlastungsbetrag (§ 24a) |
| `entlastungsbetragAlleinerziehende` | `Euro` | Entlastungsbetrag Alleinerziehende (§ 24b) |
| `freibetragLandUndForstwirtschaft` | `Euro` | Abzug nach § 13 Absatz 3 |
| `sonstigeSonderausgaben` | `Euro` | Sonderausgaben §§ 10–10c ohne § 10b (Vorsorge u. a. — anderes Recht) |
| `spenden` | `Liste<Euro>` | abziehbare Zuwendungen § 10b Abs. 1 (Voraussetzungen Abs. 2 = Sachverhalt) |
| `umsaetzeUndLoehne` | `Euro` | Basis der 4-‰-Höchstbetrags- Variante (§ 10b Abs. 1 Satz 1 Nr. 2) |
| `aussergewoehnlicheAufwendungen` | `Liste<Euro>` | zwangsläufige Aufwendungen § 33 (Abs. 2 = Sachverhalt), vor zumutbarer Belastung |
| `kinder` | `Liste<Kind>` | zu berücksichtigende Kinder (§ 32 Abs. 6) |
| `sonstigeAbzuegeVomEinkommen` | `Euro` | sonstige vom Einkommen abzuziehende Beträge (§ 2 Abs. 5 Satz 1) |
| `tarifart` | `Tarifart` | Grund- oder Splittingtarif (§§ 26, 26b) |
| `anrechnungenUndErmaessigungen` | `Euro` | § 2 Abs. 6 „vermindert um" |
| `hinzurechnungen` | `Euro` | § 2 Abs. 6 „vermehrt um" (S. 1–3) |
> Quelle: § 2 EStG — [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html)
#### datensatz `EinkommensteuerErgebnis`
```findsl
datensatz EinkommensteuerErgebnis(
summeDerEinkuenfte: Euro, // § 2 Abs. 1–3
gesamtbetragDerEinkuenfte: Euro, // § 2 Abs. 3
kinderfreibetraege: Euro, // § 32 Abs. 6
abziehbareAussergewoehnlicheBelastungen: Euro, // § 33
einkommen: Euro, // § 2 Abs. 4
zuVersteuerndesEinkommen: Euro, // § 2 Abs. 5
tariflicheEinkommensteuer: Euro, // § 32a
festzusetzendeEinkommensteuer: Euro, // § 2 Abs. 6
)
```
Ergebnis der Veranlagung — jede Zwischengröße der gesetzlichen
Reihenfolge des [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html) als eigenes Feld (Schritt-für-Schritt-Audit).
| Feld | Typ | Bedeutung |
| --- | --- | --- |
| `summeDerEinkuenfte` | `Euro` | Summe der Einkünfte (§ 2 Abs. 1–3) |
| `gesamtbetragDerEinkuenfte` | `Euro` | Gesamtbetrag der Einkünfte (§ 2 Abs. 3) |
| `kinderfreibetraege` | `Euro` | Freibeträge § 32 Abs. 6 (aggregiert) |
| `abziehbareAussergewoehnlicheBelastungen` | `Euro` | § 33 nach zumutbarer Belastung |
| `einkommen` | `Euro` | Einkommen (§ 2 Abs. 4) |
| `zuVersteuerndesEinkommen` | `Euro` | zu versteuerndes Einkommen (§ 2 Abs. 5) |
| `tariflicheEinkommensteuer` | `Euro` | tarifliche Einkommensteuer (§ 32a) |
| `festzusetzendeEinkommensteuer` | `Euro` | festzusetzende Einkommensteuer (§ 2 Abs. 6) |
> Quelle: § 2 EStG — [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html)
### Funktionen
#### fn `EstGrundtarif`
```findsl
fn EstGrundtarif(zve: Euro): Euro
```
Tariflicher Einkommensteuerbetrag nach dem Grundtarif ([§ 32a Absatz 1 EStG](https://www.gesetze-im-internet.de/estg/__32a.html)). Das zu versteuernde Einkommen ist nach Satz 1 auf volle Euro
abgerundet zu verstehen (durch den `Euro`-Typ bereits ganzzahlig). Der
sich ergebende Steuerbetrag wird nach Satz 6 auf den nächsten vollen
Euro abgerundet.
Mit den Hilfsgrößen $y = \frac{\text{zvE} - \text{GFB}}{10000}$ (Zone 2)
und $z = \frac{\text{zvE} - \text{ZONE\_2}}{10000}$ (Zone 3) lautet der
Tarif zonenweise:
$$
\text{ESt}(\text{zvE}) =
\begin{cases}
0 & \text{zvE} \le \text{GFB} \\
(a_2\,y + b_2)\,y & \text{Zone 2} \\
(a_3\,z + b_3)\,z + c_3 & \text{Zone 3} \\
0{,}42 \cdot \text{zvE} - C_4 & \text{Zone 4} \\
0{,}45 \cdot \text{zvE} - C_5 & \text{Zone 5}
\end{cases}
$$
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `zve` | zu versteuerndes Einkommen in vollen Euro (geprüfte Eingabe, ≥ 0; negativ → `abbruch`) |
**Rückgabe** — tarifliche Einkommensteuer in vollen Euro (Grundtarif)
> Quelle: § 32a Absatz 1 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### fn `EstSplitting`
```findsl
fn EstSplitting(zve: Euro): Euro
```
Tariflicher Einkommensteuerbetrag nach dem Splitting-Verfahren für
zusammen veranlagte Ehegatten ([§ 32a Absatz 5 EStG](https://www.gesetze-im-internet.de/estg/__32a.html)): das Zweifache des
Steuerbetrags, der sich für die Hälfte des gemeinsam zu versteuernden
Einkommens nach Absatz 1 ergibt. Die Hälfte wird nach Absatz 1 Satz 1
auf volle Euro abgerundet.
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `zve` | gemeinsam zu versteuerndes Einkommen der Ehegatten in vollen Euro (geprüfte Eingabe, ≥ 0; negativ → `abbruch`) |
**Rückgabe** — tarifliche Einkommensteuer in vollen Euro (Splitting)
> Quelle: § 32a Absatz 5 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### fn `SummeDerEinkuenfte`
```findsl
fn SummeDerEinkuenfte(fall: EinkommensteuerFall): Euro
```
Summe der Einkünfte ([§ 2 Absatz 1 und 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html)): Summe der sieben
Einkunftsarten. Negative Einkünfte einzelner Arten mindern die Summe
(einkunftsartübergreifende Verlustverrechnungsbeschränkungen sind
anderes Recht und in den Eingaben bereits berücksichtigt).
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `fall` | die Veranlagungseingaben |
**Rückgabe** — Summe der Einkünfte in vollen Euro
> Quelle: § 2 Absatz 1 und 2 EStG — [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html)
#### fn `GesamtbetragDerEinkuenfte`
```findsl
fn GesamtbetragDerEinkuenfte(summe: Euro, fall: EinkommensteuerFall): Euro
```
Gesamtbetrag der Einkünfte ([§ 2 Absatz 3 EStG](https://www.gesetze-im-internet.de/estg/__2.html)): Summe der Einkünfte
vermindert um Altersentlastungsbetrag (§ 24a), Entlastungsbetrag für
Alleinerziehende (§ 24b) und Abzug nach § 13 Absatz 3.
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `summe` | Summe der Einkünfte (Stufe zuvor) |
| `fall` | die Veranlagungseingaben |
**Rückgabe** — Gesamtbetrag der Einkünfte in vollen Euro
> Quelle: § 2 Absatz 3 EStG — [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html)
#### fn `KinderfreibetragGesamt`
```findsl
fn KinderfreibetragGesamt(kinder: Liste<Kind>): Euro
```
Kinderfreibetrag + BEA-Freibetrag, aggregiert über alle Kinder
([§ 32 Absatz 6 EStG](https://www.gesetze-im-internet.de/estg/__32.html)): je Kind `(3.414 + 1.464) · faktor ·
berücksichtigteMonate/12 · auslandsfaktor`; die Summe wird auf volle
Euro abgerundet (Modellierungs-Entscheidung, s. Datei-Doc).
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `kinder` | die zu berücksichtigenden Kinder |
**Rückgabe** — Gesamt-Freibetrag in vollen Euro
> Quelle: § 32 Absatz 6 EStG — [§ 32 EStG](https://www.gesetze-im-internet.de/estg/__32.html)
#### fn `ZumutbareBelastung`
```findsl
fn ZumutbareBelastung(gde: Euro, kinderzahl: Ganzzahl, tarifart: Tarifart): EuroCent
```
Zumutbare Belastung ([§ 33 Absatz 3 EStG](https://www.gesetze-im-internet.de/estg/__33.html)) — **staffelweise** über die
drei GdE-Stufen (bis 15.340 / bis 51.130 / darüber), mit den
Prozentsätzen der vier Personengruppen (keine Kinder Grund/Splitting,
1–2 Kinder, ≥ 3 Kinder). „Kinder" sind die mit Freibetrag § 32 Abs. 6
oder Kindergeld-Anspruch (§ 33 Abs. 3 Satz 2 — hier `kinderzahl`).
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `gde` | Gesamtbetrag der Einkünfte |
| `kinderzahl` | Zahl der zu berücksichtigenden Kinder |
| `tarifart` | Grund- oder Splittingtarif (nur bei 0 Kindern relevant) |
**Rückgabe** — zumutbare Belastung (EuroCent-genau)
> Quelle: § 33 Absatz 3 EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### fn `AbziehbareAussergewoehnlicheBelastungen`
```findsl
fn AbziehbareAussergewoehnlicheBelastungen(fall: EinkommensteuerFall, gde: Euro): Euro
```
Abziehbare außergewöhnliche Belastungen ([§ 33 Absatz 1 EStG](https://www.gesetze-im-internet.de/estg/__33.html)): Summe der
zwangsläufigen Aufwendungen, soweit sie die zumutbare Belastung
(§ 33 Abs. 3) übersteigt; nie negativ, auf volle Euro abgerundet.
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `fall` | die Veranlagungseingaben |
| `gde` | Gesamtbetrag der Einkünfte (Bezugsgröße der zumutbaren Belastung) |
**Rückgabe** — abziehbarer Betrag in vollen Euro
> Quelle: § 33 Absatz 1 EStG — [§ 33 EStG](https://www.gesetze-im-internet.de/estg/__33.html)
#### fn `AbziehbareSpenden`
```findsl
fn AbziehbareSpenden(fall: EinkommensteuerFall, gde: Euro): Euro
```
Abziehbare Spenden ([§ 10b Absatz 1 EStG](https://www.gesetze-im-internet.de/estg/__10b.html)): Summe der Zuwendungen,
gedeckelt auf den Höchstbetrag = größerer Wert aus 20 % des
Gesamtbetrags der Einkünfte und 4 ‰ der Umsätze + Löhne; auf volle
Euro abgerundet.
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `fall` | die Veranlagungseingaben |
| `gde` | Gesamtbetrag der Einkünfte (Bezugsgröße Variante 1) |
**Rückgabe** — abziehbare Spenden in vollen Euro
> Quelle: § 10b Absatz 1 EStG — [§ 10b EStG](https://www.gesetze-im-internet.de/estg/__10b.html)
#### fn `Einkommen`
```findsl
fn Einkommen(gesamtbetrag: Euro, fall: EinkommensteuerFall): Euro
```
Einkommen ([§ 2 Absatz 4 EStG](https://www.gesetze-im-internet.de/estg/__2.html)): Gesamtbetrag der Einkünfte vermindert
um die Sonderausgaben (sonstige + abziehbare Spenden § 10b) und die
abziehbaren außergewöhnlichen Belastungen (§ 33).
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `gesamtbetrag` | Gesamtbetrag der Einkünfte (Stufe zuvor) |
| `fall` | die Veranlagungseingaben |
**Rückgabe** — Einkommen in vollen Euro
> Quelle: § 2 Absatz 4 EStG — [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html)
#### fn `ZuVersteuerndesEinkommen`
```findsl
fn ZuVersteuerndesEinkommen(einkommen: Euro, fall: EinkommensteuerFall): Euro
```
Zu versteuerndes Einkommen ([§ 2 Absatz 5 Satz 1 EStG](https://www.gesetze-im-internet.de/estg/__2.html)): Einkommen
vermindert um die Freibeträge nach § 32 Absatz 6 (Kinder) und die
sonstigen vom Einkommen abzuziehenden Beträge.
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `einkommen` | Einkommen (Stufe zuvor) |
| `fall` | die Veranlagungseingaben |
**Rückgabe** — zu versteuerndes Einkommen in vollen Euro (kann bei Verlusten negativ sein — § 10d nicht modelliert)
> Quelle: § 2 Absatz 5 Satz 1 EStG — [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html)
#### fn `TariflicheEinkommensteuer`
```findsl
fn TariflicheEinkommensteuer(zve: Euro, tarifart: Tarifart): Euro
```
Tarifliche Einkommensteuer ([§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)): Grund- oder Splittingtarif.
Negatives zvE → 0 (§ 32a für negatives zvE nicht definiert; § 10d
Verlustabzug ist Verfahren, nicht modelliert).
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `zve` | zu versteuerndes Einkommen in vollen Euro |
| `tarifart` | Grund- oder Splittingtarif |
**Rückgabe** — tarifliche Einkommensteuer in vollen Euro
> Quelle: § 32a Absatz 1 und 5 EStG — [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
#### fn `FestzusetzendeEinkommensteuer`
```findsl
fn FestzusetzendeEinkommensteuer(tariflich: Euro, fall: EinkommensteuerFall): Euro
```
Festzusetzende Einkommensteuer ([§ 2 Absatz 6 EStG](https://www.gesetze-im-internet.de/estg/__2.html)): tarifliche Steuer
vermindert um Anrechnungen/Steuerermäßigungen, vermehrt um
Hinzurechnungen (Komponenten + Kappungen = anderes Recht/Eingabe;
keine Untergrenze — der Wortlaut sieht keine vor).
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `tariflich` | tarifliche Einkommensteuer (Stufe zuvor) |
| `fall` | die Veranlagungseingaben |
**Rückgabe** — festzusetzende Einkommensteuer in vollen Euro
> Quelle: § 2 Absatz 6 EStG — [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html)
#### fn `BerechneEinkommensteuer`
```findsl
fn BerechneEinkommensteuer(fall: EinkommensteuerFall): EinkommensteuerErgebnis
```
Orchestrator — vollständige Veranlagung in gesetzlicher Reihenfolge
([§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html)). Füllt jede Zwischengröße ins Ergebnis-Datensatz.
**Parameter**
| Name | Beschreibung |
| --- | --- |
| `fall` | die Veranlagungseingaben |
**Rückgabe** — das Veranlagungsergebnis mit allen Zwischengrößen
> Quelle: § 2 EStG, § 32a EStG — [§ 2 EStG](https://www.gesetze-im-internet.de/estg/__2.html), [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html)
### Explizit ausgeschlossene Konstellationen
| In | Stelle | Begründung |
| --- | --- | --- |
| `EstGrundtarif` | Z. 218 | § 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve}) · Quelle: § 32a Absatz 1 EStG |
| `EstSplitting` | Z. 247 | § 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve}) · Quelle: § 32a Absatz 5 EStG |
## `est.test`
*`est.test.findsl`*
#### Akzeptanztests — Einkommensteuer [§ 2](https://www.gesetze-im-internet.de/estg/__2.html) + [§ 32a EStG](https://www.gesetze-im-internet.de/estg/__32a.html) (VZ 2026)
Sollwerte **von Hand aus dem Wortlaut** gerechnet (Quelle
`examples/est/estg.xml`, Fassung „ab Veranlagungszeitraum 2026").
§ 32a Satz 6: Steuerbetrag auf vollen Euro **abgerundet**.
Tarif-Größen: `y = (zvE − 12.348)/10.000`, `z = (zvE − 17.799)/10.000`.
Zonen: Nr. 2 `(914,51·y + 1.400)·y`; Nr. 3
`(173,10·z + 2.397)·z + 1.034,87`; Nr. 4 `0,42·x − 11.135,63`;
Nr. 5 `0,45·x − 19.470,38`. Splitting (Abs. 5) = 2·Grundtarif(⌊zvE/2⌋).
§ 32 Abs. 6: je Kind (3.414 + 1.464)·faktor·Monate/12·auslandsfaktor.
§ 33 Abs. 3 zumutbare Belastung **staffelweise** (Stufen 15.340 /
51.130; Sätze ohne Kind Grund 5/6/7 %, Splitting 4/5/6 %; 1–2 Kinder
2/3/4 %; ≥3 Kinder 1/1/2 %). § 10b: Spenden ≤ max(20 % GdE; 4 ‰
Umsätze+Löhne). Modellierungs-Entscheidung: Kategorie-Abzugssummen
auf volle Euro abgerundet (s. est.findsl Datei-Doc).
### Prüfungen
#### prüfe `§ 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)`
```findsl
prüfe "§ 32a Abs. 1 Nr. 1 EStG — Zone 1 (Grundfreibetrag)"
```
**Testfall — zvE = 0 → 0**
```findsl
EstGrundtarif(0) == 0
```
**Testfall — zvE = Grundfreibetrag 12.348 → 0 (bis-Grenze inklusiv)**
```findsl
EstGrundtarif(12.348) == 0
```
**Testfall — zvE = 12.349 (Zone-2-Beginn) → 0 (Steuer rundet auf 0 ab)**
```findsl
// y = 1/10000 = 0,0001 → (914,51·0,0001 + 1.400)·0,0001
// = 0,14000914… → abrunden 0
EstGrundtarif(12.349) == 0
```
#### prüfe `§ 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)`
```findsl
prüfe "§ 32a Abs. 1 Nr. 2 EStG — Zone 2 (Eingangsprogression)"
```
**Testfall — zvE = 15.000**
```findsl
// y = (15.000 − 12.348)/10.000 = 0,2652
// (914,51·0,2652 + 1.400)·0,2652 = 435,5984… → abrunden 435
EstGrundtarif(15.000) == 435
```
**Testfall — zvE = 17.799 (obere Grenze Zone 2)**
```findsl
// y = (17.799 − 12.348)/10.000 = 0,5451
// (914,51·0,5451 + 1.400)·0,5451 = 1.034,99… → abrunden 1.034
EstGrundtarif(17.799) == 1.034
```
#### prüfe `§ 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)`
```findsl
prüfe "§ 32a Abs. 1 Nr. 3 EStG — Zone 3 (Hauptprogression)"
```
**Testfall — zvE = 17.800 (Zone-3-Beginn)**
```findsl
// z = (17.800 − 17.799)/10.000 = 0,0001
// (173,10·0,0001 + 2.397)·0,0001 + 1.034,87 = 1.035,109… → 1.035
EstGrundtarif(17.800) == 1.035
```
**Testfall — zvE = 50.000**
```findsl
// z = (50.000 − 17.799)/10.000 = 3,2201
// (173,10·3,2201 + 2.397)·3,2201 + 1.034,87 = 10.548,… → 10.548
EstGrundtarif(50.000) == 10.548
```
**Testfall — zvE = 69.878 (obere Grenze Zone 3)**
```findsl
EstGrundtarif(69.878) == 18.213
```
#### prüfe `§ 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)`
```findsl
prüfe "§ 32a Abs. 1 Nr. 4 EStG — Zone 4 (Proportionalzone, 42 %)"
```
**Testfall — zvE = 69.879 (Zone-4-Beginn, stetiger Anschluss)**
```findsl
// 0,42·69.879 − 11.135,63 = 18.213,55 → abrunden 18.213
EstGrundtarif(69.879) == 18.213
```
**Testfall — zvE = 100.000**
```findsl
// 0,42·100.000 − 11.135,63 = 30.864,37 → abrunden 30.864
EstGrundtarif(100.000) == 30.864
```
**Testfall — zvE = 277.825 (obere Grenze Zone 4)**
```findsl
// 0,42·277.825 − 11.135,63 = 105.550,87 → abrunden 105.550
EstGrundtarif(277.825) == 105.550
```
#### prüfe `§ 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)`
```findsl
prüfe "§ 32a Abs. 1 Nr. 5 EStG — Zone 5 (Proportionalzone, 45 %)"
```
**Testfall — zvE = 277.826 (Zone-5-Beginn)**
```findsl
// 0,45·277.826 − 19.470,38 = 105.551,32 → abrunden 105.551
EstGrundtarif(277.826) == 105.551
```
**Testfall — zvE = 300.000**
```findsl
// 0,45·300.000 − 19.470,38 = 115.529,62 → abrunden 115.529
EstGrundtarif(300.000) == 115.529
```
#### prüfe `§ 32a Abs. 5 EStG — Splitting-Verfahren`
```findsl
prüfe "§ 32a Abs. 5 EStG — Splitting-Verfahren"
```
**Testfall — zvE = 200.000 → 2 · Grundtarif(100.000) = 2 · 30.864**
```findsl
EstSplitting(200.000) == 61.728
```
**Testfall — zvE = 100.001 → Hälfte 50.000 (abgerundet) → 2 · 10.548**
```findsl
EstSplitting(100.001) == 21.096
```
**Testfall — zvE = 150.000 → Hälfte 75.000 → 2 · Grundtarif(75.000)**
```findsl
// 0,42·75.000 − 11.135,63 = 20.364,37 → 20.364 ; 2·20.364
EstSplitting(150.000) == 40.728
```
#### prüfe `§ 32a EStG — unzulässige Eingaben (abbruch)`
```findsl
prüfe "§ 32a EStG — unzulässige Eingaben (abbruch)"
```
**Testfall — negatives zvE (Grundtarif) ist nicht definiert** _(erwartet abbruch)_
```findsl
var n: Euro = -1
EstGrundtarif(n)
```
**Testfall — negatives gemeinsames zvE (Splitting) ist nicht definiert** _(erwartet abbruch)_
```findsl
var n: Euro = -2
EstSplitting(n)
```
#### prüfe `§ 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)`
```findsl
prüfe "§ 2 EStG — Kaskade mit § 32 Abs. 6 / § 33 / § 10b (Listen)"
```
**Testfall — Fall K — Single, 2 Kinder, agB- + Spenden-Posten**
```findsl
// GdE 60.000. zumutbare Belastung (2 Kinder, Stufen 2/3/4 %):
// 2%·15.340 + 3%·(51.130−15.340) + 4%·(60.000−51.130)
// = 306,80 + 1.073,70 + 354,80 = 1.735,30
// agB abziehbar = nichtNeg(5.000 − 1.735,30).abrunden() = 3.264
// Spenden abziehbar = min(2.000; 20%·60.000=12.000) = 2.000
// SA = 4.000 + 2.000 = 6.000
// KFB = ((3.414+1.464)·1·12/12·100% ·2 Kinder).abrunden() = 9.756
// Einkommen = 60.000 − 6.000 − 3.264 = 50.736
// zvE = 50.736 − 9.756 = 40.980 → Grundtarif = 7.521
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 60.000,
sonstigeSonderausgaben = 4.000,
spenden = [2.000],
aussergewoehnlicheAufwendungen = [5.000],
kinder = [Kind(), Kind()],
))
e.gesamtbetragDerEinkuenfte == 60.000
und e.kinderfreibetraege == 9.756
und e.abziehbareAussergewoehnlicheBelastungen == 3.264
und e.einkommen == 50.736
und e.zuVersteuerndesEinkommen == 40.980
und e.tariflicheEinkommensteuer == 7.521
und e.festzusetzendeEinkommensteuer == 7.521
```
**Testfall — Fall S — Splitting, 3 Kinder (eines halbjährig), Spenden gekappt**
```findsl
// SdE = 100.000 → GdE 100.000. zumutbar (3 Kinder, 1/1/2 %):
// 1%·15.340 + 1%·35.790 + 2%·48.870 = 153,40+357,90+977,40 = 1.488,70
// agB abziehbar = (8.000 − 1.488,70).abrunden() = 6.511
// Spenden abziehbar = min(30.000; max(20%·100.000=20.000; 0)) = 20.000
// KFB Splitting faktor 2: 2·4.878·2 + 4.878·2·6/12 = 19.512 + 4.878 = 24.390
// Einkommen = 100.000 − 20.000 − 6.511 = 73.489
// zvE = 73.489 − 24.390 = 49.099 → Splitting=2·Grundtarif(24.549)=5.462
// festzusetzend = 5.462 − 2.500 + 600 = 3.562
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 100.000,
spenden = [10.000, 20.000],
aussergewoehnlicheAufwendungen = [3.000, 5.000],
kinder = [
Kind(faktor = 2),
Kind(faktor = 2),
Kind(faktor = 2, berücksichtigteMonate = 6),
],
tarifart = Splitting,
anrechnungenUndErmaessigungen = 2.500,
hinzurechnungen = 600,
))
e.kinderfreibetraege == 24.390
und e.abziehbareAussergewoehnlicheBelastungen == 6.511
und e.einkommen == 73.489
und e.zuVersteuerndesEinkommen == 49.099
und e.tariflicheEinkommensteuer == 5.462
und e.festzusetzendeEinkommensteuer == 3.562
```
**Testfall — Fall L — agB unter zumutbarer Belastung → 0 abziehbar**
```findsl
// GdE 40.000, 0 Kinder, Grundtarif: zumutbar
// 5%·15.340 + 6%·(40.000−15.340) = 767 + 1.479,60 = 2.246,60
// 1.000 < 2.246,60 → abziehbare agB = 0
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 40.000,
aussergewoehnlicheAufwendungen = [1.000],
))
e.abziehbareAussergewoehnlicheBelastungen == 0
und e.einkommen == 40.000
und e.zuVersteuerndesEinkommen == 40.000
und e.tariflicheEinkommensteuer == 7.209
```
**Testfall — Fall 0 — leere Listen ≙ alte Skalar-0-Kaskade (Regressionsanker)**
```findsl
var e: EinkommensteuerErgebnis = BerechneEinkommensteuer(EinkommensteuerFall(
einkuenfteNichtselbstaendigeArbeit = 50.000,
))
e.kinderfreibetraege == 0
und e.abziehbareAussergewoehnlicheBelastungen == 0
und e.einkommen == 50.000
und e.zuVersteuerndesEinkommen == 50.000
und e.tariflicheEinkommensteuer == 10.548
```Programmablaufpläne — est
EstGrundtarif
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
EstGrundtarif_n0("EstGrundtarif<br/><br/>⟨§ 32a Absatz 1 EStG⟩")
EstGrundtarif_n1[/"zve: Euro"/]
EstGrundtarif_n2{"zve #lt; 0 als Euro"}
EstGrundtarif_n3("abbruch<br/>§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht n…")
EstGrundtarif_n4{"zve #lt; GFB +<br/>1"}
EstGrundtarif_n5["0"]
EstGrundtarif_n6{"zve #lt; ZONE_2_OBERGRENZE +<br/>1"}
EstGrundtarif_n7["y ← (zve -<br/>GFB) /<br/>ZEHNTAUSEND"]
EstGrundtarif_n8["roh ← (ZONE_2_PROGRESSION *<br/>y +<br/>ZONE_2_LINEAR) *<br/>y"]
EstGrundtarif_n9["roh.abrunden() als Euro"]
EstGrundtarif_n10{"zve #lt; ZONE_3_OBERGRENZE +<br/>1"}
EstGrundtarif_n11["z ← (zve -<br/>ZONE_2_OBERGRENZE) /<br/>ZEHNTAUSEND"]
EstGrundtarif_n12["roh ← (ZONE_3_PROGRESSION *<br/>z +<br/>ZONE_3_LINEAR) *<br/>z +<br/>ZONE_3_KONSTANTE"]
EstGrundtarif_n13["roh.abrunden() als Euro"]
EstGrundtarif_n14{"zve #lt; ZONE_4_OBERGRENZE +<br/>1"}
EstGrundtarif_n15["(ZONE_4_SATZ *<br/>zve -<br/>ZONE_4_ABZUG).abrunden()"]
EstGrundtarif_n16["(ZONE_5_SATZ *<br/>zve -<br/>ZONE_5_ABZUG).abrunden()"]
EstGrundtarif_n17("Ergebnis: Euro")
EstGrundtarif_n1 --> EstGrundtarif_n0
EstGrundtarif_n2 -->|"ja"| EstGrundtarif_n3
EstGrundtarif_n2 -->|"nein"| EstGrundtarif_n4
EstGrundtarif_n4 -->|"ja"| EstGrundtarif_n5
EstGrundtarif_n4 -->|"nein"| EstGrundtarif_n6
EstGrundtarif_n7 --> EstGrundtarif_n8
EstGrundtarif_n8 --> EstGrundtarif_n9
EstGrundtarif_n6 -->|"ja"| EstGrundtarif_n7
EstGrundtarif_n6 -->|"nein"| EstGrundtarif_n10
EstGrundtarif_n11 --> EstGrundtarif_n12
EstGrundtarif_n12 --> EstGrundtarif_n13
EstGrundtarif_n10 -->|"ja"| EstGrundtarif_n11
EstGrundtarif_n10 -->|"nein"| EstGrundtarif_n14
EstGrundtarif_n14 -->|"ja"| EstGrundtarif_n15
EstGrundtarif_n14 -->|"nein"| EstGrundtarif_n16
EstGrundtarif_n0 --> EstGrundtarif_n2
EstGrundtarif_n5 --> EstGrundtarif_n17
EstGrundtarif_n9 --> EstGrundtarif_n17
EstGrundtarif_n13 --> EstGrundtarif_n17
EstGrundtarif_n15 --> EstGrundtarif_n17
EstGrundtarif_n16 --> EstGrundtarif_n17
click EstGrundtarif_n0 href "https://www.gesetze-im-internet.de/estg/__32a.html" "Tariflicher Einkommensteuerbetrag nach dem Grundtarif (§ 32a Absatz 1 EStG). Das zu versteuernde Einkommen ist nach Satz 1 auf volle Euro abgerundet zu verstehen (durch den `Euro`-Typ bereits ganzzahlig). Der sich ergebende Steuerbetrag wird nach Satz 6 auf den nächsten vollen Euro abgerundet. Mit den Hilfsgrößen y = (zvE - GFB)/10000 (Zone 2) und z = (zvE - ZONE_2)/10000 (Zone 3) lautet der Tarif zonenweise: ESt(zvE) = 0 wenn zvE <= GFB (a_2y + b_2)y wenn Zone 2 (a_3z + b_3)z + c_3 wenn Zone 3 0,42 · zvE - C_4 wenn Zone 4 0,45 · zvE - C_5 wenn Zone 5" _blank
click EstGrundtarif_n3 href "https://www.gesetze-im-internet.de/estg/__32a.html" "§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve})" _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class EstGrundtarif_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class EstGrundtarif_n1 eingabe
classDef decision fill:#fdf6e0,stroke:#ecd79b,stroke-width:1px,color:#3c4043
class EstGrundtarif_n2,EstGrundtarif_n4,EstGrundtarif_n6,EstGrundtarif_n10,EstGrundtarif_n14 decision
classDef abbruch fill:#fdecea,stroke:#f1b0a8,stroke-width:1px,color:#3c4043
class EstGrundtarif_n3 abbruch
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class EstGrundtarif_n5,EstGrundtarif_n7,EstGrundtarif_n8,EstGrundtarif_n9,EstGrundtarif_n11,EstGrundtarif_n12,EstGrundtarif_n13,EstGrundtarif_n15,EstGrundtarif_n16 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class EstGrundtarif_n17 ende
EstSplitting
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
EstSplitting_n0("EstSplitting<br/><br/>⟨§ 32a Absatz 5 EStG⟩")
EstSplitting_n1[/"zve: Euro"/]
EstSplitting_n2{"zve #lt; 0 als Euro"}
EstSplitting_n3("abbruch<br/>§ 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen da…")
EstSplitting_n4["halbesZve ← (zve /<br/>2).abrunden() als Euro"]
EstSplitting_n5["2 *<br/>EstGrundtarif(…)"]
EstSplitting_n6("Ergebnis: Euro")
EstSplitting_n1 --> EstSplitting_n0
EstSplitting_n2 -->|"ja"| EstSplitting_n3
EstSplitting_n4 --> EstSplitting_n5
EstSplitting_n2 -->|"nein"| EstSplitting_n4
EstSplitting_n0 --> EstSplitting_n2
EstSplitting_n5 --> EstSplitting_n6
click EstSplitting_n0 href "https://www.gesetze-im-internet.de/estg/__32a.html" "Tariflicher Einkommensteuerbetrag nach dem Splitting-Verfahren für zusammen veranlagte Ehegatten (§ 32a Absatz 5 EStG): das Zweifache des Steuerbetrags, der sich für die Hälfte des gemeinsam zu versteuernden Einkommens nach Absatz 1 ergibt. Die Hälfte wird nach Absatz 1 Satz 1 auf volle Euro abgerundet." _blank
click EstSplitting_n3 href "https://www.gesetze-im-internet.de/estg/__32a.html" "§ 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve})" _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class EstSplitting_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class EstSplitting_n1 eingabe
classDef decision fill:#fdf6e0,stroke:#ecd79b,stroke-width:1px,color:#3c4043
class EstSplitting_n2 decision
classDef abbruch fill:#fdecea,stroke:#f1b0a8,stroke-width:1px,color:#3c4043
class EstSplitting_n3 abbruch
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class EstSplitting_n4,EstSplitting_n5 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class EstSplitting_n6 ende
_Spanne
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
_Spanne_n0("_Spanne")
_Spanne_n1[/"betrag: Euro"/]
_Spanne_n2[/"von: Euro"/]
_Spanne_n3[/"obereGrenze: Euro"/]
_Spanne_n4["(betrag.höchstens(…) -<br/>von).mindestens(…)"]
_Spanne_n5("Ergebnis: Euro")
_Spanne_n1 --> _Spanne_n0
_Spanne_n2 --> _Spanne_n0
_Spanne_n3 --> _Spanne_n0
_Spanne_n0 --> _Spanne_n4
_Spanne_n4 --> _Spanne_n5
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class _Spanne_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class _Spanne_n1,_Spanne_n2,_Spanne_n3 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class _Spanne_n4 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class _Spanne_n5 ende
SummeDerEinkuenfte
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
SummeDerEinkuenfte_n0("SummeDerEinkuenfte<br/><br/>⟨§ 2 Absatz 1 und 2 EStG⟩")
SummeDerEinkuenfte_n1[/"fall: EinkommensteuerFall"/]
SummeDerEinkuenfte_n2["fall.einkuenfteLandUndForstwirtschaft +<br/>fall.einkuenfteGewerbebetrieb +<br/>fall.einkuenfteSelbstaendigeArbeit +<br/>fall.einkuenfteNichtselbstaendigeArbeit +<br/>fall.einkuenfteKapitalvermoegen +<br/>fall.einkuenfteVermietungVerpachtung +<br/>fall.sonstigeEinkuenfte"]
SummeDerEinkuenfte_n3("Ergebnis: Euro")
SummeDerEinkuenfte_n1 --> SummeDerEinkuenfte_n0
SummeDerEinkuenfte_n0 --> SummeDerEinkuenfte_n2
SummeDerEinkuenfte_n2 --> SummeDerEinkuenfte_n3
click SummeDerEinkuenfte_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Summe der Einkünfte (§ 2 Absatz 1 und 2 EStG): Summe der sieben Einkunftsarten. Negative Einkünfte einzelner Arten mindern die Summe (einkunftsartübergreifende Verlustverrechnungsbeschränkungen sind anderes Recht und in den Eingaben bereits berücksichtigt)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class SummeDerEinkuenfte_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class SummeDerEinkuenfte_n1 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class SummeDerEinkuenfte_n2 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class SummeDerEinkuenfte_n3 ende
GesamtbetragDerEinkuenfte
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
GesamtbetragDerEinkuenfte_n0("GesamtbetragDerEinkuenfte<br/><br/>⟨§ 2 Absatz 3 EStG⟩")
GesamtbetragDerEinkuenfte_n1[/"summe: Euro"/]
GesamtbetragDerEinkuenfte_n2[/"fall: EinkommensteuerFall"/]
GesamtbetragDerEinkuenfte_n3["summe -<br/>fall.altersentlastungsbetrag -<br/>fall.entlastungsbetragAlleinerziehende -<br/>fall.freibetragLandUndForstwirtschaft"]
GesamtbetragDerEinkuenfte_n4("Ergebnis: Euro")
GesamtbetragDerEinkuenfte_n1 --> GesamtbetragDerEinkuenfte_n0
GesamtbetragDerEinkuenfte_n2 --> GesamtbetragDerEinkuenfte_n0
GesamtbetragDerEinkuenfte_n0 --> GesamtbetragDerEinkuenfte_n3
GesamtbetragDerEinkuenfte_n3 --> GesamtbetragDerEinkuenfte_n4
click GesamtbetragDerEinkuenfte_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Gesamtbetrag der Einkünfte (§ 2 Absatz 3 EStG): Summe der Einkünfte vermindert um Altersentlastungsbetrag (§ 24a), Entlastungsbetrag für Alleinerziehende (§ 24b) und Abzug nach § 13 Absatz 3." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class GesamtbetragDerEinkuenfte_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class GesamtbetragDerEinkuenfte_n1,GesamtbetragDerEinkuenfte_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class GesamtbetragDerEinkuenfte_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class GesamtbetragDerEinkuenfte_n4 ende
KinderfreibetragGesamt
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
KinderfreibetragGesamt_n0("KinderfreibetragGesamt<br/><br/>⟨§ 32 Absatz 6 EStG⟩")
KinderfreibetragGesamt_n1[/"kinder: Liste#lt;Kind#gt;"/]
KinderfreibetragGesamt_n2["(<br/>kinder.zuordnen(…).summe()<br/>).abrunden()"]
KinderfreibetragGesamt_n3("Ergebnis: Euro")
KinderfreibetragGesamt_n1 --> KinderfreibetragGesamt_n0
KinderfreibetragGesamt_n0 --> KinderfreibetragGesamt_n2
KinderfreibetragGesamt_n2 --> KinderfreibetragGesamt_n3
click KinderfreibetragGesamt_n0 href "https://www.gesetze-im-internet.de/estg/__32.html" "Kinderfreibetrag + BEA-Freibetrag, aggregiert über alle Kinder (§ 32 Absatz 6 EStG): je Kind `(3.414 + 1.464) · faktor · berücksichtigteMonate/12 · auslandsfaktor`; die Summe wird auf volle Euro abgerundet (Modellierungs-Entscheidung, s. Datei-Doc)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class KinderfreibetragGesamt_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class KinderfreibetragGesamt_n1 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class KinderfreibetragGesamt_n2 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class KinderfreibetragGesamt_n3 ende
ZumutbareBelastung
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
ZumutbareBelastung_n0("ZumutbareBelastung<br/><br/>⟨§ 33 Absatz 3 EStG⟩")
ZumutbareBelastung_n1[/"gde: Euro"/]
ZumutbareBelastung_n2[/"kinderzahl: Ganzzahl"/]
ZumutbareBelastung_n3[/"tarifart: Tarifart"/]
ZumutbareBelastung_n4["_ZmbSatz(…) *<br/>_Spanne(…) +<br/>_ZmbSatz(…) *<br/>_Spanne(…) +<br/>_ZmbSatz(…) *<br/>(gde -<br/>ZMB_STUFE_2).mindestens(…)"]
ZumutbareBelastung_n5("Ergebnis: EuroCent")
ZumutbareBelastung_n1 --> ZumutbareBelastung_n0
ZumutbareBelastung_n2 --> ZumutbareBelastung_n0
ZumutbareBelastung_n3 --> ZumutbareBelastung_n0
ZumutbareBelastung_n0 --> ZumutbareBelastung_n4
ZumutbareBelastung_n4 --> ZumutbareBelastung_n5
click ZumutbareBelastung_n0 href "https://www.gesetze-im-internet.de/estg/__33.html" "Zumutbare Belastung (§ 33 Absatz 3 EStG) — **staffelweise** über die drei GdE-Stufen (bis 15.340 / bis 51.130 / darüber), mit den Prozentsätzen der vier Personengruppen (keine Kinder Grund/Splitting, 1–2 Kinder, ≥ 3 Kinder). „Kinder' sind die mit Freibetrag § 32 Abs. 6 oder Kindergeld-Anspruch (§ 33 Abs. 3 Satz 2 — hier `kinderzahl`)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class ZumutbareBelastung_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class ZumutbareBelastung_n1,ZumutbareBelastung_n2,ZumutbareBelastung_n3 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class ZumutbareBelastung_n4 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class ZumutbareBelastung_n5 ende
_ZmbSatz
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
_ZmbSatz_n0("_ZmbSatz<br/><br/>⟨§ 33 Absatz 3 Satz 1 EStG⟩")
_ZmbSatz_n1[/"stufe: Ganzzahl"/]
_ZmbSatz_n2[/"kinderzahl: Ganzzahl"/]
_ZmbSatz_n3[/"tarifart: Tarifart"/]
_ZmbSatz_n4{"kinderzahl #lt; 1"}
_ZmbSatz_n5{{"wähle tarifart"}}
_ZmbSatz_n6{"stufe #lt; 2"}
_ZmbSatz_n7["ZMB_OHNE_KIND_GRUND_1"]
_ZmbSatz_n8{"stufe #lt; 3"}
_ZmbSatz_n9["ZMB_OHNE_KIND_GRUND_2"]
_ZmbSatz_n10["ZMB_OHNE_KIND_GRUND_3"]
_ZmbSatz_n11{"stufe #lt; 2"}
_ZmbSatz_n12["ZMB_OHNE_KIND_SPLIT_1"]
_ZmbSatz_n13{"stufe #lt; 3"}
_ZmbSatz_n14["ZMB_OHNE_KIND_SPLIT_2"]
_ZmbSatz_n15["ZMB_OHNE_KIND_SPLIT_3"]
_ZmbSatz_n16{"kinderzahl #lt; 3"}
_ZmbSatz_n17{"stufe #lt; 2"}
_ZmbSatz_n18["ZMB_1_2_KINDER_1"]
_ZmbSatz_n19{"stufe #lt; 3"}
_ZmbSatz_n20["ZMB_1_2_KINDER_2"]
_ZmbSatz_n21["ZMB_1_2_KINDER_3"]
_ZmbSatz_n22{"stufe #lt; 2"}
_ZmbSatz_n23["ZMB_AB_3_KINDER_1"]
_ZmbSatz_n24{"stufe #lt; 3"}
_ZmbSatz_n25["ZMB_AB_3_KINDER_2"]
_ZmbSatz_n26["ZMB_AB_3_KINDER_3"]
_ZmbSatz_n27("Ergebnis: Prozent")
_ZmbSatz_n1 --> _ZmbSatz_n0
_ZmbSatz_n2 --> _ZmbSatz_n0
_ZmbSatz_n3 --> _ZmbSatz_n0
_ZmbSatz_n6 -->|"ja"| _ZmbSatz_n7
_ZmbSatz_n6 -->|"nein"| _ZmbSatz_n8
_ZmbSatz_n8 -->|"ja"| _ZmbSatz_n9
_ZmbSatz_n8 -->|"nein"| _ZmbSatz_n10
_ZmbSatz_n5 -->|"Grundtarif"| _ZmbSatz_n6
_ZmbSatz_n11 -->|"ja"| _ZmbSatz_n12
_ZmbSatz_n11 -->|"nein"| _ZmbSatz_n13
_ZmbSatz_n13 -->|"ja"| _ZmbSatz_n14
_ZmbSatz_n13 -->|"nein"| _ZmbSatz_n15
_ZmbSatz_n5 -->|"Splitting"| _ZmbSatz_n11
_ZmbSatz_n4 -->|"ja"| _ZmbSatz_n5
_ZmbSatz_n4 -->|"nein"| _ZmbSatz_n16
_ZmbSatz_n17 -->|"ja"| _ZmbSatz_n18
_ZmbSatz_n17 -->|"nein"| _ZmbSatz_n19
_ZmbSatz_n19 -->|"ja"| _ZmbSatz_n20
_ZmbSatz_n19 -->|"nein"| _ZmbSatz_n21
_ZmbSatz_n16 -->|"ja"| _ZmbSatz_n17
_ZmbSatz_n22 -->|"ja"| _ZmbSatz_n23
_ZmbSatz_n22 -->|"nein"| _ZmbSatz_n24
_ZmbSatz_n24 -->|"ja"| _ZmbSatz_n25
_ZmbSatz_n24 -->|"nein"| _ZmbSatz_n26
_ZmbSatz_n16 -->|"nein"| _ZmbSatz_n22
_ZmbSatz_n0 --> _ZmbSatz_n4
_ZmbSatz_n7 --> _ZmbSatz_n27
_ZmbSatz_n9 --> _ZmbSatz_n27
_ZmbSatz_n10 --> _ZmbSatz_n27
_ZmbSatz_n12 --> _ZmbSatz_n27
_ZmbSatz_n14 --> _ZmbSatz_n27
_ZmbSatz_n15 --> _ZmbSatz_n27
_ZmbSatz_n18 --> _ZmbSatz_n27
_ZmbSatz_n20 --> _ZmbSatz_n27
_ZmbSatz_n21 --> _ZmbSatz_n27
_ZmbSatz_n23 --> _ZmbSatz_n27
_ZmbSatz_n25 --> _ZmbSatz_n27
_ZmbSatz_n26 --> _ZmbSatz_n27
click _ZmbSatz_n0 href "https://www.gesetze-im-internet.de/estg/__33.html" "Prozentsatz der zumutbaren Belastung für GdE-Stufe (1/2/3)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class _ZmbSatz_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class _ZmbSatz_n1,_ZmbSatz_n2,_ZmbSatz_n3 eingabe
classDef decision fill:#fdf6e0,stroke:#ecd79b,stroke-width:1px,color:#3c4043
class _ZmbSatz_n4,_ZmbSatz_n6,_ZmbSatz_n8,_ZmbSatz_n11,_ZmbSatz_n13,_ZmbSatz_n16,_ZmbSatz_n17,_ZmbSatz_n19,_ZmbSatz_n22,_ZmbSatz_n24 decision
classDef case fill:#fcf0e2,stroke:#f0c79a,stroke-width:1px,color:#3c4043
class _ZmbSatz_n5 case
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class _ZmbSatz_n7,_ZmbSatz_n9,_ZmbSatz_n10,_ZmbSatz_n12,_ZmbSatz_n14,_ZmbSatz_n15,_ZmbSatz_n18,_ZmbSatz_n20,_ZmbSatz_n21,_ZmbSatz_n23,_ZmbSatz_n25,_ZmbSatz_n26 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class _ZmbSatz_n27 ende
AbziehbareAussergewoehnlicheBelastungen
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
AbziehbareAussergewoehnlicheBelastungen_n0("AbziehbareAussergewoehnlicheBelastungen<br/><br/>⟨§ 33 Absatz 1 EStG⟩")
AbziehbareAussergewoehnlicheBelastungen_n1[/"fall: EinkommensteuerFall"/]
AbziehbareAussergewoehnlicheBelastungen_n2[/"gde: Euro"/]
AbziehbareAussergewoehnlicheBelastungen_n3["(<br/>(fall.aussergewoehnlicheAufwendungen.summe() als EuroCent) -<br/>ZumutbareBelastung(…)<br/>).mindestens(…).abrunden()"]
AbziehbareAussergewoehnlicheBelastungen_n4("Ergebnis: Euro")
AbziehbareAussergewoehnlicheBelastungen_n1 --> AbziehbareAussergewoehnlicheBelastungen_n0
AbziehbareAussergewoehnlicheBelastungen_n2 --> AbziehbareAussergewoehnlicheBelastungen_n0
AbziehbareAussergewoehnlicheBelastungen_n0 --> AbziehbareAussergewoehnlicheBelastungen_n3
AbziehbareAussergewoehnlicheBelastungen_n3 --> AbziehbareAussergewoehnlicheBelastungen_n4
click AbziehbareAussergewoehnlicheBelastungen_n0 href "https://www.gesetze-im-internet.de/estg/__33.html" "Abziehbare außergewöhnliche Belastungen (§ 33 Absatz 1 EStG): Summe der zwangsläufigen Aufwendungen, soweit sie die zumutbare Belastung (§ 33 Abs. 3) übersteigt; nie negativ, auf volle Euro abgerundet." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class AbziehbareAussergewoehnlicheBelastungen_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class AbziehbareAussergewoehnlicheBelastungen_n1,AbziehbareAussergewoehnlicheBelastungen_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class AbziehbareAussergewoehnlicheBelastungen_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class AbziehbareAussergewoehnlicheBelastungen_n4 ende
AbziehbareSpenden
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
AbziehbareSpenden_n0("AbziehbareSpenden<br/><br/>⟨§ 10b Absatz 1 EStG⟩")
AbziehbareSpenden_n1[/"fall: EinkommensteuerFall"/]
AbziehbareSpenden_n2[/"gde: Euro"/]
AbziehbareSpenden_n3["grenzeGde ← (SPENDEN_HB_GDE *<br/>gde).abrunden()"]
AbziehbareSpenden_n4["grenzeUmsatz ← (SPENDEN_HB_UMSATZ *<br/>fall.umsaetzeUndLoehne).abrunden()"]
AbziehbareSpenden_n5[["hoechstbetrag ← grenzeGde.mindestens(…)"]]
AbziehbareSpenden_n6[["fall.spenden.summe().höchstens(…)"]]
AbziehbareSpenden_n7("Ergebnis: Euro")
AbziehbareSpenden_n1 --> AbziehbareSpenden_n0
AbziehbareSpenden_n2 --> AbziehbareSpenden_n0
AbziehbareSpenden_n3 --> AbziehbareSpenden_n4
AbziehbareSpenden_n4 --> AbziehbareSpenden_n5
AbziehbareSpenden_n5 --> AbziehbareSpenden_n6
AbziehbareSpenden_n0 --> AbziehbareSpenden_n3
AbziehbareSpenden_n6 --> AbziehbareSpenden_n7
click AbziehbareSpenden_n0 href "https://www.gesetze-im-internet.de/estg/__10b.html" "Abziehbare Spenden (§ 10b Absatz 1 EStG): Summe der Zuwendungen, gedeckelt auf den Höchstbetrag = größerer Wert aus 20 % des Gesamtbetrags der Einkünfte und 4 ‰ der Umsätze + Löhne; auf volle Euro abgerundet." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n1,AbziehbareSpenden_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n3,AbziehbareSpenden_n4 operation
classDef subprogram fill:#eeeffb,stroke:#c3c6ef,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n5,AbziehbareSpenden_n6 subprogram
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n7 ende
Einkommen
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
Einkommen_n0("Einkommen<br/><br/>⟨§ 2 Absatz 4 EStG⟩")
Einkommen_n1[/"gesamtbetrag: Euro"/]
Einkommen_n2[/"fall: EinkommensteuerFall"/]
Einkommen_n3["gesamtbetrag -<br/>fall.sonstigeSonderausgaben -<br/>AbziehbareSpenden(…) -<br/>AbziehbareAussergewoehnlicheBelastungen(…)"]
Einkommen_n4("Ergebnis: Euro")
Einkommen_n1 --> Einkommen_n0
Einkommen_n2 --> Einkommen_n0
Einkommen_n0 --> Einkommen_n3
Einkommen_n3 --> Einkommen_n4
click Einkommen_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Einkommen (§ 2 Absatz 4 EStG): Gesamtbetrag der Einkünfte vermindert um die Sonderausgaben (sonstige + abziehbare Spenden § 10b) und die abziehbaren außergewöhnlichen Belastungen (§ 33)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class Einkommen_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class Einkommen_n1,Einkommen_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class Einkommen_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class Einkommen_n4 ende
ZuVersteuerndesEinkommen
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
ZuVersteuerndesEinkommen_n0("ZuVersteuerndesEinkommen<br/><br/>⟨§ 2 Absatz 5 Satz 1 EStG⟩")
ZuVersteuerndesEinkommen_n1[/"einkommen: Euro"/]
ZuVersteuerndesEinkommen_n2[/"fall: EinkommensteuerFall"/]
ZuVersteuerndesEinkommen_n3["einkommen -<br/>KinderfreibetragGesamt(…) -<br/>fall.sonstigeAbzuegeVomEinkommen"]
ZuVersteuerndesEinkommen_n4("Ergebnis: Euro")
ZuVersteuerndesEinkommen_n1 --> ZuVersteuerndesEinkommen_n0
ZuVersteuerndesEinkommen_n2 --> ZuVersteuerndesEinkommen_n0
ZuVersteuerndesEinkommen_n0 --> ZuVersteuerndesEinkommen_n3
ZuVersteuerndesEinkommen_n3 --> ZuVersteuerndesEinkommen_n4
click ZuVersteuerndesEinkommen_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Zu versteuerndes Einkommen (§ 2 Absatz 5 Satz 1 EStG): Einkommen vermindert um die Freibeträge nach § 32 Absatz 6 (Kinder) und die sonstigen vom Einkommen abzuziehenden Beträge." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class ZuVersteuerndesEinkommen_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class ZuVersteuerndesEinkommen_n1,ZuVersteuerndesEinkommen_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class ZuVersteuerndesEinkommen_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class ZuVersteuerndesEinkommen_n4 ende
TariflicheEinkommensteuer
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
TariflicheEinkommensteuer_n0("TariflicheEinkommensteuer<br/><br/>⟨§ 32a Absatz 1 und 5 EStG⟩")
TariflicheEinkommensteuer_n1[/"zve: Euro"/]
TariflicheEinkommensteuer_n2[/"tarifart: Tarifart"/]
TariflicheEinkommensteuer_n3{{"wähle tarifart"}}
TariflicheEinkommensteuer_n4[["EstGrundtarif(…)"]]
TariflicheEinkommensteuer_n5[["EstSplitting(…)"]]
TariflicheEinkommensteuer_n6("Ergebnis: Euro")
TariflicheEinkommensteuer_n1 --> TariflicheEinkommensteuer_n0
TariflicheEinkommensteuer_n2 --> TariflicheEinkommensteuer_n0
TariflicheEinkommensteuer_n3 -->|"Grundtarif"| TariflicheEinkommensteuer_n4
TariflicheEinkommensteuer_n3 -->|"Splitting"| TariflicheEinkommensteuer_n5
TariflicheEinkommensteuer_n0 --> TariflicheEinkommensteuer_n3
TariflicheEinkommensteuer_n4 --> TariflicheEinkommensteuer_n6
TariflicheEinkommensteuer_n5 --> TariflicheEinkommensteuer_n6
click TariflicheEinkommensteuer_n0 href "https://www.gesetze-im-internet.de/estg/__32a.html" "Tarifliche Einkommensteuer (§ 32a EStG): Grund- oder Splittingtarif. Negatives zvE → 0 (§ 32a für negatives zvE nicht definiert; § 10d Verlustabzug ist Verfahren, nicht modelliert)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n1,TariflicheEinkommensteuer_n2 eingabe
classDef case fill:#fcf0e2,stroke:#f0c79a,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n3 case
classDef subprogram fill:#eeeffb,stroke:#c3c6ef,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n4,TariflicheEinkommensteuer_n5 subprogram
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n6 ende
FestzusetzendeEinkommensteuer
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
FestzusetzendeEinkommensteuer_n0("FestzusetzendeEinkommensteuer<br/><br/>⟨§ 2 Absatz 6 EStG⟩")
FestzusetzendeEinkommensteuer_n1[/"tariflich: Euro"/]
FestzusetzendeEinkommensteuer_n2[/"fall: EinkommensteuerFall"/]
FestzusetzendeEinkommensteuer_n3["tariflich -<br/>fall.anrechnungenUndErmaessigungen +<br/>fall.hinzurechnungen"]
FestzusetzendeEinkommensteuer_n4("Ergebnis: Euro")
FestzusetzendeEinkommensteuer_n1 --> FestzusetzendeEinkommensteuer_n0
FestzusetzendeEinkommensteuer_n2 --> FestzusetzendeEinkommensteuer_n0
FestzusetzendeEinkommensteuer_n0 --> FestzusetzendeEinkommensteuer_n3
FestzusetzendeEinkommensteuer_n3 --> FestzusetzendeEinkommensteuer_n4
click FestzusetzendeEinkommensteuer_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Festzusetzende Einkommensteuer (§ 2 Absatz 6 EStG): tarifliche Steuer vermindert um Anrechnungen/Steuerermäßigungen, vermehrt um Hinzurechnungen (Komponenten + Kappungen = anderes Recht/Eingabe; keine Untergrenze — der Wortlaut sieht keine vor)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class FestzusetzendeEinkommensteuer_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class FestzusetzendeEinkommensteuer_n1,FestzusetzendeEinkommensteuer_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class FestzusetzendeEinkommensteuer_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class FestzusetzendeEinkommensteuer_n4 ende
BerechneEinkommensteuer
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
BerechneEinkommensteuer_n0("BerechneEinkommensteuer<br/><br/>⟨§ 2 EStG, § 32a EStG⟩")
BerechneEinkommensteuer_n1[/"fall: EinkommensteuerFall"/]
BerechneEinkommensteuer_n2[["sde ← SummeDerEinkuenfte(…)"]]
BerechneEinkommensteuer_n3[["gde ← GesamtbetragDerEinkuenfte(…)"]]
BerechneEinkommensteuer_n4[["kfb ← KinderfreibetragGesamt(…)"]]
BerechneEinkommensteuer_n5[["agb ← AbziehbareAussergewoehnlicheBelastungen(…)"]]
BerechneEinkommensteuer_n6[["ein ← Einkommen(…)"]]
BerechneEinkommensteuer_n7[["zve ← ZuVersteuerndesEinkommen(…)"]]
BerechneEinkommensteuer_n8[["tariflich ← TariflicheEinkommensteuer(…)"]]
BerechneEinkommensteuer_n9[["fest ← FestzusetzendeEinkommensteuer(…)"]]
BerechneEinkommensteuer_n10[["EinkommensteuerErgebnis(…)"]]
BerechneEinkommensteuer_n11("Ergebnis: EinkommensteuerErgebnis")
BerechneEinkommensteuer_n1 --> BerechneEinkommensteuer_n0
BerechneEinkommensteuer_n2 --> BerechneEinkommensteuer_n3
BerechneEinkommensteuer_n3 --> BerechneEinkommensteuer_n4
BerechneEinkommensteuer_n4 --> BerechneEinkommensteuer_n5
BerechneEinkommensteuer_n5 --> BerechneEinkommensteuer_n6
BerechneEinkommensteuer_n6 --> BerechneEinkommensteuer_n7
BerechneEinkommensteuer_n7 --> BerechneEinkommensteuer_n8
BerechneEinkommensteuer_n8 --> BerechneEinkommensteuer_n9
BerechneEinkommensteuer_n9 --> BerechneEinkommensteuer_n10
BerechneEinkommensteuer_n0 --> BerechneEinkommensteuer_n2
BerechneEinkommensteuer_n10 --> BerechneEinkommensteuer_n11
click BerechneEinkommensteuer_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Orchestrator — vollständige Veranlagung in gesetzlicher Reihenfolge (§ 2 EStG). Füllt jede Zwischengröße ins Ergebnis-Datensatz." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class BerechneEinkommensteuer_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class BerechneEinkommensteuer_n1 eingabe
classDef subprogram fill:#eeeffb,stroke:#c3c6ef,stroke-width:1px,color:#3c4043
class BerechneEinkommensteuer_n2,BerechneEinkommensteuer_n3,BerechneEinkommensteuer_n4,BerechneEinkommensteuer_n5,BerechneEinkommensteuer_n6,BerechneEinkommensteuer_n7,BerechneEinkommensteuer_n8,BerechneEinkommensteuer_n9,BerechneEinkommensteuer_n10 subprogram
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class BerechneEinkommensteuer_n11 ende
# Programmablaufpläne — est
## EstGrundtarif
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
EstGrundtarif_n0("EstGrundtarif<br/><br/>⟨§ 32a Absatz 1 EStG⟩")
EstGrundtarif_n1[/"zve: Euro"/]
EstGrundtarif_n2{"zve #lt; 0 als Euro"}
EstGrundtarif_n3("abbruch<br/>§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht n…")
EstGrundtarif_n4{"zve #lt; GFB +<br/>1"}
EstGrundtarif_n5["0"]
EstGrundtarif_n6{"zve #lt; ZONE_2_OBERGRENZE +<br/>1"}
EstGrundtarif_n7["y ← (zve -<br/>GFB) /<br/>ZEHNTAUSEND"]
EstGrundtarif_n8["roh ← (ZONE_2_PROGRESSION *<br/>y +<br/>ZONE_2_LINEAR) *<br/>y"]
EstGrundtarif_n9["roh.abrunden() als Euro"]
EstGrundtarif_n10{"zve #lt; ZONE_3_OBERGRENZE +<br/>1"}
EstGrundtarif_n11["z ← (zve -<br/>ZONE_2_OBERGRENZE) /<br/>ZEHNTAUSEND"]
EstGrundtarif_n12["roh ← (ZONE_3_PROGRESSION *<br/>z +<br/>ZONE_3_LINEAR) *<br/>z +<br/>ZONE_3_KONSTANTE"]
EstGrundtarif_n13["roh.abrunden() als Euro"]
EstGrundtarif_n14{"zve #lt; ZONE_4_OBERGRENZE +<br/>1"}
EstGrundtarif_n15["(ZONE_4_SATZ *<br/>zve -<br/>ZONE_4_ABZUG).abrunden()"]
EstGrundtarif_n16["(ZONE_5_SATZ *<br/>zve -<br/>ZONE_5_ABZUG).abrunden()"]
EstGrundtarif_n17("Ergebnis: Euro")
EstGrundtarif_n1 --> EstGrundtarif_n0
EstGrundtarif_n2 -->|"ja"| EstGrundtarif_n3
EstGrundtarif_n2 -->|"nein"| EstGrundtarif_n4
EstGrundtarif_n4 -->|"ja"| EstGrundtarif_n5
EstGrundtarif_n4 -->|"nein"| EstGrundtarif_n6
EstGrundtarif_n7 --> EstGrundtarif_n8
EstGrundtarif_n8 --> EstGrundtarif_n9
EstGrundtarif_n6 -->|"ja"| EstGrundtarif_n7
EstGrundtarif_n6 -->|"nein"| EstGrundtarif_n10
EstGrundtarif_n11 --> EstGrundtarif_n12
EstGrundtarif_n12 --> EstGrundtarif_n13
EstGrundtarif_n10 -->|"ja"| EstGrundtarif_n11
EstGrundtarif_n10 -->|"nein"| EstGrundtarif_n14
EstGrundtarif_n14 -->|"ja"| EstGrundtarif_n15
EstGrundtarif_n14 -->|"nein"| EstGrundtarif_n16
EstGrundtarif_n0 --> EstGrundtarif_n2
EstGrundtarif_n5 --> EstGrundtarif_n17
EstGrundtarif_n9 --> EstGrundtarif_n17
EstGrundtarif_n13 --> EstGrundtarif_n17
EstGrundtarif_n15 --> EstGrundtarif_n17
EstGrundtarif_n16 --> EstGrundtarif_n17
click EstGrundtarif_n0 href "https://www.gesetze-im-internet.de/estg/__32a.html" "Tariflicher Einkommensteuerbetrag nach dem Grundtarif (§ 32a Absatz 1 EStG). Das zu versteuernde Einkommen ist nach Satz 1 auf volle Euro abgerundet zu verstehen (durch den `Euro`-Typ bereits ganzzahlig). Der sich ergebende Steuerbetrag wird nach Satz 6 auf den nächsten vollen Euro abgerundet. Mit den Hilfsgrößen y = (zvE - GFB)/10000 (Zone 2) und z = (zvE - ZONE_2)/10000 (Zone 3) lautet der Tarif zonenweise: ESt(zvE) = 0 wenn zvE <= GFB (a_2y + b_2)y wenn Zone 2 (a_3z + b_3)z + c_3 wenn Zone 3 0,42 · zvE - C_4 wenn Zone 4 0,45 · zvE - C_5 wenn Zone 5" _blank
click EstGrundtarif_n3 href "https://www.gesetze-im-internet.de/estg/__32a.html" "§ 32a Absatz 1 EStG: zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve})" _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class EstGrundtarif_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class EstGrundtarif_n1 eingabe
classDef decision fill:#fdf6e0,stroke:#ecd79b,stroke-width:1px,color:#3c4043
class EstGrundtarif_n2,EstGrundtarif_n4,EstGrundtarif_n6,EstGrundtarif_n10,EstGrundtarif_n14 decision
classDef abbruch fill:#fdecea,stroke:#f1b0a8,stroke-width:1px,color:#3c4043
class EstGrundtarif_n3 abbruch
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class EstGrundtarif_n5,EstGrundtarif_n7,EstGrundtarif_n8,EstGrundtarif_n9,EstGrundtarif_n11,EstGrundtarif_n12,EstGrundtarif_n13,EstGrundtarif_n15,EstGrundtarif_n16 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class EstGrundtarif_n17 ende
```
## EstSplitting
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
EstSplitting_n0("EstSplitting<br/><br/>⟨§ 32a Absatz 5 EStG⟩")
EstSplitting_n1[/"zve: Euro"/]
EstSplitting_n2{"zve #lt; 0 als Euro"}
EstSplitting_n3("abbruch<br/>§ 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen da…")
EstSplitting_n4["halbesZve ← (zve /<br/>2).abrunden() als Euro"]
EstSplitting_n5["2 *<br/>EstGrundtarif(…)"]
EstSplitting_n6("Ergebnis: Euro")
EstSplitting_n1 --> EstSplitting_n0
EstSplitting_n2 -->|"ja"| EstSplitting_n3
EstSplitting_n4 --> EstSplitting_n5
EstSplitting_n2 -->|"nein"| EstSplitting_n4
EstSplitting_n0 --> EstSplitting_n2
EstSplitting_n5 --> EstSplitting_n6
click EstSplitting_n0 href "https://www.gesetze-im-internet.de/estg/__32a.html" "Tariflicher Einkommensteuerbetrag nach dem Splitting-Verfahren für zusammen veranlagte Ehegatten (§ 32a Absatz 5 EStG): das Zweifache des Steuerbetrags, der sich für die Hälfte des gemeinsam zu versteuernden Einkommens nach Absatz 1 ergibt. Die Hälfte wird nach Absatz 1 Satz 1 auf volle Euro abgerundet." _blank
click EstSplitting_n3 href "https://www.gesetze-im-internet.de/estg/__32a.html" "§ 32a Absatz 5 EStG: gemeinsam zu versteuerndes Einkommen darf nicht negativ sein (zvE=${zve})" _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class EstSplitting_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class EstSplitting_n1 eingabe
classDef decision fill:#fdf6e0,stroke:#ecd79b,stroke-width:1px,color:#3c4043
class EstSplitting_n2 decision
classDef abbruch fill:#fdecea,stroke:#f1b0a8,stroke-width:1px,color:#3c4043
class EstSplitting_n3 abbruch
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class EstSplitting_n4,EstSplitting_n5 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class EstSplitting_n6 ende
```
## _Spanne
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
_Spanne_n0("_Spanne")
_Spanne_n1[/"betrag: Euro"/]
_Spanne_n2[/"von: Euro"/]
_Spanne_n3[/"obereGrenze: Euro"/]
_Spanne_n4["(betrag.höchstens(…) -<br/>von).mindestens(…)"]
_Spanne_n5("Ergebnis: Euro")
_Spanne_n1 --> _Spanne_n0
_Spanne_n2 --> _Spanne_n0
_Spanne_n3 --> _Spanne_n0
_Spanne_n0 --> _Spanne_n4
_Spanne_n4 --> _Spanne_n5
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class _Spanne_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class _Spanne_n1,_Spanne_n2,_Spanne_n3 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class _Spanne_n4 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class _Spanne_n5 ende
```
## SummeDerEinkuenfte
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
SummeDerEinkuenfte_n0("SummeDerEinkuenfte<br/><br/>⟨§ 2 Absatz 1 und 2 EStG⟩")
SummeDerEinkuenfte_n1[/"fall: EinkommensteuerFall"/]
SummeDerEinkuenfte_n2["fall.einkuenfteLandUndForstwirtschaft +<br/>fall.einkuenfteGewerbebetrieb +<br/>fall.einkuenfteSelbstaendigeArbeit +<br/>fall.einkuenfteNichtselbstaendigeArbeit +<br/>fall.einkuenfteKapitalvermoegen +<br/>fall.einkuenfteVermietungVerpachtung +<br/>fall.sonstigeEinkuenfte"]
SummeDerEinkuenfte_n3("Ergebnis: Euro")
SummeDerEinkuenfte_n1 --> SummeDerEinkuenfte_n0
SummeDerEinkuenfte_n0 --> SummeDerEinkuenfte_n2
SummeDerEinkuenfte_n2 --> SummeDerEinkuenfte_n3
click SummeDerEinkuenfte_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Summe der Einkünfte (§ 2 Absatz 1 und 2 EStG): Summe der sieben Einkunftsarten. Negative Einkünfte einzelner Arten mindern die Summe (einkunftsartübergreifende Verlustverrechnungsbeschränkungen sind anderes Recht und in den Eingaben bereits berücksichtigt)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class SummeDerEinkuenfte_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class SummeDerEinkuenfte_n1 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class SummeDerEinkuenfte_n2 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class SummeDerEinkuenfte_n3 ende
```
## GesamtbetragDerEinkuenfte
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
GesamtbetragDerEinkuenfte_n0("GesamtbetragDerEinkuenfte<br/><br/>⟨§ 2 Absatz 3 EStG⟩")
GesamtbetragDerEinkuenfte_n1[/"summe: Euro"/]
GesamtbetragDerEinkuenfte_n2[/"fall: EinkommensteuerFall"/]
GesamtbetragDerEinkuenfte_n3["summe -<br/>fall.altersentlastungsbetrag -<br/>fall.entlastungsbetragAlleinerziehende -<br/>fall.freibetragLandUndForstwirtschaft"]
GesamtbetragDerEinkuenfte_n4("Ergebnis: Euro")
GesamtbetragDerEinkuenfte_n1 --> GesamtbetragDerEinkuenfte_n0
GesamtbetragDerEinkuenfte_n2 --> GesamtbetragDerEinkuenfte_n0
GesamtbetragDerEinkuenfte_n0 --> GesamtbetragDerEinkuenfte_n3
GesamtbetragDerEinkuenfte_n3 --> GesamtbetragDerEinkuenfte_n4
click GesamtbetragDerEinkuenfte_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Gesamtbetrag der Einkünfte (§ 2 Absatz 3 EStG): Summe der Einkünfte vermindert um Altersentlastungsbetrag (§ 24a), Entlastungsbetrag für Alleinerziehende (§ 24b) und Abzug nach § 13 Absatz 3." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class GesamtbetragDerEinkuenfte_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class GesamtbetragDerEinkuenfte_n1,GesamtbetragDerEinkuenfte_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class GesamtbetragDerEinkuenfte_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class GesamtbetragDerEinkuenfte_n4 ende
```
## KinderfreibetragGesamt
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
KinderfreibetragGesamt_n0("KinderfreibetragGesamt<br/><br/>⟨§ 32 Absatz 6 EStG⟩")
KinderfreibetragGesamt_n1[/"kinder: Liste#lt;Kind#gt;"/]
KinderfreibetragGesamt_n2["(<br/>kinder.zuordnen(…).summe()<br/>).abrunden()"]
KinderfreibetragGesamt_n3("Ergebnis: Euro")
KinderfreibetragGesamt_n1 --> KinderfreibetragGesamt_n0
KinderfreibetragGesamt_n0 --> KinderfreibetragGesamt_n2
KinderfreibetragGesamt_n2 --> KinderfreibetragGesamt_n3
click KinderfreibetragGesamt_n0 href "https://www.gesetze-im-internet.de/estg/__32.html" "Kinderfreibetrag + BEA-Freibetrag, aggregiert über alle Kinder (§ 32 Absatz 6 EStG): je Kind `(3.414 + 1.464) · faktor · berücksichtigteMonate/12 · auslandsfaktor`; die Summe wird auf volle Euro abgerundet (Modellierungs-Entscheidung, s. Datei-Doc)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class KinderfreibetragGesamt_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class KinderfreibetragGesamt_n1 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class KinderfreibetragGesamt_n2 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class KinderfreibetragGesamt_n3 ende
```
## ZumutbareBelastung
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
ZumutbareBelastung_n0("ZumutbareBelastung<br/><br/>⟨§ 33 Absatz 3 EStG⟩")
ZumutbareBelastung_n1[/"gde: Euro"/]
ZumutbareBelastung_n2[/"kinderzahl: Ganzzahl"/]
ZumutbareBelastung_n3[/"tarifart: Tarifart"/]
ZumutbareBelastung_n4["_ZmbSatz(…) *<br/>_Spanne(…) +<br/>_ZmbSatz(…) *<br/>_Spanne(…) +<br/>_ZmbSatz(…) *<br/>(gde -<br/>ZMB_STUFE_2).mindestens(…)"]
ZumutbareBelastung_n5("Ergebnis: EuroCent")
ZumutbareBelastung_n1 --> ZumutbareBelastung_n0
ZumutbareBelastung_n2 --> ZumutbareBelastung_n0
ZumutbareBelastung_n3 --> ZumutbareBelastung_n0
ZumutbareBelastung_n0 --> ZumutbareBelastung_n4
ZumutbareBelastung_n4 --> ZumutbareBelastung_n5
click ZumutbareBelastung_n0 href "https://www.gesetze-im-internet.de/estg/__33.html" "Zumutbare Belastung (§ 33 Absatz 3 EStG) — **staffelweise** über die drei GdE-Stufen (bis 15.340 / bis 51.130 / darüber), mit den Prozentsätzen der vier Personengruppen (keine Kinder Grund/Splitting, 1–2 Kinder, ≥ 3 Kinder). „Kinder' sind die mit Freibetrag § 32 Abs. 6 oder Kindergeld-Anspruch (§ 33 Abs. 3 Satz 2 — hier `kinderzahl`)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class ZumutbareBelastung_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class ZumutbareBelastung_n1,ZumutbareBelastung_n2,ZumutbareBelastung_n3 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class ZumutbareBelastung_n4 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class ZumutbareBelastung_n5 ende
```
## _ZmbSatz
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
_ZmbSatz_n0("_ZmbSatz<br/><br/>⟨§ 33 Absatz 3 Satz 1 EStG⟩")
_ZmbSatz_n1[/"stufe: Ganzzahl"/]
_ZmbSatz_n2[/"kinderzahl: Ganzzahl"/]
_ZmbSatz_n3[/"tarifart: Tarifart"/]
_ZmbSatz_n4{"kinderzahl #lt; 1"}
_ZmbSatz_n5{{"wähle tarifart"}}
_ZmbSatz_n6{"stufe #lt; 2"}
_ZmbSatz_n7["ZMB_OHNE_KIND_GRUND_1"]
_ZmbSatz_n8{"stufe #lt; 3"}
_ZmbSatz_n9["ZMB_OHNE_KIND_GRUND_2"]
_ZmbSatz_n10["ZMB_OHNE_KIND_GRUND_3"]
_ZmbSatz_n11{"stufe #lt; 2"}
_ZmbSatz_n12["ZMB_OHNE_KIND_SPLIT_1"]
_ZmbSatz_n13{"stufe #lt; 3"}
_ZmbSatz_n14["ZMB_OHNE_KIND_SPLIT_2"]
_ZmbSatz_n15["ZMB_OHNE_KIND_SPLIT_3"]
_ZmbSatz_n16{"kinderzahl #lt; 3"}
_ZmbSatz_n17{"stufe #lt; 2"}
_ZmbSatz_n18["ZMB_1_2_KINDER_1"]
_ZmbSatz_n19{"stufe #lt; 3"}
_ZmbSatz_n20["ZMB_1_2_KINDER_2"]
_ZmbSatz_n21["ZMB_1_2_KINDER_3"]
_ZmbSatz_n22{"stufe #lt; 2"}
_ZmbSatz_n23["ZMB_AB_3_KINDER_1"]
_ZmbSatz_n24{"stufe #lt; 3"}
_ZmbSatz_n25["ZMB_AB_3_KINDER_2"]
_ZmbSatz_n26["ZMB_AB_3_KINDER_3"]
_ZmbSatz_n27("Ergebnis: Prozent")
_ZmbSatz_n1 --> _ZmbSatz_n0
_ZmbSatz_n2 --> _ZmbSatz_n0
_ZmbSatz_n3 --> _ZmbSatz_n0
_ZmbSatz_n6 -->|"ja"| _ZmbSatz_n7
_ZmbSatz_n6 -->|"nein"| _ZmbSatz_n8
_ZmbSatz_n8 -->|"ja"| _ZmbSatz_n9
_ZmbSatz_n8 -->|"nein"| _ZmbSatz_n10
_ZmbSatz_n5 -->|"Grundtarif"| _ZmbSatz_n6
_ZmbSatz_n11 -->|"ja"| _ZmbSatz_n12
_ZmbSatz_n11 -->|"nein"| _ZmbSatz_n13
_ZmbSatz_n13 -->|"ja"| _ZmbSatz_n14
_ZmbSatz_n13 -->|"nein"| _ZmbSatz_n15
_ZmbSatz_n5 -->|"Splitting"| _ZmbSatz_n11
_ZmbSatz_n4 -->|"ja"| _ZmbSatz_n5
_ZmbSatz_n4 -->|"nein"| _ZmbSatz_n16
_ZmbSatz_n17 -->|"ja"| _ZmbSatz_n18
_ZmbSatz_n17 -->|"nein"| _ZmbSatz_n19
_ZmbSatz_n19 -->|"ja"| _ZmbSatz_n20
_ZmbSatz_n19 -->|"nein"| _ZmbSatz_n21
_ZmbSatz_n16 -->|"ja"| _ZmbSatz_n17
_ZmbSatz_n22 -->|"ja"| _ZmbSatz_n23
_ZmbSatz_n22 -->|"nein"| _ZmbSatz_n24
_ZmbSatz_n24 -->|"ja"| _ZmbSatz_n25
_ZmbSatz_n24 -->|"nein"| _ZmbSatz_n26
_ZmbSatz_n16 -->|"nein"| _ZmbSatz_n22
_ZmbSatz_n0 --> _ZmbSatz_n4
_ZmbSatz_n7 --> _ZmbSatz_n27
_ZmbSatz_n9 --> _ZmbSatz_n27
_ZmbSatz_n10 --> _ZmbSatz_n27
_ZmbSatz_n12 --> _ZmbSatz_n27
_ZmbSatz_n14 --> _ZmbSatz_n27
_ZmbSatz_n15 --> _ZmbSatz_n27
_ZmbSatz_n18 --> _ZmbSatz_n27
_ZmbSatz_n20 --> _ZmbSatz_n27
_ZmbSatz_n21 --> _ZmbSatz_n27
_ZmbSatz_n23 --> _ZmbSatz_n27
_ZmbSatz_n25 --> _ZmbSatz_n27
_ZmbSatz_n26 --> _ZmbSatz_n27
click _ZmbSatz_n0 href "https://www.gesetze-im-internet.de/estg/__33.html" "Prozentsatz der zumutbaren Belastung für GdE-Stufe (1/2/3)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class _ZmbSatz_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class _ZmbSatz_n1,_ZmbSatz_n2,_ZmbSatz_n3 eingabe
classDef decision fill:#fdf6e0,stroke:#ecd79b,stroke-width:1px,color:#3c4043
class _ZmbSatz_n4,_ZmbSatz_n6,_ZmbSatz_n8,_ZmbSatz_n11,_ZmbSatz_n13,_ZmbSatz_n16,_ZmbSatz_n17,_ZmbSatz_n19,_ZmbSatz_n22,_ZmbSatz_n24 decision
classDef case fill:#fcf0e2,stroke:#f0c79a,stroke-width:1px,color:#3c4043
class _ZmbSatz_n5 case
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class _ZmbSatz_n7,_ZmbSatz_n9,_ZmbSatz_n10,_ZmbSatz_n12,_ZmbSatz_n14,_ZmbSatz_n15,_ZmbSatz_n18,_ZmbSatz_n20,_ZmbSatz_n21,_ZmbSatz_n23,_ZmbSatz_n25,_ZmbSatz_n26 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class _ZmbSatz_n27 ende
```
## AbziehbareAussergewoehnlicheBelastungen
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
AbziehbareAussergewoehnlicheBelastungen_n0("AbziehbareAussergewoehnlicheBelastungen<br/><br/>⟨§ 33 Absatz 1 EStG⟩")
AbziehbareAussergewoehnlicheBelastungen_n1[/"fall: EinkommensteuerFall"/]
AbziehbareAussergewoehnlicheBelastungen_n2[/"gde: Euro"/]
AbziehbareAussergewoehnlicheBelastungen_n3["(<br/>(fall.aussergewoehnlicheAufwendungen.summe() als EuroCent) -<br/>ZumutbareBelastung(…)<br/>).mindestens(…).abrunden()"]
AbziehbareAussergewoehnlicheBelastungen_n4("Ergebnis: Euro")
AbziehbareAussergewoehnlicheBelastungen_n1 --> AbziehbareAussergewoehnlicheBelastungen_n0
AbziehbareAussergewoehnlicheBelastungen_n2 --> AbziehbareAussergewoehnlicheBelastungen_n0
AbziehbareAussergewoehnlicheBelastungen_n0 --> AbziehbareAussergewoehnlicheBelastungen_n3
AbziehbareAussergewoehnlicheBelastungen_n3 --> AbziehbareAussergewoehnlicheBelastungen_n4
click AbziehbareAussergewoehnlicheBelastungen_n0 href "https://www.gesetze-im-internet.de/estg/__33.html" "Abziehbare außergewöhnliche Belastungen (§ 33 Absatz 1 EStG): Summe der zwangsläufigen Aufwendungen, soweit sie die zumutbare Belastung (§ 33 Abs. 3) übersteigt; nie negativ, auf volle Euro abgerundet." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class AbziehbareAussergewoehnlicheBelastungen_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class AbziehbareAussergewoehnlicheBelastungen_n1,AbziehbareAussergewoehnlicheBelastungen_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class AbziehbareAussergewoehnlicheBelastungen_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class AbziehbareAussergewoehnlicheBelastungen_n4 ende
```
## AbziehbareSpenden
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
AbziehbareSpenden_n0("AbziehbareSpenden<br/><br/>⟨§ 10b Absatz 1 EStG⟩")
AbziehbareSpenden_n1[/"fall: EinkommensteuerFall"/]
AbziehbareSpenden_n2[/"gde: Euro"/]
AbziehbareSpenden_n3["grenzeGde ← (SPENDEN_HB_GDE *<br/>gde).abrunden()"]
AbziehbareSpenden_n4["grenzeUmsatz ← (SPENDEN_HB_UMSATZ *<br/>fall.umsaetzeUndLoehne).abrunden()"]
AbziehbareSpenden_n5[["hoechstbetrag ← grenzeGde.mindestens(…)"]]
AbziehbareSpenden_n6[["fall.spenden.summe().höchstens(…)"]]
AbziehbareSpenden_n7("Ergebnis: Euro")
AbziehbareSpenden_n1 --> AbziehbareSpenden_n0
AbziehbareSpenden_n2 --> AbziehbareSpenden_n0
AbziehbareSpenden_n3 --> AbziehbareSpenden_n4
AbziehbareSpenden_n4 --> AbziehbareSpenden_n5
AbziehbareSpenden_n5 --> AbziehbareSpenden_n6
AbziehbareSpenden_n0 --> AbziehbareSpenden_n3
AbziehbareSpenden_n6 --> AbziehbareSpenden_n7
click AbziehbareSpenden_n0 href "https://www.gesetze-im-internet.de/estg/__10b.html" "Abziehbare Spenden (§ 10b Absatz 1 EStG): Summe der Zuwendungen, gedeckelt auf den Höchstbetrag = größerer Wert aus 20 % des Gesamtbetrags der Einkünfte und 4 ‰ der Umsätze + Löhne; auf volle Euro abgerundet." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n1,AbziehbareSpenden_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n3,AbziehbareSpenden_n4 operation
classDef subprogram fill:#eeeffb,stroke:#c3c6ef,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n5,AbziehbareSpenden_n6 subprogram
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class AbziehbareSpenden_n7 ende
```
## Einkommen
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
Einkommen_n0("Einkommen<br/><br/>⟨§ 2 Absatz 4 EStG⟩")
Einkommen_n1[/"gesamtbetrag: Euro"/]
Einkommen_n2[/"fall: EinkommensteuerFall"/]
Einkommen_n3["gesamtbetrag -<br/>fall.sonstigeSonderausgaben -<br/>AbziehbareSpenden(…) -<br/>AbziehbareAussergewoehnlicheBelastungen(…)"]
Einkommen_n4("Ergebnis: Euro")
Einkommen_n1 --> Einkommen_n0
Einkommen_n2 --> Einkommen_n0
Einkommen_n0 --> Einkommen_n3
Einkommen_n3 --> Einkommen_n4
click Einkommen_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Einkommen (§ 2 Absatz 4 EStG): Gesamtbetrag der Einkünfte vermindert um die Sonderausgaben (sonstige + abziehbare Spenden § 10b) und die abziehbaren außergewöhnlichen Belastungen (§ 33)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class Einkommen_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class Einkommen_n1,Einkommen_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class Einkommen_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class Einkommen_n4 ende
```
## ZuVersteuerndesEinkommen
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
ZuVersteuerndesEinkommen_n0("ZuVersteuerndesEinkommen<br/><br/>⟨§ 2 Absatz 5 Satz 1 EStG⟩")
ZuVersteuerndesEinkommen_n1[/"einkommen: Euro"/]
ZuVersteuerndesEinkommen_n2[/"fall: EinkommensteuerFall"/]
ZuVersteuerndesEinkommen_n3["einkommen -<br/>KinderfreibetragGesamt(…) -<br/>fall.sonstigeAbzuegeVomEinkommen"]
ZuVersteuerndesEinkommen_n4("Ergebnis: Euro")
ZuVersteuerndesEinkommen_n1 --> ZuVersteuerndesEinkommen_n0
ZuVersteuerndesEinkommen_n2 --> ZuVersteuerndesEinkommen_n0
ZuVersteuerndesEinkommen_n0 --> ZuVersteuerndesEinkommen_n3
ZuVersteuerndesEinkommen_n3 --> ZuVersteuerndesEinkommen_n4
click ZuVersteuerndesEinkommen_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Zu versteuerndes Einkommen (§ 2 Absatz 5 Satz 1 EStG): Einkommen vermindert um die Freibeträge nach § 32 Absatz 6 (Kinder) und die sonstigen vom Einkommen abzuziehenden Beträge." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class ZuVersteuerndesEinkommen_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class ZuVersteuerndesEinkommen_n1,ZuVersteuerndesEinkommen_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class ZuVersteuerndesEinkommen_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class ZuVersteuerndesEinkommen_n4 ende
```
## TariflicheEinkommensteuer
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
TariflicheEinkommensteuer_n0("TariflicheEinkommensteuer<br/><br/>⟨§ 32a Absatz 1 und 5 EStG⟩")
TariflicheEinkommensteuer_n1[/"zve: Euro"/]
TariflicheEinkommensteuer_n2[/"tarifart: Tarifart"/]
TariflicheEinkommensteuer_n3{{"wähle tarifart"}}
TariflicheEinkommensteuer_n4[["EstGrundtarif(…)"]]
TariflicheEinkommensteuer_n5[["EstSplitting(…)"]]
TariflicheEinkommensteuer_n6("Ergebnis: Euro")
TariflicheEinkommensteuer_n1 --> TariflicheEinkommensteuer_n0
TariflicheEinkommensteuer_n2 --> TariflicheEinkommensteuer_n0
TariflicheEinkommensteuer_n3 -->|"Grundtarif"| TariflicheEinkommensteuer_n4
TariflicheEinkommensteuer_n3 -->|"Splitting"| TariflicheEinkommensteuer_n5
TariflicheEinkommensteuer_n0 --> TariflicheEinkommensteuer_n3
TariflicheEinkommensteuer_n4 --> TariflicheEinkommensteuer_n6
TariflicheEinkommensteuer_n5 --> TariflicheEinkommensteuer_n6
click TariflicheEinkommensteuer_n0 href "https://www.gesetze-im-internet.de/estg/__32a.html" "Tarifliche Einkommensteuer (§ 32a EStG): Grund- oder Splittingtarif. Negatives zvE → 0 (§ 32a für negatives zvE nicht definiert; § 10d Verlustabzug ist Verfahren, nicht modelliert)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n1,TariflicheEinkommensteuer_n2 eingabe
classDef case fill:#fcf0e2,stroke:#f0c79a,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n3 case
classDef subprogram fill:#eeeffb,stroke:#c3c6ef,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n4,TariflicheEinkommensteuer_n5 subprogram
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class TariflicheEinkommensteuer_n6 ende
```
## FestzusetzendeEinkommensteuer
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
FestzusetzendeEinkommensteuer_n0("FestzusetzendeEinkommensteuer<br/><br/>⟨§ 2 Absatz 6 EStG⟩")
FestzusetzendeEinkommensteuer_n1[/"tariflich: Euro"/]
FestzusetzendeEinkommensteuer_n2[/"fall: EinkommensteuerFall"/]
FestzusetzendeEinkommensteuer_n3["tariflich -<br/>fall.anrechnungenUndErmaessigungen +<br/>fall.hinzurechnungen"]
FestzusetzendeEinkommensteuer_n4("Ergebnis: Euro")
FestzusetzendeEinkommensteuer_n1 --> FestzusetzendeEinkommensteuer_n0
FestzusetzendeEinkommensteuer_n2 --> FestzusetzendeEinkommensteuer_n0
FestzusetzendeEinkommensteuer_n0 --> FestzusetzendeEinkommensteuer_n3
FestzusetzendeEinkommensteuer_n3 --> FestzusetzendeEinkommensteuer_n4
click FestzusetzendeEinkommensteuer_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Festzusetzende Einkommensteuer (§ 2 Absatz 6 EStG): tarifliche Steuer vermindert um Anrechnungen/Steuerermäßigungen, vermehrt um Hinzurechnungen (Komponenten + Kappungen = anderes Recht/Eingabe; keine Untergrenze — der Wortlaut sieht keine vor)." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class FestzusetzendeEinkommensteuer_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class FestzusetzendeEinkommensteuer_n1,FestzusetzendeEinkommensteuer_n2 eingabe
classDef operation fill:#f6f7f8,stroke:#d8dce0,stroke-width:1px,color:#3c4043
class FestzusetzendeEinkommensteuer_n3 operation
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class FestzusetzendeEinkommensteuer_n4 ende
```
## BerechneEinkommensteuer
```mermaid
%%{init: {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'themeVariables': {'fontFamily': 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace', 'fontSize': '13px', 'lineColor': '#c8ccd1'}, 'flowchart': {'curve': 'basis', 'padding': 10, 'nodeSpacing': 45, 'rankSpacing': 45}}}%%
flowchart TD
BerechneEinkommensteuer_n0("BerechneEinkommensteuer<br/><br/>⟨§ 2 EStG, § 32a EStG⟩")
BerechneEinkommensteuer_n1[/"fall: EinkommensteuerFall"/]
BerechneEinkommensteuer_n2[["sde ← SummeDerEinkuenfte(…)"]]
BerechneEinkommensteuer_n3[["gde ← GesamtbetragDerEinkuenfte(…)"]]
BerechneEinkommensteuer_n4[["kfb ← KinderfreibetragGesamt(…)"]]
BerechneEinkommensteuer_n5[["agb ← AbziehbareAussergewoehnlicheBelastungen(…)"]]
BerechneEinkommensteuer_n6[["ein ← Einkommen(…)"]]
BerechneEinkommensteuer_n7[["zve ← ZuVersteuerndesEinkommen(…)"]]
BerechneEinkommensteuer_n8[["tariflich ← TariflicheEinkommensteuer(…)"]]
BerechneEinkommensteuer_n9[["fest ← FestzusetzendeEinkommensteuer(…)"]]
BerechneEinkommensteuer_n10[["EinkommensteuerErgebnis(…)"]]
BerechneEinkommensteuer_n11("Ergebnis: EinkommensteuerErgebnis")
BerechneEinkommensteuer_n1 --> BerechneEinkommensteuer_n0
BerechneEinkommensteuer_n2 --> BerechneEinkommensteuer_n3
BerechneEinkommensteuer_n3 --> BerechneEinkommensteuer_n4
BerechneEinkommensteuer_n4 --> BerechneEinkommensteuer_n5
BerechneEinkommensteuer_n5 --> BerechneEinkommensteuer_n6
BerechneEinkommensteuer_n6 --> BerechneEinkommensteuer_n7
BerechneEinkommensteuer_n7 --> BerechneEinkommensteuer_n8
BerechneEinkommensteuer_n8 --> BerechneEinkommensteuer_n9
BerechneEinkommensteuer_n9 --> BerechneEinkommensteuer_n10
BerechneEinkommensteuer_n0 --> BerechneEinkommensteuer_n2
BerechneEinkommensteuer_n10 --> BerechneEinkommensteuer_n11
click BerechneEinkommensteuer_n0 href "https://www.gesetze-im-internet.de/estg/__2.html" "Orchestrator — vollständige Veranlagung in gesetzlicher Reihenfolge (§ 2 EStG). Füllt jede Zwischengröße ins Ergebnis-Datensatz." _blank
classDef start fill:#eef4fe,stroke:#a9c7f5,stroke-width:1px,color:#3c4043
class BerechneEinkommensteuer_n0 start
classDef eingabe fill:#e9f3fb,stroke:#b2d3ec,stroke-width:1px,color:#3c4043
class BerechneEinkommensteuer_n1 eingabe
classDef subprogram fill:#eeeffb,stroke:#c3c6ef,stroke-width:1px,color:#3c4043
class BerechneEinkommensteuer_n2,BerechneEinkommensteuer_n3,BerechneEinkommensteuer_n4,BerechneEinkommensteuer_n5,BerechneEinkommensteuer_n6,BerechneEinkommensteuer_n7,BerechneEinkommensteuer_n8,BerechneEinkommensteuer_n9,BerechneEinkommensteuer_n10 subprogram
classDef ende fill:#eaf5ee,stroke:#a6d5b8,stroke-width:1px,color:#3c4043
class BerechneEinkommensteuer_n11 ende
```