Python 3 モジュール

前の記事では、Pythonインタープリターを使用してスクリプトをプログラムしましたが、Pythonインタープリターを終了してから再び入ると、定義したすべてのメソッドと変数が消えます。

このため、Pythonは、一部のスクリプトまたは対話型インタープリター実例で使用するために、これらの定義したメソッドと変数をファイルに格納する方法を提供します。このファイルはモジュールと呼ばれます。

モジュールは、定義したすべての関数と変数を含むファイルであり、その拡張子は.pyです。 モジュールは、他のプログラムによって導入され、モジュール内の関数や他の機能を使用できます。 これは、Python標準ライブラリを使用する方法でもあります。

以下は、Python標準ライブラリのモジュールの使用例です。

実例(Python 3.0以降)

#!/usr/bin/python3 
# ファイル名: using_sys.py 
import sys 
print('コマンドライン引数は次のとおり:') 
for i in sys.argv: 
print(i) 

print('\n\nPython パス:', sys.path, '\n')

実行結果は以下のとおりです。

$ python using_sys.py引数1引数2
コマンドライン引数は次のとおりです。
using_sys.py
引数1
引数2

Python パス: ['/root', '/usr/lib/python3.4', '/usr/lib/python3.4/plat-x86_64-linux-gnu', '/usr/lib/python3.4/lib-dynload', '/usr/local/lib/python3.4/dist-packages', '/usr/lib/python3/dist-packages'] 
  • Importsysは、Python標準ライブラリのsys.pyモジュールをインポートします。これは、特定のモジュールをインポートする方法です。
  • sys.argvは、コマンドライン引数を含むリストです。
  • sys.pathには、Pythonインタープリターが必要なモジュールを自動的に見つけるパスのリストが含まれています。

importステートメント

Pythonソースファイルを使用するには、別のソースファイルでimportステートメントを実行するだけです。構文は次のとおりです。

import module1[, module2[,... moduleN]

インタープリターがimportステートメントを検出すると、モジュールが現在の検索パスにある場合はモジュールがインポートされます。

検索パスは、インタープリターが最初にすべてのディレクトリのリストを検索します。 モジュールサポートをインポートする場合は、スクリプトの先頭にコマンドを配置する必要があります。

support.pyファイルコード

#!/usr/bin/python3 
# Filename: support.py 

def print_func( par ): 
print ("Hello : ", par) 
return

test.pyをsupportモジュールにインポートします。

test.pyファイルコード

#!/usr/bin/python3 
# Filename: test.py 

#モジュールをインポートする
import support 

# これで、モジュールに含まれている関数を呼び出す
support.print_func("Florian")

上記の実例の出力結果は以下になります。

$ python3 test.py 
Hello :  Florian

モジュールは、実行するインポートの数に関係なく、一度だけインポートされます。 これにより、インポートされたモジュールが何度も実行されるのを防ぎます。

importステートメントを使用する場合、Pythonインタープリターはどのようにして対応するファイルを見つけますか?

これにはPythonの検索パスに関係しています。検索パスは一連のディレクトリ名で構成され、Pythonインタープリターはこれらのディレクトリからインポートされたモジュールを順番に検索します。

これは環境変数によく似ています。実際、検索パスは環境変数を定義することによっても決められます。

検索パスはPythonのコンパイル時またはインストール時に決定され、新しいライブラリのインストールも変更されます。 検索パスは、sysモジュールのpath変数に格納されます。簡単なテストを行います。対話型インタープリターに次のコードを入力します。

>>> import sys
>>> sys.path
['', '/usr/lib/python3.4', '/usr/lib/python3.4/plat-x86_64-linux-gnu', '/usr/lib/python3.4/lib-dynload', '/usr/local/lib/python3.4/dist-packages', '/usr/lib/python3/dist-packages']
>>> 

sys.pathの出力はリストであり、最初の項目は空の文字列 “であり、これは現在のディレクトリを表します(スクリプトから出力された場合、どのディレクトリをより明確に確認できます)。 Pythonインタープリターディレクトリを実行します(スクリプトの場合、実行中のスクリプトが配置されているディレクトリです)。

そのため、現在のディレクトリにインポートするモジュールと同じ名前のファイルがあると、インポートするモジュールがブロックされます。

検索パスの概念を理解すると、スクリプト内のsys.pathを変更して、検索パスにないいくつかのモジュールを導入できます。

ここで、インタプリタの現在のディレクトリまたはsys.pathのディレクトリにfibo.pyファイルを作成します。コードは次のとおりです。

実例

# フィボナッチ(fibonacci)シーケンスモジュール
def fib(n): # nに定義されたフィボナッチ数列
a, b = 0, 1 
while b < n: 
print(b, end=' ') 
a, b = b, a+b 
print() 

def fib2(n): # nのフィボナッチ数列に戻る 
result = [] 
a, b = 0, 1 
while b < n: 
result.append(b) 
a, b = b, a+b 
return result

次に、Pythonインタープリターを入力し、次のコマンドを使用してこのモジュールをインポートします。

>>> import fibo

これは、fiboで直接定義されている関数の名前を現在の記号テーブルに書き込むのではなく、モジュールfiboの名前をそこに書き込むだけです。

モジュール名を使用して、関数にアクセスできます。

実例

>>>fibo.fib(1000) 
1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987 
>>> fibo.fib2(100) 
[1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89] 
>>> fibo.__name__ 
'fibo'

関数を頻繁に使用する場合は、ローカル名に割り当てることができます。

>>> fib = fibo.fib
>>> fib(500)
1 1 2 3 5 8 13 21 34 55 89 144 233 377

from…importステートメント

Pythonのfromステートメントを使用すると、モジュールから指定した部分を現在の名前の空間にインポートできます。構文は次のとおりです。

from modname import name1[, name2[, ... nameN]]

たとえば、モジュールfiboのfib関数をインポートするには、次のステートメントを使用します。

>>> from fibo import fib, fib2
>>> fib(500)
1 1 2 3 5 8 13 21 34 55 89 144 233 377

このステートメントは、fiboモジュール全体を現在の名前空間にインポートするのではなく、fiboのfib関数のみをインポートします。

from…import *ステートメント

次の宣言を使用するだけで、モジュールのすべてのコンテンツを現在の名前空間にインポートすることもできます。

from modname import *

これにより、モジュール内のすべてのアイテムを簡単にインポートできます。 ただし、このステートメントは使用しすぎないようにしてください。

モジュールの詳細

メソッド定義に加えて、モジュールには実行可能コードを含めることもできます。 これらのコードは通常、このモジュールを初期化するために使用されます。 これらのコードは、最初にインポートされたときにのみ実行されます。

各モジュールには独自の独立した記号テーブルがあり、モジュール内のすべての関数のグローバル記号テーブルとして使用されます。

したがって、モジュールの作成者は、他のユーザーのグローバル変数を混同することを心配することなく、モジュール内でこれらのグローバル変数を安全に使用できます。

一方、自分が何をしているのかが本当にわかっている場合は、modname.itemnameのような表記を使用してモジュール内の関数にアクセスすることもできます。

モジュールには他のモジュールをインポートできます。 モジュール(またはスクリプトなど)の前でimportを使用してモジュールをインポートします。もちろん、これは単なる慣例であり、必須ではありません。 インポートされたモジュールの名前は、現在動作中のモジュールの記号テーブルに配置されます。

もう一つimportメソッドもあります。importを使用して、モジュールの名前(関数、変数)を現在の操作モジュールに直接インポートできます。

>>> from fibo import fib, fib2
>>> fib(500)
1 1 2 3 5 8 13 21 34 55 89 144 233 377

このimportメソッドは、インポートされたモジュールの名前を現在の文字テーブルに配置しません(したがって、この例では、名前fiboは定義されていません)。

モジュール内のすべての(関数、変数)名を現在のモジュールの文字テーブルに一度にインポートする別の方法があります。

>>> from fibo import *
>>> fib(500)
1 1 2 3 5 8 13 21 34 55 89 144 233 377

これによりすべての名前がインポートされますが、単一の下線(_)で始まる名前は含まれていません。 導入された他のソースの名前が既存の定義をカバーしている可能性があるため、ほとんどの場合、Pythonプログラマーはこのメソッドを使用しません。

_name_プロパティ

モジュールが最初に別のプログラムによって導入されると、そのメインプログラムが実行されます。 モジュールの導入時にモジュール内の特定のプログラムブロックを実行しないようにする場合は、_ name_プロパティを使用して、モジュール自体が実行されているときにのみプログラムブロックを実行することができます。

#!/usr/bin/python3
# Filename: using_name.py

if __name__ == '__main__':
   print('プログラム自体が実行されている')
else:
   print('別のモジュールに属する')

実行出力は次のとおりです。

$ python using_name.py

プログラム自体が実行されている

$ python
>>> import using_name
別のモジュールに属する
>>>

説明:各モジュールには__name__属性があります。値が「__main__」の場合は、モジュール自体が実行中であることを示します。それ以外の場合は、インポートされます。

説明:__ name__と__main__は二重下線です。_ _中央のスペースを削除したものです。

dir()関数

組み込み関数dir()は、モジュールで定義されているすべての名前を見つけることができます。 文字列のリストとして返します。

>>> import fibo, sys
>>> dir(fibo)
['__name__', 'fib', 'fib2']
>>> dir(sys)  
['__displayhook__', '__doc__', '__excepthook__', '__loader__', '__name__',
 '__package__', '__stderr__', '__stdin__', '__stdout__',
 '_clear_type_cache', '_current_frames', '_debugmallocstats', '_getframe',
 '_home', '_mercurial', '_xoptions', 'abiflags', 'api_version', 'argv',
 'base_exec_prefix', 'base_prefix', 'builtin_module_names', 'byteorder',
 'call_tracing', 'callstats', 'copyright', 'displayhook',
 'dont_write_bytecode', 'exc_info', 'excepthook', 'exec_prefix',
 'executable', 'exit', 'flags', 'float_info', 'float_repr_style',
 'getcheckinterval', 'getdefaultencoding', 'getdlopenflags',
 'getfilesystemencoding', 'getobjects', 'getprofile', 'getrecursionlimit',
 'getrefcount', 'getsizeof', 'getswitchinterval', 'gettotalrefcount',
 'gettrace', 'hash_info', 'hexversion', 'implementation', 'int_info',
 'intern', 'maxsize', 'maxunicode', 'meta_path', 'modules', 'path',
 'path_hooks', 'path_importer_cache', 'platform', 'prefix', 'ps1',
 'setcheckinterval', 'setdlopenflags', 'setprofile', 'setrecursionlimit',
 'setswitchinterval', 'settrace', 'stderr', 'stdin', 'stdout',
 'thread_info', 'version', 'version_info', 'warnoptions']

引数が指定されていない場合、dir()関数は現在定義されているすべての名前を一覧表示します。

>>> a = [1, 2, 3, 4, 5]
>>> import fibo
>>> fib = fibo.fib
>>> dir() # 現在のモジュールで定義されているプロパティのリストを取得する
['__builtins__', '__name__', 'a', 'fib', 'fibo', 'sys']
>>> a = 5 # 新しい変数「a」を作成する
>>> dir()
['__builtins__', '__doc__', '__name__', 'a', 'sys']
>>>
>>> del a # 変数aを削除する
>>>
>>> dir()
['__builtins__', '__doc__', '__name__', 'sys']
>>>

標準モジュール

Python自体には、いくつかの標準モジュールライブラリが付属しています。これらは、Pythonライブラリで紹介されます。

一部のモジュールはパーサ(parser) に直接組み込まれています。これらは言語の組み込み機能ではありませんが、非常に効率的に使用でき、システムレベルの呼び出しでも問題ありません。

これらのコンポーネントは、さまざまなオペレーティングシステムに応じてさまざまな形式で構成されます。たとえば、winregモジュールはWindowsシステムにのみ提供されます。

すべてのPythonパーサーに組み込まれている特別なモジュールsysに注意してください。 変数sys.ps1およびsys.ps2は、プライマリプロンプトとセカンダリプロンプトに対応する文字列を定義します。

>>> import sys
>>> sys.ps1
'>>> '
>>> sys.ps2
'... '
>>> sys.ps1 = 'C> '
C> print('Florian Studio!')
Florian Studio!
C> 

パッケージ

パッケージは、「ドットモジュール名」を使用してPythonモジュールの名前空間を管理する形式です。

たとえば、モジュールの名前がA.Bの場合、パッケージAのサブモジュールBを意味します。

モジュールを使用する場合、異なるモジュール間のグローバル変数の相互影響について心配する必要はないと同様、ドットモジュール名形式を使用する場合も、異なるライブラリ間でモジュール名が被ることを心配する必要もありません。

このようにして、さまざまな作成者がNumPyモジュールまたはPythonグラフィックライブラリを提供できます。

サウンドファイルとデータを処理するモジュールのセット(または「パッケージ」と呼ぶ)を設計するとします。

多くの異なるオーディオファイル形式があります(基本的にサフィックス名で区別されます。例:.wav、:file:.aiff、:file:.au、したがって、異なる形式間で変換するために、増加するモジュールのセットが必要です。

また、これらのオーディオデータには、さまざまな操作(ミキシング、エコーの追加、イコライザー機能の追加、人工ステレオエフェクトの作成など)があるため、これらの操作を処理するために書き込みきれないモジュールのセットが必要です。

一種の可能なパッケージ構造は次のとおりです。(階層ファイルシステムの中で)

sound/                          トップパッケージ
      __init__.py               サウンドパッケージを初期化する
      formats/                  ファイルフォーマット変換サブパッケージ
              __init__.py
              wavread.py
              wavwrite.py
              aiffread.py
              aiffwrite.py
              auread.py
              auwrite.py
              ...
      effects/                  効果音サブパッケージ
              __init__.py
              echo.py
              surround.py
              reverse.py
              ...
      filters/                  filters サブパッケージ
              __init__.py
              equalizer.py
              vocoder.py
              karaoke.py
              ...

パッケージをインポートするとき、Pythonはsys.pathのディレクトリに従って、パッケージに含まれているサブディレクトリを探します。

ディレクトリは、_init_.pyというファイルが含まれている場合にのみパッケージと見なされます。これは主に、一部の名前(stringなど)が検索パスの有効なモジュールに誤って影響を与えるのを防ぐためです。

最も単純なケースでは、空の:file:_init_.pyを配置するだけです。 もちろん、このファイルには、初期化コードを含めたり、_ all_変数に値を割り当てたりすることもできます(後で紹介します)。

ユーザーは、次のように、一度に1つのパッケージで特定のモジュールのみをインポートできます。

import sound.effects.echo

これにより、サブモジュールsound.effects.echoがインポートされます。フルネームを使用してアクセスします。

sound.effects.echo.echofilter(input, output, delay=0.7, atten=4)

サブモジュールをインポートする別の方法は次のとおりです。

from sound.effects import echo

これにより、サブモジュールechoもインポートされます。長いプレフィックスを必要としないため、次のように使用できます。

echo.echofilter(input, output, delay=0.7, atten=4)

もう1つの変更は、関数または変数を直接インポートすることです。

from sound.effects.echo import echofilter

同様に、このメソッドはサブモジュールechoをインポートし、echofilter()関数を直接使用できます。

echofilter(input, output, delay=0.7, atten=4)

from package import itemの形式を使用する場合、対応するアイテムは、パッケージ内のサブモジュール(サブパッケージ)、または関数、クラス、変数など、パッケージで定義されている他の名前のいずれかであることに注意してください。

インポート構文は、最初にアイテムをパッケージ定義の名前として扱い、見つからない場合は、モジュールとしてインポートを試みます。 まだ見つからない場合は、 :exc:ImportError 例外をスローします。

逆に、import item.subitem.subsubitemのようなインポートフォームを使用する場合、最後のアイテムを除くすべてがパッケージである必要があり、最後のアイテムはモジュールまたはパッケージにすることができますが、クラス、関数、または変数の名前にすることはできません。

パッケージからインポート*

from sound.effects import *を使用するとどうなるか想像してみてください。

Pythonはファイルシステムに入り、このパッケージ内のすべてのサブモジュールを見つけて、それらを1つずつインポートします。

残念ながら、Windowsは大文字と小文字を区別しないシステムであるため、この方法はWindowsプラットフォームではうまく機能しません。

このタイプのプラットフォームでは、ECHO.pyというファイルがモジュールecho、Echo、またはECHOとしてインポートされるかどうかを保証することはできません。

たとえば、Windows 95は各ファイルの最初の文字を大文字にするのが面倒です)そしてDOSの8 + 3命名規則は長いモジュール名を処理するため、問題はさらに複雑になります。
この問題を解決するために、パッケージの作者に正確なパッケージインデックスを提供することしかできません。

importステートメントは次のルールに従います。パッケージ定義ファイル__init__.pyに__.pyに__all__というリスト変数がある場合、from package import *を使用すると、このリスト内のすべての名前がパッケージコンテンツとしてインポートされます。

パッケージの作成者は、パッケージの更新後に__all__も更新されることを忘れないでください。 impotr*を使用したくない場合は、 次に例をご覧ください。file:sounds / Effects /__init__.pyには次のコードが含まれています。

__all__ = ["echo"、 "surround"、 "reverse"]

これは、from sound.effects import *を使用する場合、これら3つのサブモジュールのみをパッケージにインポートすることを意味します。

__all__が実際に定義されていない場合、sound.effects import *の構文を使用すると、sound.effectsパッケージ内のサブモジュールはインポートされません。 パッケージsound.effectsとそれに定義されているすべてのコンテンツをインポートするだけです(おそらく__init__.pyで定義されている初期化コードを実行します)。

これにより、__init__.py で定義されているすべての名前がインポートされます。 また、このステートメントの前にインポートした明示的に指定されたすべてのモジュールを影響ません。 コードをご覧ください。

import sound.effects.echo
import sound.effects.surround
from sound.effects import *

この例では、from … importを実行する前に、sound.effectsパッケージのechoモジュールとsurroundモジュールが現在の名前空間にインポートされています。 (もちろん、__ all__が定義されていれば、問題はありません)

通常、この* メソッドを使用してモジュールをインポートすることはお勧めしません。これは、このメソッドがコードの可読性を低下させることが多いためです。 ただし、これによりキーを押す手間が大幅に節約され、一部のモジュールは特定の方法でのみインポートされるように設計されています。

from Package import specific_submodule この方法を使用に間違いがないことを忘れないでください。 実際、これも推奨される方法です。 インポートするサブモジュールが他のパッケージのサブモジュールと同じ名前である場合を除きます。

パッケージが構造内のサブパッケージ(この例のパッケージsoundなど)であり、同じレベルのパッケージをインポートする場合は、絶対パスを使用してインポートする必要があります。 たとえば、モジュールsound.filters.vocoderがパッケージsound.effectsのモジュールechoを使用する場合は、from sound.effects import echoを書き込む必要があります。

from . import echo
from .. import formats
from ..filters import equalizer

暗黙的および明示的な相対インポートはどちらも、現在のモジュールから開始されます。 メインモジュールの名前は常に”__main__”です。Pythonアプリケーションのメインモジュールは、常に絶対パスで参照する必要があります。

このパッケージには、別のプロパティpathも含まれています。 これはディレクトリのリストです。含まれている各ディレクトリは、このパッケージに使用する__init__pyがあります。他の__init__.pyを実行する前に定義する必要があります。 この変数は、パッケージに含まれるモジュールとサブパッケージに影響を与えるように変更できます。

この機能は頻繁には使用されなく、一般的にパッケージ内のモジュールを拡張するために使用されます。

Share

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です