8. Практичне завдання — версія 1
8.1. Задача

Наведена вище таблиця дозволяє розрахувати податок у спрощеному випадку, коли платник податків декларує лише свою заробітну плату. Як зазначено у примітці (1), розрахований таким чином податок є податком до застосування трьох механізмів:
- обмеження сімейного коефіцієнта, яке застосовується до високих доходів;
- знижки та зменшення податку, що застосовуються до низьких доходів;
Отже, розрахунок податку включає такі етапи [http://impotsurlerevenu.org/comprendre-le-calcul-de-l-impot/1217-calcul-de-l-impot-2019.php]:

Пропонується написати програму, що дозволяє розрахувати податок платника податків у спрощеному випадку, коли платник податків має лише одну заробітну плату, яку потрібно задекларувати:
8.1.1. Розрахунок валового податку
Валовий податок можна розрахувати таким чином:
Спочатку обчислюємо кількість часток платника податків:
- кожен з батьків дає 1 частку;
- двоє перших дітей приносять по 1/2 частки;
- наступні діти — по одній частці кожен:
Отже, кількість часток становить:
- nbParts=1+nbEnfants*0,5+(nbEnfants-2)*0,5, якщо працівник не одружений;
- nbParts = 2 + nbEnfants * 0,5 + (nbEnfants - 2) * 0,5, якщо він одружений;
- де nbEnfants — кількість дітей;
- розраховується оподатковуваний дохід R = 0,9 * S, де S — річна заробітна плата;
- розраховується сімейний коефіцієнт QF = R / nbParts;
- розраховується валовий податок I на основі таких даних (2019 р.):
9964 | 0 | 0 |
27519 | 0,14 | 1394,96 |
73779 | 0,3 | 5798 |
156244 | 0,4 | 13913,69 |
0 | 0,45 | 20163,45 |
Кожен рядок має 3 поля: champ1, champ2, champ3. Щоб обчислити податок I, шукаємо перший рядок, у якому QF <= поле1, і беремо значення з цього рядка. Наприклад, для працівника, який перебуває у шлюбі, має двох дітей і отримує річну заробітну плату S у розмірі 50000 євро:
Оподатковуваний дохід: R = 0,9 * S = 45000
Кількість часток: nbParts = 2 + 2 * 0,5 = 3
Сімейний коефіцієнт: QF = 45 000 / 3 = 15 000
Перший рядок, де QF <= поле1, виглядає так:
Тоді податок I дорівнює 0,14*R – 1394,96*nbParts=[0,14*45000-1394,96*3]=2115. Податок округлюється до найближчого нижчого євро.
Якщо вже в першому рядку виконується умова QF <= поле1, то податок дорівнює нулю.
Якщо QF таке, що умова QF<=поле1 ніколи не виконується, то використовуються коефіцієнти останнього рядка. У даному випадку:
що дає валовий податок I = 0,45*R – 20163,45*nbParts.
8.1.2. Обмеження сімейного коефіцієнта

Щоб з’ясувати, чи застосовується обмеження сімейного коефіцієнта QF, потрібно перерахувати валовий податок без урахування дітей. Знову ж таки, для працівника, який перебуває у шлюбі, має двох дітей та отримує річну заробітну плату S у розмірі 50000 євро:
Оподатковуваний дохід: R = 0,9 * S = 45 000
Кількість часток: nbParts = 2 (дітей більше не враховують)
Сімейний коефіцієнт: QF = 45 000 / 2 = 22 500
Перший рядок, де QF <= поле1, виглядає так:
Податок I дорівнює 0,14*R – 1394,96*nbParts=[0,14*45000-1394,96*2]=3510.
Максимальний дохід, пов’язаний з дітьми: 1551 * 2 = 3102 євро
Мінімальний податок: 3510 – 3102 = 408 євро
Валовий податок із 3 частками, який вже розраховано як 2115 євро, перевищує мінімальний податок у розмірі 408 євро, тому сімейне обмеження в цьому випадку не застосовується.
Загалом, валовий податок перевищує (податок1, податок2), де:
- [impôt1] — валовий податок, розрахований з урахуванням дітей;
- [impôt2] — валовий податок, розрахований без урахування дітей та зменшений на максимальну суму пільги (у даному випадку 1551 євро за півчастини), пов’язану з дітьми;
8.1.3. Розрахунок знижки

Знову ж таки, для працівника, який перебуває у шлюбі, має двох дітей та отримує річну заробітну плату S у розмірі 50 000 євро:
Валовий податок (2115), отриманий на попередньому етапі, є меншим за 2627 євро для подружжя (1595 євро для одинокої особи): отже, застосовується знижка. Її розраховують за такою формулою:
знижка = поріг (для подружжя = 1970 / для одинокої особи = 1196) – 0,75 * валовий податок
знижка = 1970 – 0,75 × 2115 = 383,75, округлено до 384 євро.
Новий валовий податок = 2115 – 384 = 1731 євро
8.1.4. Розрахунок податкової знижки

Нижче певного порогу до валового податку, розрахованого за попередніми розрахунками, застосовується знижка у розмірі 20 %. У 2019 році пороги є такими:
- одинокі особи: 21 037 євро;
- для подружжя: 42 074 євро; (цифра 37 968, використана у наведеному вище прикладі, здається помилковою);
Цей поріг збільшується на величину: 3797 * (кількість півчастин, що припадають на дітей).
Знову ж таки, для працівника, який перебуває у шлюбі, має двох дітей та отримує річну заробітну плату S у розмірі 50 000 євро:
- його оподатковуваний дохід (45 000 євро) є меншим за поріг (42 074 + 2 × 3797) = 49 668 євро;
- отже, він має право на зменшення податку на 20 %: 1731 * 0,2 = 346,2 євро, округлено до 347 євро;
- валовий податок платника податків становить: 1731 – 347 = 1384 євро;
8.1.5. Розрахунок чистого податку
На цьому наш розрахунок завершується: чистий податок до сплати становитиме 1384 євро. Насправді платник податків може скористатися іншими пільгами, зокрема за пожертви на користь організацій, що діють в інтересах суспільства або загального блага.
8.1.6. Випадок високих доходів
Наш попередній приклад відповідає більшості випадків найманих працівників. Однак розрахунок податку відрізняється у випадку високих доходів.
8.1.6.1. Обмеження 10-відсоткової знижки на річний дохід
У більшості випадків оподатковуваний дохід обчислюється за формулою: R = 0,9 * S, де S — річна заробітна плата. Це називається 10-відсотковим зниженням. Для цього зниження встановлено верхню межу. У 2019 році:
- вона не може перевищувати 12 502 євро;
- вона не може бути меншою за 437 євро;
Розглянемо випадок неодруженого працівника без дітей із річною заробітною платою 200 000 євро:
- зниження на 10 % становить 20 000 євро > 12 502 євро. Отже, воно зменшується до 12 502 євро;
8.1.6.2. Обмеження сімейного коефіцієнта
Розглянемо випадок, коли застосовується обмеження сімейного коефіцієнта, описане в розділі |Обмеження сімейного коефіцієнта|. Розглянемо випадок подружжя з трьома дітьми та річним доходом 100 000 євро. Повторимо етапи розрахунку:
- відрахування у розмірі 10 % становить 10 000 євро < 12 502 євро. Отже, оподатковуваний дохід R дорівнює 100 000 – 10 000 = 90 000 євро;
- пара має nbParts = 2 + 0,5 × 2 + 1 = 4 частки;
- отже, їхній сімейний коефіцієнт становить QF = R / nbParts = 90 000 / 4 = 22 500 євро;
- їхній валовий податок I1 з урахуванням дітей становить I1=0,14*90000-1394,96*4= 7020 євро;
- його валовий податок I2 без дітей:
- QF = 90 000 / 2 = 45 000 євро;
- I2 = 0,3 × 90 000 – 5 798 × 2 = 15 404 євро;
- правило обмеження сімейного коефіцієнта передбачає, що виграш, який приносять діти, не може перевищувати (1551 × 4 півчастини) = 6204 євро. Однак у даному випадку він становить I2-I1 = 15404 – 7020 = 8384 євро, тобто перевищує 6204 євро;
- отже, валовий податок перераховується як I3 = I2-6204 = 15404 – 6204 = 9200 євро;
Ця подружня пара не матиме ані знижки, ані пільги, і її остаточний податок становитиме 9200 євро.
8.1.7. Офіційні цифри
Розрахунок податку є складним. У цьому документі розрахунки будуть проводитися на таких прикладах. Результати отримано за допомогою симулятора податкової адміністрації |https://www3.impots.gouv.fr/simulateur/calcul_impot/2019/simplifie/index.htm|:
Платник податків | Офіційні результати | Результати алгоритму, наведеного в документі |
Пара з двома дітьми та річним доходом 55555 євро | Податок = 2815 євро Ставка податку = 14 % | Податок = 2814 євро Ставка податку = 14 % |
Сім’я з двома дітьми та річним доходом 50 000 євро | Податок = 1385 євро Знижка = 720 євро Знижка = 0 євро Ставка податку = 14 % | Податок = 1384 євро Знижка = 384 євро Знижка = 347 євро Ставка податку = 14 % |
Пара з трьома дітьми та річним доходом 50 000 євро | Податок = 0 євро Знижка = 384 євро Знижка = 346 євро Ставка оподаткування = 14 % | Податок = 0 євро знижка = 720 євро Знижка = 0 євро Ставка податку = 14 % |
Одинока особа з 2 дітьми та річним доходом 100 000 євро | Податок = 19 884 євро Знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 41 % | Податок = 19 884 євро Надбавка = 4480 євро знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 41 % |
Одинока особа з 3 дітьми та річним доходом 100 000 євро | Податок = 16 782 євро Знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 41 % | Податок = 16 782 євро Надбавка = 7176 євро знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 41 % |
Подружжя з трьома дітьми та річним доходом 100 000 євро | Податок = 9200 євро знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 30 % | Податок = 9200 євро Надбавка = 2180 євро знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 30 % |
Пара з 5 дітьми та річним доходом 100 000 євро | Податок = 4230 євро Знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 14 % | Податок = 4230 євро знижка = 0 євро Знижка = 0 євро Ставка податку = 14 % |
Одинока особа без дітей із річним доходом 100 000 євро | Податок = 22 986 євро Знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 41 % | Податок = 22 986 євро Надбавка = 0 євро знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 41 % |
Подружжя з двома дітьми та річним доходом 30 000 євро | Податок = 0 євро Знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 0 % | Податок = 0 євро знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 0 % |
Одинока особа без дітей із річним доходом 200 000 євро | Податок = 64 211 євро знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 45 % | Податок = 64 210 євро Надбавка = 7498 євро знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 45 % |
Подружжя з трьома дітьми та річним доходом 200 000 євро | Податок = 42 843 євро Знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 41 % | Податок = 42 842 євро Надбавка = 17 283 євро знижка = 0 євро Знижка = 0 євро Ставка оподаткування = 41 % |
У наведеному вище прикладі надбавкою називають суму, яку додатково сплачують особи з високими доходами через два фактори:
- обмеження розміру податкової пільги 10 % від річного доходу;
- обмеження сімейного коефіцієнта;
Цей показник не вдалося перевірити, оскільки симулятор податкової адміністрації його не надає.
Видно, що алгоритм, наведений у документі, щоразу обчислює правильну суму податку, однак із похибкою в 1 євро. Ця похибка зумовлена округленням. Усі суми іноді округлюються до вищого, іноді — до нижчого євро. Оскільки я не знав офіційних правил, грошові суми в алгоритмі документа були округлені:
- до вищого євро — для знижок та пільг;
- до нижчого євро — для надбавок та остаточного податку;
Ми розробимо кілька версій програми для розрахунку податку.
8.2. Версія 1

8.2.1. Головний скрипт
Ми представляємо першу програму, в якій:
- дані, необхідні для розрахунку податку, жорстко задані в коді у вигляді списків та констант;
- дані про платників податків (сімейний стан, діти, заробітна плата) містяться у першому текстовому файлі [taxpayersdata.txt];
- результати розрахунку податку (статус у шлюбі, діти, заробітна плата, податок) зберігаються у другому текстовому файлі [résultats.txt];
Скрипт [v-01/main.py] має такий вигляд:
# модулі
import sys
from impots.v01.shared.impôts_module_01 import *
# main -----------------------
# константи
# файл платників податків
DATA = "./data/taxpayersdata.txt"
# файл результатів
RESULTATS = "./data/résultats.txt"
try:
# читання даних про платників податків
tax_payers = get_taxpayers_data(DATA)
# список результатів
results = []
# розрахунок податку платників податків
for tax_payer in tax_payers:
# розрахунок податку повертає словник ключів
# ['marié', 'enfants', 'salaire', 'impôt', 'surcôte', 'décôte', 'réduction', 'taux']
result = calcul_impôt(tax_payer['marié'], tax_payer['enfants'], tax_payer['salaire'])
# словник додано до списку результатів
results.append(result)
# результати зберігаються
record_results(RESULTATS, results)
except BaseException as erreur:
# можуть виникнути різні помилки: відсутність файлу, неправильний вміст файлу
# виводиться повідомлення про помилку та закривається програма
print(f"l'erreur suivante s'est produite : {erreur}]\n")
sys.exit()
Примітки
- рядок 4: використовується модуль [impots.v01.modules.impôts_module_01]. Нагадуємо, що цей шлях вимірюється від кореневого каталогу проєкту PyCharm;
- рядок 10: файл [data/taxpayersdata.txt] має такий вигляд:
Кожен рядок представляє кортеж із трьох елементів [marié / pacsé ou pas, nombre d'enfants, salaire annuel en euros].
- рядок 12: файл, у який будуть записані результати розрахунку податку для кожного з платників податків із файлу [taxpayersdata.txt]. Він матиме такий вміст:
- рядок 16: витягуються дані про платників податків, що містяться у файлі [taxpayersdata.txt]. Витягується список словників ключів [marié, enfants, salaire], кожен словник представляє одного платника податків;
- рядки 17–25: обчислюється податок платників податків зі списку [taxPayers]. Отримується список [results], кожен елемент якого знову є словником ключів [marié, enfants, salaire, impôt, surcôte, décôte, réduction, taux];
- рядок 27: список результатів [results] записується у файл [résultats.txt] у формі, показаній вище;
- рядки 28–32: перехоплюються всі винятки, які можуть виникнути в модулі [impots.v01.modules.impôts_module_01];
Тепер детально розглянемо три функції, які використовує скрипт [main]:
- [get_taxpayers_data]: для зчитування даних про платників податків;
- [calcul_impôt]: для розрахунку податку платників;
- [record_results]: для запису результатів у текстовий файл;
Усі ці функції містяться в модулі [impots.modules.impôts_module_01].
8.2.2. Модуль [impots.v01.shared.impôts_module_01]
Функції, необхідні для розрахунку податку, зібрано в модулі [impots.v01.shared.impôts_module_01]:

- у [1]: визначення констант для розрахунку податку;
- у [2] — перелік функцій модуля;
8.2.3. Функція [get_taxpayers_data]
Функція [get_taxpayers_data] має такий вигляд:
# імпорт
import codecs
…
# зчитування даних платників податків
# ----------------------------------------
def get_taxpayers_data(taxpayers_filename: str) -> list:
# читання даних платників податків
file = None
try:
# список платників податків
taxpayers = []
# відкриття файлу
file = codecs.open(taxpayers_filename, "r", "utf8")
# зчитування першого рядка файлу платників податків
ligne = file.readline().strip()
# поки залишається хоча б один рядок для обробки
while ligne != '':
# витягуються 3 поля «одружений», «діти», «зарплата», що складають цей рядок
(marié, enfants, salaire) = ligne.split(",")
# додаємо їх до списку платників податків
taxpayers.append({'marié': marié.strip().lower(), 'enfants': int(enfants), 'salaire': int(salaire)})
# зчитуємо новий рядок з файлу платників податків
ligne = file.readline().strip()
# виводимо результат
return taxpayers
finally:
# закриваємо файл, якщо він був відкритий
if file:
file.close()
Примітки
- рядок 7: [taxpayers_filename] — це ім’я файлу, що обробляється. Функція повертає список;
- рядки 18–24: цикл обробки рядків [marié, enfants, salaire] з текстового файлу;
- рядок 20: витягуються три елементи рядка. Тут припускається, що рядок є синтаксично правильним, тобто містить саме ті три очікувані елементи;
- рядок 22: створюється словник із ключами [marié, enfants, salaire], і цей словник додається до списку [taxPayers];
- рядок 26: після обробки файлу повертається список [taxPayers];
- рядки 10–30: зверніть увагу, що ми не додали умову [catch] до [try] у рядку 10. Умова [catch] не є обов’язковою. У рядку 27 додано оператор [finally] для закриття текстового файлу в будь-якому випадку, незалежно від того, чи сталася помилка;
- ця структура try / finally пропускає можливе виключення (немає catch). Це виключення буде передано до головного скрипта [main], який зупиниться та відобразить виключення (див. параграф |Головний скрипт|). Цей механізм було використано для більшості функцій модуля;
8.2.4. Функція [calcul_impôt]
Функція [calcul_impôt] має такий вигляд:
# імпорт
import codecs
import math
# податкові шкали за 2019 рік
limites = [9964, 27519, 73779, 156244, 0]
coeffr = [0, 0.14, 0.3, 0.41, 0.45]
coeffn = [0, 1394.96, 5798, 13913.69, 20163.45]
# константи для розрахунку податку за 2019 рік
PLAFOND_QF_DEMI_PART = 1551
PLAFOND_REVENUS_CELIBATAIRE_POUR_REDUCTION = 21037
PLAFOND_REVENUS_COUPLE_POUR_REDUCTION = 42074
VALEUR_REDUC_DEMI_PART = 3797
PLAFOND_DECOTE_CELIBATAIRE = 1196
PLAFOND_DECOTE_COUPLE = 1970
PLAFOND_IMPOT_COUPLE_POUR_DECOTE = 2627
PLAFOND_IMPOT_CELIBATAIRE_POUR_DECOTE = 1595
ABATTEMENT_DIXPOURCENT_MAX = 12502
ABATTEMENT_DIXPOURCENT_MIN = 437
…
# розрахунок податку
# ----------------------------------------
def calcul_impôt(marié: str, enfants: int, salaire: int) -> dict:
# одружений: так, ні
# діти: кількість дітей
# зарплата: річна зарплата
# ліміти, коефіцієнт, коефіцієнт: таблиці даних, що дозволяють розрахувати податок
#
# розрахунок податку з урахуванням дітей
result1 = calcul_impôt_2(marié, enfants, salaire)
impot1 = result1["impôt"]
# розрахунок податку без урахування дітей
if enfants != 0:
result2 = calcul_impôt_2(marié, 0, salaire)
impot2 = result2["impôt"]
# застосування обмеження сімейного коефіцієнта
if enfants < 3:
# PLAFOND_QF_DEMI_PART євро для перших двох дітей
impot2 = impot2 - enfants * PLAFOND_QF_DEMI_PART
else:
# PLAFOND_QF_DEMI_PART євро за перших двох дітей, удвічі більше — за наступних
impot2 = impot2 - 2 * PLAFOND_QF_DEMI_PART - (enfants - 2) * 2 * PLAFOND_QF_DEMI_PART
else:
impot2 = impot1
result2 = result1
# береться найвищий податок із відповідною ставкою та надбавкою
if impot1 > impot2:
impot = impot1
taux = result1["taux"]
surcôte = result1["surcôte"]
else:
surcôte = impot2 - impot1 + result2["surcôte"]
impot = impot2
taux = result2["taux"]
# розрахунок можливого зниження
décôte = get_décôte(marié, salaire, impot)
impot -= décôte
# розрахунок можливого зменшення податку
réduction = get_réduction(marié, salaire, enfants, impot)
impot -= réduction
# результат
return {"marié": marié, "enfants": enfants, "salaire": salaire, "impôt": math.floor(impot), "surcôte": surcôte,
"décôte": décôte, "réduction": réduction, "taux": taux}
Примітки
- рядки 6–8: податкові шкали (див. розділ |Розрахунок валового податку|);
- рядки 11–20: константи для розрахунку податку;
- варто зауважити, що елементи, ініціалізовані у рядках 5–20, будуть глобальними для функцій, які ми опишемо. Отже, вони залишаються відомими, доки функція, яка їх використовує, не оголошує змінних з такими самими іменами;
- цифри в рядках 5–20 змінюються щороку. Тут наведено дані за 2019 рік;
- рядок 25: функція [calcul_impôt] приймає три параметри:
- [marié]: так/ні, вказує, чи перебуває платник податків у шлюбі або в цивільному партнерстві;
- [enfants]: кількість дітей;
- [salaire]: його річний заробіток у євро;
- рядки 31–33: розрахунок податку з урахуванням дітей;
- рядки 34–47: у цих рядках реалізовано обмеження сімейного коефіцієнта (див. розділ |Обмеження сімейного коефіцієнта|);
- рядки 49–57: у цих рядках розраховується ставка оподаткування платника податків, а також можлива надбавка (див. параграф |Випадки високих доходів|);
- рядки 59–61: розрахунок можливої знижки (див. розділ |Розрахунок знижки|);
- рядки 62–64: розрахунок можливого зменшення суми податку до сплати (див. розділ |Розрахунок зменшення податку|);
Алгоритм є досить складним, і ми не будемо детально його описувати, окрім того, що зазначено в коментарях. Алгоритм реалізує спосіб розрахунку податку, описаний у розділі |Проблема|.
8.2.5. Функція [calcul_impôt_2]
Функція [calcul_impôt] викликає наступну функцію [calcul_impôt_2]:
def calcul_impôt_2(marié: str, enfants: int, salaire: int) -> list:
# одружений: так, ні
# діти: кількість дітей
# зарплата: річна зарплата
# ліміти, коефіцієнт, коефіцієнт: таблиці даних, що дозволяють розрахувати податок
#
# кількість часток
marié = marié.strip().lower()
if marié == "oui":
nb_parts = enfants / 2 + 2
else:
nb_parts = enfants / 2 + 1
# 1 частка на дитину, починаючи з третьої
if enfants >= 3:
# півчастки додатково за кожну дитину, починаючи з третьої
nb_parts += 0.5 * (enfants - 2)
# оподатковуваний дохід
revenu_imposable = get_revenu_imposable(salaire)
# надбавка
surcôte = math.floor(revenu_imposable - 0.9 * salaire)
# для виправлення округлень
if surcôte < 0:
surcôte = 0
# сімейний коефіцієнт
quotient = revenu_imposable / nb_parts
# встановлюється в кінці таблиці обмежень для зупинки наступного циклу
limites[len(limites) - 1] = quotient
# розрахунок податку
i = 0
while quotient > limites[i]:
i += 1
# оскільки коефіцієнт розміщено в кінці таблиці обмежень, попередній цикл
# не може виходити за межі таблиці обмежень
# тепер можна обчислити податок
impôt = math.floor(revenu_imposable * coeffr[i] - nb_parts * coeffn[i])
# результат
return {"impôt": impôt, "surcôte": surcôte, "taux": coeffr[i]}
Цей алгоритм описано в розділі 8.1.1.
8.2.6. Функція [get_décôte]
Функція [get_décôte] реалізує обчислення можливої знижки з податку (розділ |Обчислення знижки|):
# розраховує можливу знижку
def get_décôte(marié: str, salaire: int, impots: int) -> int:
# спочатку знижка дорівнює нулю
décôte = 0
# максимальна сума податку для отримання знижки
plafond_impôt_pour_décôte = PLAFOND_IMPOT_COUPLE_POUR_DECOTE if marié == "oui" else PLAFOND_IMPOT_CELIBATAIRE_POUR_DECOTE
if impots < plafond_impôt_pour_décôte:
# максимальна сума знижки
plafond_décôte = PLAFOND_DECOTE_COUPLE if marié == "oui" else PLAFOND_DECOTE_CELIBATAIRE
# теоретична знижка
décôte = plafond_décôte - 0.75 * impots
# знижка не може перевищувати суму податку
if décôte > impots:
décôte = impots
# знижка <0
if décôte < 0:
décôte = 0
# результат
return math.ceil(décôte)
8.2.7. Функція [get_réduction]
Функція [get_réduction] реалізує розрахунок можливого зменшення суми податку до сплати (розділ |Розрахунок зменшення податку|):
# розраховує можливе зниження
def get_réduction(marié: str, salaire: int, enfants: int, impots: int) -> int:
# максимальний рівень доходу для отримання права на знижку в розмірі 20 %
plafond_revenu_pour_réduction = PLAFOND_REVENUS_COUPLE_POUR_REDUCTION if marié == "oui" else PLAFOND_REVENUS_CELIBATAIRE_POUR_REDUCTION
plafond_revenu_pour_réduction += enfants * VALEUR_REDUC_DEMI_PART
if enfants > 2:
plafond_revenu_pour_réduction += (enfants - 2) * VALEUR_REDUC_DEMI_PART
# оподатковуваний дохід
revenu_imposable = get_revenu_imposable(salaire)
# знижка
réduction = 0
if revenu_imposable < plafond_revenu_pour_réduction:
# знижка у розмірі 20 %
réduction = 0.2 * impots
# результат
return math.ceil(réduction)
8.2.8. Функція [get_revenu_imposable]
Функція [get_revenu_imposable] розраховує оподатковуваний дохід на основі річної заробітної плати:
# revenu_imposable = salaireAnnuel — податкова пільга
# знижка має мінімальний та максимальний розмір
# ----------------------------------------
def get_revenu_imposable(salaire: int) -> int:
# знижка у розмірі 10 % від заробітної плати
abattement = 0.1 * salaire
# ця знижка не може перевищувати ABATTEMENT_DIXPOURCENT_MAX
if abattement > ABATTEMENT_DIXPOURCENT_MAX:
abattement = ABATTEMENT_DIXPOURCENT_MAX
# знижка не може бути меншою за ABATTEMENT_DIXPOURCENT_MIN
if abattement < ABATTEMENT_DIXPOURCENT_MIN:
abattement = ABATTEMENT_DIXPOURCENT_MIN
# оподатковуваний дохід
revenu_imposable = salaire - abattement
# результат
return math.floor(revenu_imposable)
8.2.9. Функція [record_results]
Функція [record_results] записує результати розрахунку податку у текстовий файл:
# запис результатів у текстовий файл
# ----------------------------------------
def record_results(results_filename: str, results: list):
# results_filename: ім’я текстового файлу, куди слід записати результати
# results: список результатів у вигляді списку словників
# кожен словник записується в окремому рядку тексту
résultats = None
try:
# відкриття файлу з результатами
résultats = codecs.open(results_filename, "w", "utf8")
# обробка даних
for result in results:
# запис результату у файл результатів
résultats.write(f"{result}\n")
# наступний платник податків
finally:
# закриття файлу, якщо він був відкритий
if résultats:
résultats.close()
8.2.10. Результати
Як уже зазначалося, за допомогою такого файлу платників податків [taxpayersdata.txt]:
скрипт [main.py] створює такий файл [résultats.txt]:
Ці результати відповідають офіційним даним, наведеним у розділі |Офіційні дані|.
Тепер запустимо цю версію у вікні консолі:
(venv) C:\Data\st-2020\dev\python\cours-2020\python3-flask-2020\impots\v01>python main.py
Traceback (most recent call last):
File "main.py", line 4, in <module>
from impots.v01.shared.impôts_module_01 import *
ModuleNotFoundError: No module named 'impots'
Ми знову стикаємося з помилкою, яка вже траплялася раніше: модуль не знайдено, у даному випадку — модуль [impots]. Нагадаємо, що це означає:
- інтерпретатор Python по черзі обійшов усі папки в Python Path;
- у жодній з них він не знайшов папки, в якій міг би бути скрипт [impots.py];
Версія [v02] вирішить цю проблему.