Проверка правильности аргументов функции в Python: должна ли каждая функция делать это? - PullRequest
0 голосов
/ 31 октября 2018

Должна ли каждая функция (или метод) Python проверять правильность своих аргументов?

Не только тип, но если значения находятся в допустимых пределах, размеры соответствуют ожидаемым, и т. Д.

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

В случае с "приватными" методами мне кажется, что нам не нужно проверять правильность, но как насчет других методов / функций?

Если мы будем слишком строги к этому и проверим все, разве код не будет полон скучного кода типа декоратора? Это нормально?

Ответы [ 3 ]

0 голосов
/ 31 октября 2018

Я видел много разных подходов. Наиболее экстремальным было то, что строки документов содержали формальное объявление типов параметров и диапазонов (также возвращаемых значений). Приложение проверило параметры во время выполнения на основе этих строк документации и выдало исключение, если с ними что-то не так. Это было реализовано с использованием метапрограммирования и может быть отключено для производственных циклов.

Это был уже не Python, дафттип тоже был невозможен. Это было больше похоже на статически типизированный язык без помощи компилятора. Вы все еще должны были ждать, пока он не сломается во время выполнения.

Я также видел приложения, которые не выполняют никаких проверок и просто запускают комплексные модульные тесты . Если они проходят, предполагается, что параметры также в порядке.

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

Надеюсь, это поможет

0 голосов
/ 31 октября 2018

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

0 голосов
/ 31 октября 2018

Python рекомендует печатать на утках или «проще просить прощения, чем разрешения» (EAFP), что означает, что вы должны полагать, что ваши аргументы верны, а если нет, обрабатывать ситуацию надлежащим образом.

Мы предполагаем, что «если он ходит и говорит как утка, значит, это утка». Смотрите здесь:

class Duck:
    def quack(self):
        return 'quack!'

class Person:
    def quack(self):
        return 'Hey there!'

d = Duck()
p = Person()

def make_it_quack(duck):
    return duck.quack()

print(make_it_quack(d))
print(make_it_quack(p))

Как видите, оба типа работают. Это намеренное поведение. Если вы столкнетесь с чем-то, что не определяет этот метод, вы получите AttributeError, как и ожидалось. Чтобы обойти это, используйте обработку исключений:

try:
   print(make_it_quack(d))
    print(make_it_quack(p))
    print(make_it_quack('hello world'))
except AttributeError:
    print('object must have a "quack" method')

Сказав все это, я лично не всегда придерживаюсь этого. Например, если я не могу гарантировать типы моих объектов, я буду использовать такие вещи, как if isinstance(x, Y), чтобы правильно направлять код. Если нет, то он возвращается к try except.

Вам решать, какой из них сделает ваш код чище и соответствует ситуации. Есть рекомендации по этому поводу, такие как «всегда использовать попытку / за исключением ошибок ввода-вывода» (есть причина этого).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...