2017-09-16 3 views
0

私はPyCharmとPython 3を使用していると私は、次のpythonフォルダのレイアウトを持っている:Pythonのimport(大文字のみの作業ではなく、親戚と)

src/ 
    __init__.py 
    command/ 
     __init__.py 
     simpleremote/ 
      __init__.py 
      Command.py 
      GarageDoor.py 
      GarageDoorOpenCommand.py 
      Light.py 
      LightOffCommand.py 
      LightOnCommand.py 
      RemoteControlTest.py 
      SimpleRemoteControl.py 

あなたが見ることができるように、私は、パッケージを作成しました。 mainメソッドを持つファイルは、これらの輸入品と完全に働いたRemoteControlTest.pyです:

from pythonDesignPatterns.src.command.simpleremote.GarageDoor import GarageDoor 
from pythonDesignPatterns.src.command.simpleremote.GarageDoorOpenCommand import GarageDoorOpenCommand 
from pythonDesignPatterns.src.command.simpleremote.Light import Light 
from pythonDesignPatterns.src.command.simpleremote.command import LightOnCommand 
from pythonDesignPatterns.src.command.simpleremote.SimpleRemoteControl import SimpleRemoteControl 

パッケージのinitの.pyファイルを作成する前に、私は相対的な輸入品の代わりに前者を使用しようとしました、

​​ :それは私にエラーを与えた

from .command import LightOnCommand 

なく、例えば(このケースを呼び出すために行きます)

ので、私はこれが同じ行のために働いていたことが判明周りいじる:

from command.simpleremote.Command import LightOnCommand 

とプログラムが正常に再び実行されましたが、私はIDE(PyCharm)から「リファクタリング」オプションを使用している場合名前の変更「コマンドコマンド ""に"、この行を書く:

from command.simpleremote.command import LightOnCommand 

を、それが突然エラー(ケースB)を示しています

ImportError: No module named 'command.simpleremote'; 'command' is not a package 

いずれの場合(AとB)に問題がありますか?私は、command.simpleremoteからインポートする際に、それぞれのケースでなぜ動作するのか理解できません。なぜ、1つのレベルがそれ以上に近くないのでしょうか?なぜそれが資本 'C'で働いていて、 'c'ではないのですか?大文字と小文字は区別されますか?

公式のPythonのドキュメント(およびPEP302、PEP328、PEP420のWeb)を見てきましたが、一晩で私にとっては複雑すぎます。誰でも簡単な方法でこれを理解することができますか(またはこれについて簡単に説明したリソースを教えてください)?私はあなたが直接RemoteControlTest.pyを実行することを推測事前

答えて

1

感謝。

ケースモジュールはパッケージ構造を経由して取得するのではなく、スクリプトとして直接実行された場合

Pythonの輸入者が親に行くことができません。

おそらく、Pythonデザイナーは、サブモジュールをスクリプトとして直接呼び出させたくないので、実際にはそれに対する解決策はありません。 srcは、現在のディレクトリまたはPYTHONPATHまたは

  • のいずれかがあなたのために呼び出しを行うテストフレームワークを使用するときに主にあなたは

    1. python -m command.simpleremote.RemoteControlTestでスクリプトを実行することができます。

    解決策の詳細については、Relative imports in Python 3を参照してください。

    ケースB

    ダイレクトスタートの結果は "src/command/simpleremoteは" module search pathであるということです。 "src"もパスに追加されるようですが、 "src/command/simpleremote"の後に追加されます。ケースBの前に

    from command...にインポートメカニズムは、「src/command/simpleremote」で「command」をマッチング見つけるとcommandパッケージが見つかった「src」で探し続けていなかった - >成功を。

    ケースBでは、パッケージ - >エラーではない "src/command/simpleremote"にcommand.pyが見つかりました。

  • +0

    についてA:相対的なインポートとパッケージ構造を経由して、各フォルダに__init__.pyファイルを置くだけでは不十分ですか? についてB:この点をテストするために、モジュールの検索パスのリンクについて読んでいます。 PyCharmは、私が関係していると思われるsys.path.exy __endを行います。 – madtyn

    +0

    @madtynについてA:いいえ、直接開始されたスクリプトの場合。 '__package__'属性は空です。モジュールがパッケージを通して読み込まれた場合、 '__package__'はパッケージ名を含みます。 –

    +0

    私はこれらの日を読んできました。 PythonのドキュメントとPEP366は、2行の回避策を推奨しています。私は '__package__'でいくつかの値を試しましたが、常に'親モジュール 'package.value'がロードされておらず、相対インポートを実行できません。 ' – madtyn

    関連する問題