Как правильно организовать проверку значений функций в коде?

Есть код, который выполняет некоторые математические операции. Нужно проверить как входные данные, которые пользователь задает в функцию, так и выходное значение функции. Но не знаю где будет правильно написать метод проверке, внутри этой функции или же это внешняя функция через которую мы вызываем нужную и проверяем ее значение?

Для примера приведу часть кода:

from dataclasses import dataclass


@dataclass(frozen=True, slots=True)
class CentrifugalLiquidInjector:
    outer_diameter_injector: float
    side_wall_thickness_injector: float
    number_input_tangential_holes: float

    diameter_input_tangential_holes: float
    length_input_tangential_holes: float

    @property
    def diameter_twisting_chamber_injector(self) -> float:
        return self.outer_diameter_injector - 2 * self.side_wall_thickness_injector

    @property
    def relative_length_tangential_hole(self) -> float:
        return self.length_input_tangential_holes / self.diameter_input_tangential_holes

Для примера возьмем функцию relative_length_tangential_hole, ее выходное значение не может выходить за диапазон [1.5; 6.0] и конечно значение входных данных не могут ровняться 0.

Сейчас для отладки запускаю функции так, проверял значение здесь, но показалось не совсем правильным такое решение:

from src.centrifugal_injector_calc import CentrifugalLiquidInjector


def test() -> None:
    common = {
        "outer_diameter_injector": 0,
        "side_wall_thickness_injector": 0,
        "number_input_tangential_holes": 0,
        "diameter_input_tangential_holes": 0,
        "length_input_tangential_holes": 0
    }

    centrifugal = CentrifugalLiquidInjector(
        **common
    )

    print(centrifugal.relative_length_tangential_hole)


if __name__ == '__main__':
    test()

Как правильно организовать проверку значение входных данных функции и ее результат?


Ответы (1 шт):

Автор решения: master_Alish

По моему мнению, лучше для этого не использовать dataclass, а создать просто обычный класс. Так как dataclass предназначен чисто для данных. И желательно функции сделать принимающим также входные параметры.

Валидацию входных значений может делать сама функция, проверяя в самом начале и кидая Exception если они неправильные. Соответственно в нужных местах вы должны ловить эти Exception.

def diameter_twisting_chamber_injector(
    self, outer_diameter_injector: float, side_wall_thickness_injector: float
) -> float:
    if not (1.5 <= outer_diameter_injector <= 6.0):
        raise Exception("bla bla")        

    return outer_diameter_injector - 2 * side_wall_thickness_injector

А валидацию выходных данных лучше делать не в самой функции, или ее вообще не должно быть. Т.е. если у вас формула зависящая от входных данных, то при валидации входных данных, результат всегда должен быть валидним.

Или если все таки результат может стать не валидным, то лучше делать валидацию там, где этот результат используется.

→ Ссылка