59

Pythonでは、正確には何がimport *インポートされますか?__init__.py含まれているフォルダで見つかったものをインポートしますか?

たとえば、宣言する必要がありますかfrom project.model import __init__、それともfrom project.model import *十分ですか?

4

6 に答える 6

68

from xyz import *他の形式のインポートとは対照的なの「利点」は、現在のモジュールの下にある指定されたモジュールからすべて(まあ、ほとんど... [以下の(a)を参照]すべて)をインポートすることです。これにより、インポートされたモジュールのさまざまなオブジェクト(変数、クラス、メソッドなど)を、モジュール名の前に付けることなく使用できます。例えば

>>> from math import *
>>>pi
3.141592653589793
>>>sin(pi/2)
>>>1.0

ただし、この方法(*を現在の名前空間にインポートする)は

  • 名前空間の衝突の機会を提供します(たとえば、インポート前に変数名piがあった場合)
  • インポートされるオブジェクトの数が多い場合、非効率になる可能性があります
  • 変数/メソッド/クラスの起源を明示的に文書化していない(将来コードにアクセスするために、プログラムのこの「自己文書化」があると便利です)

したがって、通常、このインポート*プラクティスはアドホックテストなどに限定します。@Denilson-Sá-Maiaが指摘しているように、(pygameなど)などの一部のライブラリには、最も一般的に使用されるすべての定数と関数が定義され、そのようなサブモジュールがでインポートされるように効果的に設計されimport *たサブモジュールがあります。これらの特別なサブモジュールを使用する場合を除いて、それ以外の場合は...:

いくつかのオブジェクトのみを明示的にインポートする

>>>from math import pi
>>>pi
>>>3.141592653589793
>>> sin(pi/2)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
NameError: name 'sin' is not defined

または、モジュールを独自の名前空間(または、特にこれが長い名前であり、プログラムがそのオブジェクトを何度も参照する場合はそのエイリアス)でインポートします。

  >>>import math
  >>>math.pi
  >>>3.141592653589793
  etc..


  >>>import math as m  #bad example math being so short and standard...
  >>>m.pi
  >>>3.141592653589793
  etc..

このトピックに関するPythonのドキュメントを参照してください

(a)具体的には、何がインポートされfrom xyz import *ますか?
xyzモジュールが__all__変数を定義する場合、このシーケンスで定義されたすべての名前をインポートします。それ以外の場合は、アンダースコアで始まる名前を除くすべての名前をインポートします。

多くのライブラリにはサブモジュールがあります。たとえば、標準ライブラリには、、などのurllibサブモジュールが含まれています。よくある混乱のポイントは、urllib.requesturllib.errorsurllib.response

from urllib import *

これらすべてのサブモジュールをインポートします。そうではありません。たとえば、これらを個別に明示的にインポートする必要がありますfrom urllib.request import *。これは偶然にも固有のものではなくimport *、plainimportはサブモジュールもインポートしません(もちろん、これは「すべて」*の省略形であることがよくあります。すべてのサブモジュールと他のすべてがインポートされると人々を誤解させます)。

于 2010-03-02T03:56:25.443 に答える
15

モジュール(またはパッケージ)がその属性にリストしている名前を(現在の名前空間に)インポートします。その__all__ような属性が欠落しているため、。で始まらないすべての名前がインポートされます_

これは主に、インタラクティブなインタプリタセッションでのみ使用するための便利なショートカットとして意図されています。他の回答が示唆しているように、プログラムでは使用しないでください。

GoogleのPythonスタイルガイドによると、モジュール内からクラスや関数(または他の名前)ではなく、モジュールのみをインポートすることをお勧めします。これに厳密に従うことで、明確さと精度が向上し、「モジュール内からのもの」をインポートするときに発生する可能性のある微妙なトラップを回避できます。

パッケージ(またはその中から何か)をインポートすると、本質的にパッケージがロードされて実行__init__.pyされます。そのファイルはパッケージの本体を定義します。ただし、__init__現在の名前空間の名前はバインドされません(したがって、この意味では、その名前はインポートされません)。

于 2010-03-02T03:47:36.560 に答える
4

はい、そうです。すべてをインポートします(プライベート変数ではありません。つまり、名前が_またはで始まる変数) 。ローカル名前空間の汚染を避けるために、「Pythonでモジュールを適切にインポート__する」に従って使用しないようにしてください。

それで十分ですが、一般的には、 「Pythonインポートについて」に従って、import project.modelすでにインポートしているを実行する必要がありますが、使いすぎると言葉が多すぎるか、後で使用するときにいくつかのキーストロークを節約できます。__init__.pyimport project.model as pmimport project.model as model

「「import*」は正確には何をインポートしますか?」のAlexのアドバイスに従ってください。

于 2010-03-02T03:35:32.760 に答える
4

project.modelがパッケージの場合、によって参照されるモジュールimport project.modelはから.../project/model/__init__.pyです。の名前空間からあなたの名前空間にfrom project.model import *すべてをダンプします。__init__.pyモデル内の他のモジュールに対しては自動的に何もしません。推奨されるスタイルは、__init__.py何も含まないことです。

決して使用することはありませんimport *。それはあなたのコードを読めなくし、維持不可能にします。

于 2010-03-02T03:39:43.667 に答える
4

モジュールからインポートされたスター/アスタリスク(*)を確認するための良い方法は次のとおりです。

before = dir()
from math import *
after = dir()
print(set(after) - set(before))

戻り値:

{'modf', 'pow', 'erfc', 'copysign', 'sqrt', 'atan2', 'e', 'tanh', 'pi', 'factorial', 'cosh', 'expm1', 'cos', 'fmod', 'frexp', 'log', 'acosh', 'sinh', 'floor', 'isclose', 'lgamma', 'ceil', 'gcd', 'ldexp', 'hypot', 'radians', 'atan', 'isnan', 'atanh', 'before', 'isinf', 'fabs', 'isfinite', 'log10', 'nan', 'tau', 'acos', 'gamma', 'asin', 'log2', 'tan', 'degrees', 'asinh', 'erf', 'fsum', 'inf', 'exp', 'sin', 'trunc', 'log1p'}

私は自分のモジュールで作業していて、すべてを明示的にインポートしていましたが、インポートするもののリストが長くなりすぎていました。したがって、このメソッドを使用して、*がインポートしたもののリストを取得する必要がありました。

于 2019-03-01T10:32:30.497 に答える
2

問題のモジュール(project.modelあなたの場合)がという名前の刺し傷のリストを定義している場合__all__、そのリスト内のすべての名前付き変数がインポートされます。そのような変数がない場合は、すべてをインポートします。

于 2010-03-02T03:43:20.243 に答える