2015-12-02 69 views
0

我正在升級一堆腳本,其中的生態系統有點混亂。這些腳本總是依賴於外部模塊,並沒有自己的軟件包基礎設施(他們也沒有做太多的OOP,就像你想象的那樣)。頂層沒有任何東西,但它是啓動Python時的工作目錄,我想保持這種狀態。在頂層,我剛剛創建了__init__.py文件(基於another question)。由於我對Python的經驗不足__init__.py讓我感到困惑。我創建的所有__init__.py文件都是空的,這是我的理解,這是所有必需的。簡單遷移到__init__.py

假設我有以下目錄結構:

__init__.py 
dev.properties 
prod.properties 
F/ 
    Foo.py 
    __init__.py 

B/ 
    bar.py 
    __init__.py 

和代碼是這樣的:

# Foo.py 
    from ..b import bar 
    barFunc() 
# bar.py 
    def barFunc(): 
     print "Hello, World!" 
     sys.stdout.flush() 

我在根目錄中創建__init__.py,在F/B/。然而,當我運行python F/Foo.py,我得到一個錯誤:

Traceback (most recent call last): 
    File "F/Foo.py", line 3, in <module> 
    from ..b import bar 
ValueError: Attempted relative import in non-package 

究竟我需要做的調用python F/Foo.py並能夠依賴於兄弟目錄中定義的東西呢?

更新

感謝@user2455127,我意識到,我忘了刪除的文件擴展名.py和我的工作目錄是錯誤的。從mypackage目錄運行python -m mypackage/F/Foo,錯誤爲:myvirtualenv/bin/python: No module named mypackage/B/bar

重讀@user2455127的帖子,我從上面的目錄中運行,並得到一個長回溯:

Traceback (most recent call last): 
    File "/usr/lib/python2.7/runpy.py", line 162, in _run_module_as_main 
    "__main__", fname, loader, pkg_name) 
    File "/usr/lib/python2.7/runpy.py", line 72, in _run_code 
    exec code in run_globals 
    File "<full path>/mypackage/foo/Foo.py", line 24, in <module> 
    from ..b import bar 
ValueError: Attempted relative import in non-package 

我不太清楚需要做的事情來解決這個東西,但它似乎像__package__屬性可能會有所幫助。我會試着弄清楚,併發布另一個更新。

回答

1

看一看這樣的: Attempted relative import in non-package even with init.py和brenBarn的回答

如果從文件夾不是一個與dev.properties和其他文件(稱爲拉姆達在我的情況),運行上,使用此命令行:

python -m lambda.F.Foo 

它的工作原理。

+0

那麼,你是說你的情況下,'F'上面的目錄叫做'lambda'?模仿,我已經運行'python mypackage/F/Foo.py',但是我得到一個錯誤:'myvirtualenv/bin/python:不支持通過文件名導入。' – blong

+0

是的,但讀取鏈接,你的命令是錯的,看看我的,最後有「-m」選項,沒有「.py」,把它稱爲一個包。 加上我從包含「lambda」的文件夾中調用它 – user2455127

+0

啊,對不起,我確實有'-m'(命令是對的,我的SO評論是錯誤的),但沒有意識到你刪除了'.py'延期。回覆:調用文件夾,我想我已經弄錯了那部分(工作目錄是'mypackage')。 – blong

1

如果當前工作目錄是F和B的父目錄,那麼F和B可作爲所有Python代碼的模塊使用。您應該運行:

$ F/foo.py 

然後F/foo.py應該包含

from B.bar import barFunc 
barFunc() 

至於__init__.py,該文件的所有腦幹只是使目錄中導入的模塊。如果您想了解更多信息,請查看docs on how imports work。 (對於大多數人來說,閱讀所有這些都是不必要的。)

相對進口可能相當混亂,所以我建議現在就回避它們。

+0

啊哈!這爲我解決了! :)這是從'..進口酒吧'線'絆我。現在使用'from B.bar import barFunc',我可以從'F /'和'B /'的父目錄運行'python -m F.Foo'和'python -m F/Foo'。 *但是,目前還不清楚爲什麼上一個目錄並運行'python -m mypackage.F.Foo'(或'python -m mypackage/F/Foo')會導致'ImportError:No module named b.bar'。我很高興繼續不知道,但我很好奇:) – blong

+0

這是關於[PYTHONPATH](https://docs.python.org/3/using/cmdline.html#envvar-PYTHONPATH) - Python的外觀在那些可導入東西的目錄中,當前的工作目錄就是其中之一。 –