2012-07-30 25 views
17

想象的目錄結構:默認情況下,python27中的導入不應該是絕對的嗎?

 
/
    a/ 
     __init__.py 
     b.py 
     c.py 
    c.py 

文件/a/b.py樣子:

 
import c 
should_be_absolute = c 

所有其他文件(包括__init__)是空的。

當運行一個測試腳本(使用Python 2.7):按照這裏從一個空目錄(所以沒有什麼是從當前目錄添加到PYTHONPATH)我得到

<module 'a.c' from '/a/c.py'> 

import a.b 
print a.b.should_be_absolute 

PYTHONPATH=/PEP 328和聲明import <> is always absolute我期望:

<module 'c' from '/c.py'> 

當我刪除/a/c.py文件時,輸出與預期一致。

我錯過了什麼?如果這是正確的行爲 - 如何從b(而不是a.c)導入c模塊?

更新:

根據python dev mailing list它似乎是在文檔中的錯誤。默認情況下,python27中的進口是而不是

+0

什麼是你完整的pythonpath?它只是/?你可能應該使用一個根包名稱 – jdi 2012-07-30 17:43:22

+3

FWIW,這可以像Python 3期望的那樣工作。 – geoffspear 2012-07-30 17:50:22

+0

@jdi - 是根是PYTHONPATH中唯一的東西(編輯原始文章使其更加明確) – karolx 2012-07-31 08:44:20

回答

26

您需要添加from __future__ import absolute_import或Python的2.7

使用importlib.import_module('c')這是默認的Python的3。

Python中存在一個錯誤:__future__.py and its documentation claim absolute imports became mandatory in 2.7, but they didn't

+2

你是對的!進一步挖掘後,我找到了[python-dev mailing list]的鏈接(http://python.6.n6.nabble.com/status-of-absolute-import-w-python-2-7-td1850742.html )確認python27中的absolute_import功能默認沒有打開。 – karolx 2012-07-31 14:58:17

+0

那種可笑... – 2015-12-10 15:48:11

0

如果您只是將/添加到您的PYTHONPATH中,那麼搜索順序仍然可以在當前目錄中查找c。這將是好了很多,如果你把一切事情都根包下,絕對稱它:

/myPackage 
    a/ 
     __init__.py 
     b.py 
     c.py 
    __init__.py 
    c.py 

並有PYTHONPATH,如:export PYTHONPATH=/:$PYTHONPATH

因此,在您a.c你會做和這些:

from myPackage import c 
from myPackage.c import Foo 
import myPackage.c 

這樣,它總是相對於你的包。

+0

謝謝,但是問題更多的是這是一種正確的行爲,而不是如何重組代碼來使其工作。我正在解決的實際問題是'c'是python內建模塊的名稱,我正在工作的軟件包中的代碼隱藏了它(並且根據python文檔不應該這樣做) – karolx 2012-07-31 08:42:17

-1

「絕對」並不意味着你認爲它的作用;相反,這意味着「通常」包解析過程發生:首先,它查看包的目錄,然後查找sys.path的所有元素;其中包括來自PYTHONPATH的元素。

如果你真的想要,你可以使用像imp模塊這樣的工具,但我建議不要這樣的東西。因爲一般來說,你不應該創建一個與標準Python發行版同名的模塊。

+0

Thanks @Ivo但[PEP 328#絕對進口原理](http://www.python.org/dev/peps/pep-0328/#rationale-for-absolute-imports)聲明絕對導入_will總是從sys.path_可訪問的模塊或程序包。沒有關於軟件包目錄中的查找。你能指出一些記錄你描述的行爲的資源嗎? – karolx 2012-07-31 10:42:31

+0

http://docs.python.org/reference/simple_stmts.html#import在執行過程中非常清晰:「如果被導入的模塊應該包含在一個包中,那麼第二個參數將傳遞給find_module (),父包上的__path__被用作路徑的來源。「 – Ivo 2012-07-31 13:28:07

+0

「首先,它在包的目錄中查找」。不,這是相對的進口。 – 2013-04-23 23:12:45

相關問題