Как изменить имя модуля Python?

Это возможно, только если я переименую файл? Или в файле есть переменная __module__, чтобы определить его имя?


person Rodrigo    schedule 26.02.2009    source источник
comment
В чем проблема переименовать файл? Почему не работает переименование?   -  person S.Lott    schedule 26.02.2009
comment
Собственно, просто лень... Не хотелось удалять и снова добавлять файл на Launchpad.   -  person Rodrigo    schedule 26.02.2009


Ответы (8)


Да, вы должны переименовать файл. Лучше всего после того, как вы это сделаете, удалить oldname.pyc и oldname.pyo скомпилированные файлы (если они есть) из вашей системы, иначе модуль можно будет импортировать и под старым именем.

person theller    schedule 26.02.2009

Если вы действительно хотите импортировать файл 'oldname.py' с оператором 'import newname', есть трюк, который делает это возможным: импортируйте модуль куда-нибудь со старым именем, а затем внедрите его в sys.modules с новым именем. Последующие операторы импорта также найдут его под новым именем. Пример кода:

# this is in file 'oldname.py'
...module code...

Использование:

# inject the 'oldname' module with a new name
import oldname
import sys
sys.modules['newname'] = oldname

Теперь вы можете везде использовать свой модуль с import newname.

person theller    schedule 26.02.2009
comment
Я не могу придумать ситуацию, в которой я хотел бы это сделать, но здорово, что вы можете :) - person technomalogical; 26.02.2009
comment
Одна ситуация: проект, в котором вам нужна совместимость как с Python 2.6, так и с 2.7, но вы хотите использовать некоторые новые функции unittest 2.7. Этот трюк позволяет нам просто использовать код `import unittest', сохраняя при этом новую функциональность, поэтому нам не нужно каждый раз изменять кучу операторов импорта при переключении версии Python. - person Tobi; 15.09.2010
comment
Отлично. пример: import tensorflow.keras as tf_keras import sys sys.modules['tf_keras'] = keras Тогда вы сможете использовать примеры keras с версией keras для tensorflow - person liangbright; 26.04.2019
comment
Я хочу, чтобы это было применено к такому примеру: у меня есть модуль pname, и я разработал модифицированный модуль pname_dev. В работающем скрипте я хочу переключить import pname или pname_dev для любой ситуации, и скрипт использует много строк import pname.util.a, import pname.analysis.run.... Затем, вместо того, чтобы изменять все строки pname, Я просто хочу изменить исходный модуль на pname_orig, а затем позволить pname выборочно указать pname_orig или pname_dev. Я ожидаю, что это сработает для него. - person Joonho Park; 31.07.2020

Вы можете изменить имя, используемое для модуля при импорте, используя as:

import foo as bar
print bar.baz
person Ignacio Vazquez-Abrams    schedule 26.02.2009

Когда вы делаете import module_name, интерпретатор Python ищет файл module_name.extension в PYTHONPATH. Таким образом, это имя нельзя изменить без изменения имени файла. Но, конечно, вы можете сделать:

import module_name as new_module_name

или даже

import module_name.submodule.subsubmodule as short_name

Полезно напр. для написания кода БД.

import sqlite3 as sql
sql.whatever..

А затем переключиться, например. sqlite3 на pysqlite вы просто меняете строку импорта

person vartec    schedule 26.02.2009

У каждого класса есть свойство __module__, хотя я считаю, что его изменение не изменит пространство имен класса.

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

Лучше всего переименовать файл.

person toothygoose    schedule 26.02.2009

Где бы вы хотели иметь эту переменную __module__, чтобы ваш исходный скрипт знал, что импортировать? Модули распознаются по именам файлов и просматриваются по путям, определенным в переменной sys.path.

Итак, вам нужно переименовать файл, а затем удалить oldname.pyc, просто чтобы убедиться, что все работает правильно.

person kender    schedule 26.02.2009

У меня была такая проблема с bsddb. Мне пришлось установить модуль bsddb3, но сотни скриптов импортировали bsddb. Вместо того, чтобы изменить импорт во всех них, я извлек яйцо bsddb3 и создал программную ссылку в каталоге пакетов сайта, чтобы и «bsddb», и «bsddb3» были одним и тем же для python.

person Marty    schedule 20.11.2013

Вы можете установить модуль с помощью атрибута module, как показано ниже.

func.__module__ = module

Вы даже можете создать декоратор, чтобы изменить имена модулей для определенных функций в файле, например:

def set_module(module):
    """Decorator for overriding __module__ on a function or class.
    Example usage::
        @set_module('numpy')
        def example():
            pass
        assert example.__module__ == 'numpy'
    """
    def decorator(func):
        if module is not None:
            func.__module__ = module
        return func
    return 

а затем использовать

@set_module('my_module')
def some_func(...):

Обратите внимание, так как этот декоратор предназначен для изменения имен отдельных модулей для функций.

Этот пример взят из исходного кода numpy: https://github.com/numpy/numpy/blob/0721406ede8b983b8689d8b70556499fc2aea28a/numpy/core/numeric.py#L289

person Yigit Alparslan    schedule 02.03.2021