私はいつもこの方法を使用しています:
from sys import argv
そしてargv
を argv と一緒に使用します。ただし、これを使用する規則があります:
import sys
およびsys.argv
2番目の方法では、コードが自己文書化され、(本当に)準拠します。しかし、私が最初の方法を好む理由は、モジュール全体をインポートするのではなく、必要な関数のみをインポートするため、高速であるためです(Pythonがインポートに時間を浪費する、より多くの役に立たない関数が含まれています)。必要なのはargvだけであり、sysの他のすべての関数は役に立たないことに注意してください。
つまり、私の質問はそうです。最初の方法は本当にスクリプトを高速にしますか?どの方法が最も好ましいですか?なぜですか?
コメント
回答
モジュールをインポートしても何も無駄になりません;モジュールは常に完全ですは(sys.modules
マッピングに)インポートされるため、import sys
またはfrom sys import argv
はオッズを作成しません。
2つのステートメントの唯一の違いは、バインドされる名前です。import sys
は名前をバインドしますsys
をモジュールに(つまり、sys
-> sys.modules["sys"]
)、from sys import argv
はバインドします別の名前argv
は、モジュール内に含まれる属性をまっすぐ指します(つまり、argv
-> sys.modules["sys"].argv
)。残りの部分e sys
モジュールは、モジュールの他のものを使用するかどうかに関係なく、引き続き存在します。
2つのアプローチの間にパフォーマンスの違いもありません。はい、sys.argv
は2つのことを調べる必要があります。グローバル名前空間でsys
を検索し(モジュールを検索)、次に属性argv
を検索する必要があります。はい、from sys import argv
を使用すると、属性への直接参照がすでにあるため、属性の検索をスキップできます。ただし、import
ステートメントは引き続きその作業を行う必要があり、インポート時に同じ属性を検索します。「argv
一度。ループでargv
を何千回も使用する必要がある場合は、おそらく違いが生じる可能性がありますが、この特定のケースでは実際には違いがありません。 。
その場合、どちらを選択するかは、代わりにコーディングスタイルに基づく必要があります。
large モジュール内、私は確かにimport sys
を使用します。コードのドキュメントが重要であり、大きなモジュールのどこかでsys.argv
を使用すると、argv
よりもはるかに明確になります。
argv
を使用する唯一の場所が"__main__"
ブロック内にある場合main()
関数、それについて満足している場合は、必ずfrom sys import argv
を使用してください:
if __name__ == "__main__": from sys import argv main(argv)
I 「まだimport sys
を自分で使用しています。すべてが同じです(正確には、パフォーマンスと書き込みに使用される文字数の点で ) 、それは私にとっては簡単です。
他のものをまとめてインポートする場合は、おそらくパフォーマンスが影響します。ただし、特定の名前を使用する場合に限ります。モジュールは何度も、たとえばクリティカルループで行われます。ただし、ローカル名(関数内)の作成はさらに高速になります:
import somemodule def somefunction(): localname = somemodule.somefunctionorother while test: # huge, critical loop foo = localname(bar)
コメント
- 最上位パッケージ内のサブパッケージ/モジュールの1つの属性を公開するサブパッケージまたはモジュールを含むパッケージがある場合もあります。
from...import
を使用すると、package.subpackage_or_module.attribute
ではなくpackage.attribute
を実行できます。パッケージ内に論理的または概念的なグループ化がありますが、パッケージのユーザーにとってもう少し便利なものにしたいです。 (numpy
はこのようなことをしていると思います。) - djangoには、
from django.core.management.base import BaseCommand
の方が優れており、他のもの(特にimport django
)を使用すると、コードが読み取れなくなります。ですから、私はこの答えが好きですが、慣例が裸のインポートに違反することであるいくつかのライブラリ(そして特にいくつかのフレームワーク)があると思います。いつものように、与えられた状況で何が最善かについてあなたの判断を使用してください。しかし、明示的な側で誤りを犯します(言い換えれば、私はほとんどの部分に同意します)。 - @JAB:
import ... as
を使用してパッケージを見つけることができます。別の名前:import package.subpackage_or_module as shortname
。from parent import sub
は基本的に同じことを行います。 -
so wether you use import sys or from sys import argv makes no odds
これはIDLEには当てはまらないようです。モジュールをインポートするだけではその関数はインポートされず、IDLEシェルで呼び出すことができるのは< module >。< function > name - @Suncatcher:私の答えを完全に読んでください。あなたが引用する文は、どの名前がバインドされているかではなく、どれだけインポートされているかについて話します。その’は回答の他の場所で説明されています。
回答
from module import function
ではなくimport module
を使用することに賛成する2つの理由があります。
最初は名前空間です。関数をグローバル名前空間にインポートすると、名前の衝突のリスクがあります。
2つ目は、標準モジュールには関係ありませんが、特に開発中は、独自のモジュールにとって重要です。モジュール。これを考慮してください:
from module import func ... reload(module) # func still points to the old code
一方
import module ... reload(module) # module.func points to the new code
速度については。 。
モジュール全体をインポートするのではなく、必要な関数のみをインポートします(これには、Pythonがインポートに時間を浪費する無駄な関数が含まれています)
モジュールをインポートする場合でも、モジュールから関数をインポートする場合でも、Pythonはモジュール全体を解析します。どちらの方法でも、モジュールがインポートされます。 「関数のインポート」は、関数を名前にバインドすることに他なりません。実際、import module
は、from module import func
よりも通訳者の作業が少なくて済みます。
コメント
- reload()はPython2に組み込まれていました。これはPython3には当てはまりません。
- 循環インポートの依存関係にも影響があると思いましたか?
回答
読みやすさが向上するたびに、from import
を使用します。たとえば、私は好みます(セミコロンはここでスペースを節約するためだけのものです):
from collections import defaultdict from foomodule import FooBar, FooBaz from twisted.internet.protocol import Factory defaultdict(); FooBar(); FooBaz(); Factory()
代わりに:
import collections import foomodule import twisted.internet.protocol collections.defaultdict(); foomodule.FooBar(); foomodule.FooBaz() twisted.internet.protocol.Factory()
後者は冗長な情報がたくさん含まれているため、私にとっては読み取り(および書き込み)が困難です。また、モジュールのどの部分を使用しているかを事前に知っておくと便利です。
ロットを使用している場合は、通常のimport
を使用します。モジュールからの短い名前の例:
import sys sys.argv; sys.stderr; sys.exit()
または、名前が非常に一般的で、名前空間の外では意味をなさない場合:
import json json.loads(foo) from json import loads loads(foo) # potentially confusing
コメント
- これが私のお気に入りの回答です。 ‘暗黙的よりも明示的の方が優れている’は、読みやすさ、シンプルさ、DRYと競合することがあります。特にDjangoのようなフレームワークを使用する場合。
回答
私の意見では通常のimport
は読みやすさを向上させます。 Pythonコードを確認するとき、指定された関数またはクラスが使用されている場所からどこから来ているかを確認するのが好きです。モジュールの一番上までスクロールしてその情報を取得する手間が省けます。
長いモジュール名については、as
キーワードを使用して短くします。エイリアス:
import collections as col import foomodule as foo import twisted.internet.protocol as twip my_dict = col.defaultdict() foo.FooBar() twip_fac = twip.Factory()
例外として、iv id =を扱うときは、常にfrom module import something
表記を使用します。 “c58a4bc552”>
モジュール。 Python 2でデフォルトですべての文字列をユニコードにしたい場合は、別の方法でそれを行うことはできません。たとえば、
from __future__ import unicode_literals from __future__ import print_function
コメント
- アーメン!” import as “は勝利の組み合わせです:-)
回答
ただし、import sys
およびfrom sys import agrv
両方ともsys
モジュール全体をインポートします。後者は名前バインディングを使用するため、残りのコードはargv
モジュールのみにアクセスできます。
明示的に指定した関数にのみアクセスできるため、これが推奨されるスタイルです。
ただし、名前の競合が発生する可能性があります。
?関数を明示的にインポートし、from sys import argv as sys_argv
で名前を変更することもできます。これは、明示的なインポートに適合し、名前空間を指定する可能性が低い規則です。衝突。
コメント
- では、
if sys_argv:
は?私は2番目のステートメントが何を意味するかを知っていますが、奇妙なインポートに戻ることなく、最初のフォームが何を意味するのかわかりません。
回答
最近、この質問を自分に問いかけました。さまざまなメソッドの時間を計りました。
リクエストライブラリ
def r(): import requests return "hello" timeit r() # output: 1000000 loops, best of 3: 1.55 µs per loop def rg(): from requests import get return "hello" timeit rg() # output: 100000 loops, best of 3: 2.53 µs per loop
美しいスープライブラリ
def bs(): import bs4 return "hello" timeit bs() # output: 1000000 loops, best of 3: 1.53 µs per loop def be(): from bs4 import BeautifulSoup return "hello" timeit be() # output: 100000 loops, best of 3: 2.59 µs per loop
jsonライブラリ
def js(): import json return "hello" timeit js() # output: 1000000 loops, best of 3: 1.53 µs per loop def jl(): from json import loads return "hello" timeit jl() # output: 100000 loops, best of 3: 2.56 µs per loop
sysライブラリ
def s(): import sys return "hello" timeit s() # output: 1000000 loops, best of 3: 1.55 µs per loop def ar(): from sys import argv return "hello" timeit ar() # output: 100000 loops, best of 3: 2.87 µs per loop
パフォーマンスにわずかな違いがある と私は思います。
コメント
- 属性ルックアップを追加しています。
import module
とfrom module import name
を正しく比較するには、その名前ルックアップをimport module
追加します。
の場合。例えば。sys.argv
の行をar
テストなどに追加します。実行される作業はわずかに異なるバイトコードが生成され、異なるコードパスが実行されるため、異なります。
import sys
を使用する場合とsys.argv
をループで数千回使用する場合と、from sys import argv
次に、argv
のみを使用します。ただし、’ tはしません。モジュールのグローバルレベルで一度行うことについては、タイミングの微視的な違いではなく、読みやすさを最適化する必要があります。回答
公開されたコードフラグメントを見て、モジュール全体をインポートし、module.function
は、少なくとも標準モジュールでは、ほぼ標準です。唯一の例外はdatetime
from datetime import datetime, timedelta
のようですので、datetime.now()
datetime.datetime.now()ではなく/ div>。
パフォーマンスが心配な場合は、いつでも(たとえば)
次に、モジュールルックアップがすでに実行されているため、パフォーマンスが重要なコードを実行します。ただし、これは関数/メソッドで機能しますが、ほとんどのIDEは混乱し、(たとえば)変数に割り当てられたときに関数のソースリンク/署名を表示しません。
回答
次のようなことをした場合に追加したい
from math import sin
(またはsys
やposix
などの他の組み込みライブラリ)、sin
はモジュールのドキュメントに含まれている(つまり、>>> help(mymodule)
または$ pydoc3 mymodule
を実行する場合。これを回避するには、次を使用してインポートします。
import math from math import sin as _sin
PS:組み込みライブラリは、Cコードからコンパイルされ、Pythonに含まれているライブラリです。argparse
、os
とio
は組み込みパッケージではありません
from … import …
構文の背後にある理由