PEP 8 говорит:
- Импорты всегда помещаются в начало файла, сразу после любых комментариев и строк документации, а также перед глобальными переменными и константами модуля.
Иногда я нарушаю PEP 8. Иногда я импортирую что-то внутри функций. Как правило, я делаю это, если есть импорт, который используется только в одной функции.
Есть мнения?
ИЗМЕНИТЬ (причина, по которой я считаю, что импорт функций может быть хорошей идеей):
Основная причина: это может сделать код более понятным.
- Глядя на код функции, я могу спросить себя: «Что такое функция / класс xxx?» (xxx используется внутри функции). Если у меня есть весь мой импорт в верхней части модуля, я должен пойти посмотреть туда, чтобы определить, что такое xxx. Это больше проблема при использовании
from m import xxx
. Просмотрm.xxx
функции, вероятно, говорит мне больше. В зависимости от того, чтоm
это: хорошо известный модуль верхнего уровня / package (import m
)? Или это подмодуль / пакет (from a.b.c import m
)? - В некоторых случаях наличие этой дополнительной информации («Что такое xxx?») Рядом с тем, где используется xxx, может облегчить понимание функции.
python
conventions
codeape
источник
источник
Ответы:
В конечном итоге, я думаю, вы оцените то, что большая часть вашего импорта находится в верхней части файла, таким образом вы можете сразу определить, насколько сложен ваш модуль по тому, что ему нужно импортировать.
Если я добавляю новый код в существующий файл, я обычно выполняю импорт там, где он нужен, а затем, если код остается, я делаю вещи более постоянными, перемещая строку импорта в верхнюю часть файла.
Еще один момент: я предпочитаю получать
ImportError
исключение перед запуском любого кода - в качестве проверки работоспособности, так что это еще одна причина для импорта вверху.Использую
pyChecker
для проверки неиспользуемых модулей.источник
Я нарушаю PEP 8 в двух случаях:
import pdb; pdb.set_trace()
это удобно, b / c я не хочу помещатьimport pdb
вверху каждого модуля, который я мог бы захотеть отладить, и легко не забыть удалить импорт, когда я удаляю точку останова.За пределами этих двух случаев рекомендуется размещать все наверху. Это делает зависимости более понятными.
источник
Вот четыре варианта использования импорта, которые мы используем
import
(иfrom x import y
иimport x as y
) в верхнейВыбор для импорта. На вершине.
Условный импорт. Используется с библиотеками JSON, XML и т. Д. На вершине.
Динамический импорт. Пока что у нас есть только один пример этого.
Обратите внимание, что этот динамический импорт не вводит код, но вводит сложные структуры данных, написанные на Python. Это что-то вроде маринованного фрагмента данных, за исключением того, что мы собирали его вручную.
Это также более или менее находится в верхней части модуля.
Вот что мы делаем, чтобы код был понятнее:
Модули должны быть короткими.
Если у меня есть весь мой импорт в верхней части модуля, я должен пойти посмотреть туда, чтобы определить, что это за имя. Если модуль короткий, это легко сделать.
В некоторых случаях наличие этой дополнительной информации рядом с тем, где используется имя, может облегчить понимание функции. Если модуль короткий, это легко сделать.
источник
Следует помнить об одном: ненужный импорт может вызвать проблемы с производительностью. Так что, если эта функция будет вызываться часто, вам лучше просто поместить импорт вверху. Конечно , это является оптимизацией, так что если есть действительный случай , который будет сделано , что импорт внутри функции является более ясным , чем импорт в верхней части файла, что козыри производительности в большинстве случаев.
Если вы используете IronPython, мне сказали, что лучше импортировать внутренние функции (поскольку компиляция кода в IronPython может быть медленной). Таким образом, вы можете получить способ импорта внутренних функций. Но кроме этого, я бы сказал, что бороться с условностями просто не стоит.
Еще я хотел бы отметить, что это может быть потенциальной проблемой обслуживания. Что произойдет, если вы добавите функцию, которая использует модуль, который ранее использовался только одной функцией? Не забудьте добавить импорт в начало файла? Или вы собираетесь сканировать каждую функцию на предмет импорта?
FWIW, бывают случаи, когда имеет смысл импортировать внутри функции. Например, если вы хотите установить язык в cx_Oracle, вам необходимо установить
_
переменную среды NLS LANG перед ее импортом. Таким образом, вы можете увидеть такой код:источник
Я уже нарушал это правило для модулей, которые проходят самотестирование. То есть они обычно используются только для поддержки, но я определяю для них основную, так что если вы запустите их сами по себе, вы можете проверить их функциональность. В этом случае я иногда импортирую
getopt
иcmd
просто в основном, потому что я хочу, чтобы кто-то, читающий код, понял, что эти модули не имеют ничего общего с нормальной работой модуля и включаются только для тестирования.источник
Исходя из вопроса о загрузке модуля дважды - а почему не оба?
Импорт в верхней части скрипта укажет зависимости и другой импорт в функции, сделав эту функцию более атомарной, при этом, по-видимому, не вызовет какого-либо снижения производительности, поскольку последовательный импорт дешев.
источник
Пока это
import
и неfrom x import *
, вы должны поместить их вверху. Он добавляет только одно имя в глобальное пространство имен, и вы придерживаетесь PEP 8. Плюс, если оно вам позже понадобится в другом месте, вам не нужно ничего перемещать.В этом нет ничего страшного, но поскольку разницы почти нет, я предлагаю делать то, что говорит PEP 8.
источник
from x import *
функции внутри функции вызовет SyntaxWarning, по крайней мере, в 2.5.Взгляните на альтернативный подход, который используется в sqlalchemy: внедрение зависимости:
Обратите внимание, как импортированная библиотека объявляется в декораторе и передается в качестве аргумента функции !
Такой подход делает код чище, а также работает в 4,5 раза быстрее, чем
import
оператор!Тест: https://gist.github.com/kolypto/589e84fbcfb6312532658df2fabdb796
источник
В модулях, которые являются «обычными» модулями и могут выполняться (т.е. имеют
if __name__ == '__main__':
Е. -секцию), я обычно импортирую модули, которые используются только при выполнении модуля внутри основного раздела.Пример:
источник
Есть еще один (вероятно, «угловой») случай, когда это может быть полезно для
import
внутренних редко используемых функций: сокращение времени запуска.Однажды я столкнулся с этой проблемой, когда на небольшом IoT-сервере работала довольно сложная программа, которая принимает команды из последовательной линии и выполняет операции, возможно, очень сложные.
Размещение
import
операторов в верхней части файлов означает, что все импорт будет обработан до запуска сервера; посколькуimport
список включеныjinja2
,lxml
,signxml
и другие «тяжелые веса» (и SoC был не очень мощным) это означало минут до первой команды была фактически выполнены.OTOH разместил большую часть импорта в функциях, и мне удалось подключить сервер к последовательной линии за секунды. Конечно, когда модули были действительно необходимы, мне пришлось заплатить цену (Примечание: также это можно смягчить, создав фоновую задачу, выполняющую
import
s во время простоя).источник