【基本】Pythonの変数の名前空間とスコープを解説!

2023-07-17

Pocket

こんにちは、爽です。皆さん、いかがお過ごしでしょうか?

今回はPythonの変数の名前空間とスコープについて確認します。
他の言語でもそうですが、変数は定義する場所によってどこからでも呼び出せるものや、関数内でのみ呼び出せるものが存在します。
このことを知らないとアプリケーション開発がスムーズに進みませんので、ここで是非知っておきましょう。

■この記事の対象読者
・Pythonに興味がある方
・Pythonを学び始めてみたい方

・Pythonの変数の名前空間とスコープについて詳細を知りたい方

なお、私はPythonをAnacondaをインストールしてJupyterで実行しています。MacのAnacondaのインストール方法とJupyterの使い方は下記記事にまとめているので良かったらご参考ください。

それではどうぞ!

グローバル変数とローカル変数

グローバル変数とはプログラムのどこからでも呼び出せる変数です。一方でローカル変数とは関数内でのみ呼び出せる変数です。また、関数内ではローカル変数を優先して参照する性質があります。
例えば下記例を見ると関数の外ではグローバル変数、関数の中ではローカル変数を優先していることが分かります。

#グローバル変数
animal = 'cat'

def function():
    #ローカル変数
    animal = 'dog'
    print(animal)

#グローバル変数が出力される
print(animal) 
#ローカル変数が出力される
function()

# cat
# dog

また、関数の外からローカル変数を呼び出そうとするとエラーになります。

#============================================================================
#Jupyterで再現するためには、Kernel→Restart Kernel
#============================================================================
def function():
    #ローカル変数
    animal = 'dog'
    print(animal)

#ローカル変数が出力される
function()
#関数の外から呼び出すとエラー
print(animal) 

# dog
# ---------------------------------------------------------------------------
# NameError                                 Traceback (most recent call last)
# Input In [2], in <cell line: 9>()
#       7 function()
#       8 #関数の外から呼び出すとエラー
# ----> 9 print(animal)

# NameError: name 'animal' is not defined

また、関数の中でグローバル変数と同じ名前のローカル変数を宣言した場合、呼び出しより先に宣言しないとエラーになります。これは冒頭でも書いたように関数内ではまずはローカル変数を優先して参照しようとする性質があるためです。

animal = 'cat'

def function():
    #後続のローカル変数dogを優先して参照しようとするためエラーになる
    print(animal)
    animal = 'dog'

function()

#  ---------------------------------------------------------------------------
#  UnboundLocalError                         Traceback (most recent call last)
#  Input In [4], in <cell line: 9>()
#        6     animal = 'dog'
#        8 #ローカル変数が出力される
#  ----> 9 function()

#  Input In [4], in function()
#        3 def function():
#        4     #後続のローカル変数dogを優先して参照しようとするためエラーになる
#  ----> 5     print(animal)
#        6     animal = 'dog'

# UnboundLocalError: local variable 'animal' referenced before assignment

関数内からグローバル変数を書き換える場合は、globalキーワードを使用します。

animal = 'cat'

def function():
    #グローバル変数のanimalをdogに上書き
    global animal 
    animal = 'dog'
    print(animal)

#ローカル変数が出力される
function()    
#animalがdogに上書きされた    
print(animal)

# dog
# dog

その他小技

globas()メソッドを使うとグローバル変数と元々Pythonが用意してくれているオブジェクトを表示できます。
locals()メソッドを使うとローカルに用意されたオブジェクトを表示できます。

animal = 'cat'

def function():
    animal = 'dog'
    #ローカルに用意されたオブジェクトを表示
    print(locals())

#グローバル変数と元々Pythonが用意してくれているオブジェクトを表示 
print(globals())
function()

#globals()の結果
# {'__name__': '__main__', '__doc__': 'Automatically created module for IPython interactive environment', '__package__': None, '__loader__': None, '__spec__': None, '__builtin__': <module 'builtins' (built-in)>, '__builtins__': <module 'builtins' (built-in)>, '_ih': ['', "animal = 'cat'\n\ndef function():\n    animal = 'dog'\n    #ローカルに用意されたオブジェクトを表示\n    print(locals())\n\n#グローバル変数と元々Pythonが用意してくれているオブジェクトを表示 \nprint(globals())\nfunction()"], '_oh': {}, '_dh': [PosixPath('/Users/mhaga/Keiba_AI')], 'In': ['', "animal = 'cat'\n\ndef function():\n    animal = 'dog'\n    #ローカルに用意されたオブジェクトを表示\n    print(locals())\n\n#グローバル変数と元々Pythonが用意してくれているオブジェクトを表示 \nprint(globals())\nfunction()"], 'Out': {}, 'get_ipython': <bound method InteractiveShell.get_ipython of <ipykernel.zmqshell.ZMQInteractiveShell object at 0x7fdae5451160>>, 'exit': <IPython.core.autocall.ZMQExitAutocall object at 0x7fdae546d0a0>, 'quit': <IPython.core.autocall.ZMQExitAutocall object at 0x7fdae546d0a0>, '_': '', '__': '', '___': '', '_i': '', '_ii': '', '_iii': '', '_i1': "animal = 'cat'\n\ndef function():\n    animal = 'dog'\n    #ローカルに用意されたオブジェクトを表示\n    print(locals())\n\n#グローバル変数と元々Pythonが用意してくれているオブジェクトを表示 \nprint(globals())\nfunction()", 'animal': 'cat', 'function': <function function at 0x7fdae53bc4c0>}
#locals()の結果
# {'animal': 'dog'}

参考資料

この記事はUdemyのPython+FlaskでのWebアプリケーション開発講座!!~0からFlaskをマスターしてSNSを作成する~という講座と現役シリコンバレーエンジニアが教えるPython 3 入門 + 応用 +アメリカのシリコンバレー流コードスタイルという2つの講座を参考にさせていただき、作成しました。

Python+FlaskでのWebアプリケーション開発講座!!~0からFlaskをマスターしてSNSを作成する~

Udemyより抜粋

当講座は最低限のWeb開発の知識を知っていることが前提とはなりますが、とにかくPythonの説明とFlask開発の為の説明が充実しているのでおすすめです。
28時間に及ぶ長丁場の講座にはなりますが、絶対に聞く価値がある講座です。
これをマスターすればPythonでどんなアプリケーションでも作ることができると思います。

当講座のおすすめポイントを以下にまとめておきます。

当講座のおすすめポイント

とにかく説明が充実している

Webアプリ開発におけるフレームワークがなぜ有益なのか知ることができる

セキュリティ対策、Ajaxなどの技術も知れる

現役シリコンバレーエンジニアが教えるPython 3 入門 + 応用 +アメリカのシリコンバレー流コードスタイル

画像に alt 属性が指定されていません。ファイル名: a1ee3d048d6aa860662b6f58c4aa167f-1024x328.png
Udemyより抜粋

当講座はPythonの基礎から応用まで幅広く学べる講座なのでおすすめです。
この講座の講師はとにかくPythonについての知識が豊富ですし、話も適度な速さで聞き取りやすいです。さすがのシリコンバレーです。
また、最後の方に機械学習で使うライブラリについても解説があるので、データサイエンス・AIについても多少知ることができます。

当講座のおすすめポイントを以下にまとめておきます。

当講座のおすすめポイント

シリコンバレーで働いているということもあり、講師のPythonの知識が豊富

話も適度な速さで聞き取りやすい

コードの意味だけでなく、それをどう応用するかまで解説してくれる

なお、Udemyについては以下の記事でまとめていますのでご参考ください。

まとめ

ということで、今回はPythonの変数の名前空間とスコープについて解説しました。
短い記事ですがこのことを知っておかないとアプリケーション開発がスムーズに進まないので知っておく必要があると思います。
では、今回はここまでとさせていただきます。