Python
 Computer >> コンピューター >  >> プログラミング >> Python

Pythonの関数は引数を参照渡しする?id()による検証方法を解説

Pythonの関数における引数の受け渡しの仕組み

Pythonでは、関数の引数は常に参照渡し(正確には「オブジェクトへの参照を受け渡す」方式)で行われます。つまり、関数に渡されるのはオブジェクトそのものではなく、そのオブジェクトへの参照です。この挙動は、実際の引数・仮引数・戻り値の各オブジェクトに対してid()を確認することで簡単に検証できます。

検証用サンプルコード

def foo(x):
  print ("id of received argument",id(x))
  x.append("20")
  return x

a = ["10"]
print ("id of argument before calling function",id(a))
b = foo(a)
print ("id of returned object",id(b))
print (b)
print (a)

実行結果

このコードを実行すると、関数呼び出し前のafoo()内のx、そして戻り値bid()がすべて同一の値になることが確認できます。

id of argument before calling function 1475589299912
id of received argument 1475589299912
id of returned object 1475589299912

なぜ3つのidが一致するのか

リストのようなミュータブル(変更可能)なオブジェクトの場合、関数内で行った変更は元のオブジェクトにも直接反映されます。上記の例では、foo()内でx.append("20")を実行しているため、呼び出し元のリストaにも要素「20」が追加されます。これは、xaがメモリ上の同じオブジェクトを指しているからです。

一方、数値や文字列などのイミュータブル(変更不可)なオブジェクトを引数に渡した場合、関数内で再代入を行っても呼び出し元の変数には影響しません。これは、変数が「新しいオブジェクトへの参照」に差し替えられるだけで、元のオブジェクト自体は変更されないためです。

まとめ

Pythonの引数渡しは「オブジェクトへの参照を渡す」方式であり、ミュータブルなオブジェクトは関数内での変更が呼び出し元に波及します。意図しない副作用を避けたい場合は、list.copy()copy.deepcopy()などでコピーを作成してから渡すと安全です。

  1. Pythonのラムダ関数(lambda)とは?基本構文と使い方を実例付きで解説

    Pythonのラムダ関数(lambda関数)は、実行時にその場で生成される「名前を持たない匿名関数」です。通常、1行で記述され、特定の名前に束縛されることなく定義できます。 ラムダ関数には以下のような特徴があります。 関数の定義をその場で返すことができる return文を含まず、常に式(expression)を評価して結果を返す 関数オブジェクトが期待される場所なら、どこにでもラムダ式を記述できる ラムダ関数を使う場面 ある関数が一度しか使わず、呼び出し箇所も一箇所だけであるような場合、ラムダ関数が便利です。このようなケースでは、わざわざdef文で関数に名前を付けて定義する必要はありません

  2. Pythonで関数を引数として渡す方法をわかりやすく解説

    Pythonでは、関数もオブジェクトの一つとして扱われるため、他の関数の引数として渡すことができます。この仕組みを活用すると、柔軟で再利用性の高いコードを書くことができます。map()関数を使った例Pythonが標準で提供している代表的な例が、第一引数に関数を受け取る map() 関数です。map(function, iterable, ...) — iterable(イテラブル)の各要素に対してfunctionを適用し、その結果を返します。もちろん、独自に定義したカスタム関数でも、引数として関数を受け取るように実装できます。自作関数sqr(x)を引数として渡すここでは、リストの各要素を2乗す