Я в основном работаю с Python и почти ежедневно проверяю код. В нашей кодовой базе форматирование и линтинг выполняются заданиями CI с использованием black и mypy. Итак, мы фокусируемся только на изменениях.
Работая в команде, ты уже знаешь, какой код ожидать от конкретного члена команды. Обзоры кода становятся интересными, когда к команде присоединяется новый человек. Я говорю «интересно», поскольку у каждого есть какой-то стиль кодирования, который они используют бессознательно; в хорошую или плохую сторону! Как будто у меня есть немного,
# I used (long back) to do def func(a: int, b: Optional[list] = None, c: Optional[Dict] = None): if b is None: b = [] if c is None: c = {} # Instead I do def func(a: int, b: Optional[list] = None, c: Optional[Dict] = None): b = b or [] c = c or {}
Это простой вариант использования, когда вы возвращаете строку или вызываете функцию на основе некоторого значения.
Примечание: начиная с версии 3.10 вместо этого следует использовать match.
def get_number_of_wheels(vehicle: str): if vehicle == "car": wheels = 2 elif vehicle == "bus": wheels = 6 elif vehicle == "bicycle": wheels = 2 else: raise ... # I prefer doing, def get_number_of_wheels(vehicle: str): return { "car": 2, "bus": 6, "bicycle": 2 }[vehicle] # Raise is now KeyError
Выше приведено несколько примеров. Люди, просматривающие мой код, найдут еще примеры.
Недавно к моей команде присоединился новый разработчик, и я заметил шаблон, который мне понравился, но я попросил изменить его на простой случай if...else. Сначала я покажу вам схему, а затем объясню причину, по которой я прошу внести изменения.
Код представляет собой декоратор, который что-то делает с параметрами. Давайте напишем простой (бесполезный) декоратор, который будет печатать количество аргументов и kwargs, с помощью которых была вызвана функция/метод.
def counter(is_cls_method: bool = False): """ print number of args & kwargs for func/method """ def outer(f): def inner(*args, **kwargs): args_cnt = len(args) kwargs_cnt = len(kwargs) print(f"{f.__name__} called with {args_cnt=} & {kwargs_cnt=}") return f(*args, **kwargs) return inner return outer @counter() def test1(a, b, c): pass class A: @counter(is_cls_method=True) def test1(self, a, b, c): pass print("function") test1(1, 2, c=3) test1(a=1, b=2, c=3) print("method") a = A() a.test1(1, 2, 3) a.test1(1, b=2, c=3)
При запуске этого кода вы должны увидеть
function test1 called with args_cnt=2 & kwargs_cnt=1 test1 called with args_cnt=0 & kwargs_cnt=3 method test1 called with args_cnt=4 & kwargs_cnt=0 test1 called with args_cnt=2 & kwargs_cnt=2
Он работает нормально, но для методов он также считает себя. так что давай это исправим!
def counter(is_cls_method: bool = False): def outer(f): def inner(*args, **kwargs): args_cnt = len(args) if is_cls_method: # Check added args_cnt -= 1 # Reduced count by 1 kwargs_cnt = len(kwargs) print(f"{f.__name__} called with {args_cnt=} & {kwargs_cnt=}") return f(*args, **kwargs) return inner return outer
Это простое предложение if, но новый разработчик сделал что-то еще, интересное использование логического значения.
Я показываю только измененный код...
args_cnt = len(args[is_cls_method:])
Решение намного лучше, чем использование if, поскольку bool в Python — это просто int. Исходный код был немного длиннее, и заметить это небольшое изменение неочевидно, а также базу кода, используемую пользователями, которые являются базовыми пользователями Python. И если вам нужно угадать, что делает строка, я думаю, вам следует изменить ее, чтобы сделать это очевидным.
Что вы думаете по этому поводу? Используете ли вы логическое значение в качестве индекса?
Есть ли у вас еще подобные шаблоны Python?
Отказ от ответственности: Все предоставленные ресурсы частично взяты из Интернета. В случае нарушения ваших авторских прав или других прав и интересов, пожалуйста, объясните подробные причины и предоставьте доказательства авторских прав или прав и интересов, а затем отправьте их по электронной почте: [email protected]. Мы сделаем это за вас как можно скорее.
Copyright© 2022 湘ICP备2022001581号-3