【レッスンF-1】可変長引数argsと*kwargsの使い方と実践例|Python学習
Flaskの学習に入る前にもう少しだけPythonの学習をしましょう。
今回は可変長引数について見ていきます。
Lesson1:基礎文法編
Lesson2:制御構造編
Lesson3:関数とスコープ編
Lesson4:データ構造編
Lesson5:オブジェクト指向編
Lesson F:Flask学習の準備編
・Lesson F-2:可変長引数を理解しよう ◁今回はココ
・Lesson F-2:デコレーターを理解しよう
可変長引数とは?|*args
と**kwargs
の使い方と実例
ここから可変長引数の説明に入ります。
ページ下部にはこのページで出てくる用語の意味をまとめた 用語集 もありますので、分からない言葉が出てきたらそちらも参考にしてください。
関数に渡す引数の数が状況によって異なる場合、どうすれば柔軟に対応できるでしょうか?
Pythonでは「可変長引数」を使うことで、関数の呼び出し方に自由度を持たせることができます。
可変長引数の概要|複数の引数を柔軟に受け取る方法
可変長引数とは、関数に渡す引数の数を制限せず、好きなだけ渡せる仕組みのことです。
通常の引数は呼び出すたびにすべての値を明示的に指定する必要がありますが、可変長引数を使うと、「0個〜複数個」の引数を渡せるようになります。
Pythonでは次の2種類の可変長引数があります:
*args
:位置引数を可変で受け取る**kwargs
:キーワード引数を可変で受け取る
argsやkwargsの部分は任意に決めることができます。
アスタリスクの数に意味があり、「*」はまとめてタプルに、「**
」はまとめて辞書に変換されます。
可変長引数の基本構文とルール
以下が、可変長引数を使った関数定義の基本形です:
def func(*args): # 可変長(数を自在に決めれる)の位置引数を持つ関数funkを定義 print(args) def func(**kwargs): # 可変長のキーワード引数を持つ関数funkを定義 print(kwargs)
*args
は複数の位置引数を1つのタプルとして受け取ります。**kwargs
は複数のキーワード引数を1つの辞書として受け取ります。
また、通常の引数と併用することもできます:
def greet(greeting, *names): # 1つ目の引数はgreeting。2つめ以降は可変長の引数names for name in names: print(f"{greeting}, {name}!") greet("Hello", "Alice", "Bob") # greetingにHelloを渡し、可変長引数namesに2つの名前を渡す # 2つの名前はタプルに変換され、greet関数はそれぞれに対して実行される
このコードを実行すると、以下のように出力されます。
Hello, Alice! Hello, Bob!
Pythonでは以下の順序を守って引数を定義する必要があります:
- 通常の位置引数
*args
- デフォルト付きのキーワード引数
**kwargs
def funk(pos1, pos2, *args, kwd1, kwd2, **kwargs)
可変長引数*args
と**kwargs
の使用例とその解説
いくつかの使用例を以下に紹介します。
例1:*args
の使用
def add_numbers(*args): return sum(args) print(add_numbers(1, 2, 3)) # 6 print(add_numbers(10)) # 10 print(add_numbers()) # 0
この関数は、渡されたすべての数値を合計します。args
はタプルとして受け取られます。
例2:**kwargs
の使用
def print_info(**kwargs): for key, value in kwargs.items(): print(f"{key}: {value}") print_info(name="Taro", age=20) # name: Taro # age: 20
この関数は任意のキーワード引数を受け取り、キーと値を表示します。
例3:引数の混在
def profile(title, *args, **kwargs): print(f"== {title} ==") print("Names:", args) print("Details:", kwargs) profile("User Info", "Alice", "Bob", age=25, city="Tokyo") # == User Info == # Names: ('Alice', 'Bob') # Details: {'age': 25, 'city': 'Tokyo'}
この例ではtitle
が通常引数、args
が名前のリスト、kwargs
が詳細情報となっています。
まとめ
可変長引数は、関数を柔軟かつ汎用的に作るための重要なテクニックです。
*args
:任意の数の位置引数をタプルとして受け取る**kwargs
:任意のキーワード引数を辞書として受け取る- 可変長引数を使う際には引数の順序に注意する必要がある
引数の順序や使い方を正しく理解することで、より読みやすく便利な関数が書けるようになります。
練習問題:買い物リストと合計金額を表示しよう
買い物リストの品目と、商品価格の合計を表示するプログラムを作成しましょう。
品目の名前や価格の数は毎回変わる可能性があります。
そこで、可変長引数を使って関数に複数の値を柔軟に渡せるようにすることが今回の学習目標です。
問題の詳細条件
以下の要件に従ってコードを完成させてください。
- 関数
show_shopping_list
を定義し、可変長引数*items
を使って複数の文字列(品目名)を受け取ること。 show_shopping_list
の中では、「買い物リストを表示します:」というメッセージを表示し、その後受け取った各品目を- 品目名
の形式で1行ずつ表示すること。- 関数
calculate_total_price
を定義し、可変長引数*prices
を使って複数の数値(商品価格)を受け取ること。 calculate_total_price
の中では、受け取った価格をすべて合計し、その合計値を返すこと。show_shopping_list("たまご", "パン", "牛乳")
を実行して、買い物リストを表示すること。calculate_total_price(120, 350, 220)
を実行して、その戻り値をtotal
に代入し、「合計金額は ○○ 円です。」の形式で出力すること。
ただし、以下のような実行結果となるコードを書くこと。
買い物リストを表示します: - たまご - パン - 牛乳 合計金額は 690 円です。
【ヒント】難しいと感じる人だけ見よう
1からコードを組み立てることが難しい場合は、以下のヒントを開いて参考にしましょう。
- ヒント1【コードの構成を見る】
-
正解のコードは上から順に以下のような構成となっています。
(※下記の□はコード内のインデントを表しています)1:関数show_shopping_listの定義(可変長引数*itemsを受け取る)
□ 「買い物リストを表示します:」というメッセージを出力
□ for文でitems内の各値を順に取り出し、「- 品目名」の形式で出力
2:関数calculate_total_priceの定義(可変長引数*pricesを受け取る)
□ 変数totalを0で初期化
□ for文でprices内の各値を順に取り出してtotalに加算
□ 合計金額totalをreturnで返す
3:関数show_shopping_listを呼び出し、「たまご」「パン」「牛乳」を引数として渡す
4:関数calculate_total_priceを呼び出し、120・350・220を引数として渡し、その結果を変数totalに代入
5:print文で「合計金額は ○○ 円です。」の形式で合計を出力
- ヒント2【穴埋め問題にする】
-
以下のコードをコピーし、コメントに従ってコードを完成させて下さい。
"""【穴埋め問題1】 ここに関数show_shopping_listを定義し、可変長引数*itemsを受け取り、 「買い物リストを表示します:」というメッセージと、渡された各品目を「- 品目名」の形式で出力するコードを書いてください。 """ """【穴埋め問題2】 ここに関数calculate_total_priceを定義し、可変長引数*pricesを受け取り、 すべての数値を合計し、合計値を返すコードを書いてください。 """ # 実行例①:文字列を複数渡して表示する show_shopping_list("たまご", "パン", "牛乳") # 実行例②:価格を複数渡して合計を計算する total = calculate_total_price(120, 350, 220) print("合計金額は", total, "円です。")
このヒントを見てもまだ回答を導き出すのが難しいと感じる場合は、先に正解のコードと解説を見て内容を理解するようにしましょう。
問題の答え合わせと解説
この問題の一つの正解例とそのコードの解説を以下に示します。
一つの正解例
例えば以下のようなプログラムが考えられます。
- 正解コード
-
# 複数の品目(文字列)を受け取り、それらを表示する関数 # 可変長引数 *items を使って、いくつでも値を受け取れるようにする def show_shopping_list(*items): # items には渡されたすべての値がまとまって入ってくる print("買い物リストを表示します:") for item in items: print("- " + item) # 複数の価格(整数)を受け取り、合計を計算する関数 def calculate_total_price(*prices): # prices も可変長引数として受け取り、合計を出す total = 0 for price in prices: total += price return total # 実行例①:文字列を複数渡して表示する show_shopping_list("たまご", "パン", "牛乳") # 実行例②:価格を複数渡して合計を計算する total = calculate_total_price(120, 350, 220) print("合計金額は", total, "円です。")
正解例の詳細解説
このコードは、
コードをブロックごとに分けて説明していきます。
- 詳細解説
-
このPythonコードでは可変長引数を使って、「買い物リストを表示する関数」と「複数の価格の合計を計算する関数」を定義し、実際に使っています。
それぞれのコードブロックごとに使われている機能を説明していきましょう。
関数
show_shopping_list
の定義def show_shopping_list(*items): # items には渡されたすべての値がまとまって入ってくる print("買い物リストを表示します:") for item in items: print("- " + item)
この関数では、
*items
という書き方が使われています。これは 「可変長引数」 という文法で、関数に渡す引数の数を自由に変えられるようにするものです。*items
と書くと、渡された複数の値(この場合は品物の名前)が、まとめてitems
という変数に格納されます。for item in items:
で、その中身をひとつずつ取り出して表示しています。
たとえば、
show_shopping_list("りんご", "みかん", "バナナ")
のように書けば、3つの品目が表示されます。品目の数が何個であっても関数は正しく動作します。関数
calculate_total_price
の定義def calculate_total_price(*prices): # prices も可変長引数として受け取り、合計を出す total = 0 for price in prices: total += price return total
こちらも
*prices
を使った 可変長引数 の例です。この関数は、複数の数値(価格)を引数として受け取り、それらの合計を計算して返す役割を持っています。
*prices
によって、関数を呼ぶときに渡された任意の数の引数がprices
という変数にまとめられます。for price in prices:
でそれぞれの価格を順番に取り出して、total
に加算しています。
「値段がいくつになるかわからないけど全部足したい」といった時にとても便利です。
関数の呼び出しと出力
# 実行例①:文字列を複数渡して表示する show_shopping_list("たまご", "パン", "牛乳") # 実行例②:価格を複数渡して合計を計算する total = calculate_total_price(120, 350, 220) print("合計金額は", total, "円です。")
ここでは、先ほど定義した2つの関数を実際に使っています。
show_shopping_list("たまご", "パン", "牛乳")
は、買い物リストの品目を表示。calculate_total_price(120, 350, 220)
は、3つの価格の合計(690)を求めています。
このように、関数の使い方を覚えると、同じ処理を何度も簡単に再利用できるようになります。
まとめ
このコードでは可変長引数という重要なPython文法を学びました。
可変長引数を使うと、関数をもっと柔軟にして、いろいろな数の引数に対応できるようになります。
プログラミングのコツは「少しずつ使って慣れること」。ぜひ手を動かして試してみてください!
Python用語集|可変長引数編
今回の記事で出てきた用語・関数などを一覧で紹介します。
このサイトに出てくる 全てのPython用語をまとめた用語集 も活用してください。
Python用語 | 定義・使い方の概要 | 解説記事へのリンク |
---|---|---|
引数 | 関数に渡す値。関数定義時には仮引数、呼び出し時には実引数として使われる | Lesson3-1 |
可変長引数 | 引数の数が不定な場合に使用する構文。*args や **kwargs を使って複数の値を受け取れる | 本記事 |
*args | 位置引数の可変長リストを受け取るための記法。関数に複数の位置引数を渡したいときに使う | 本記事 |
**kwargs | キーワード引数の可変長辞書を受け取るための記法。引数名と値のペアをまとめて受け取れる | 本記事 |
位置引数 | 関数呼び出し時に、引数の順序によって渡される通常の引数 | なし |
FAQ|Pythonの可変長引数に関するよくある質問
- Q1. Pythonの可変長引数はどんな場面で使うと便利ですか?
-
可変長引数は、関数に渡す引数の数が毎回異なるような場面で便利です。例えば、買い物リストやログ出力など、ユーザーの入力数が不定な処理に最適です。コードの柔軟性が増し、汎用的な関数を作成できます。
- Q2. *argsと**kwargsは同時に使うことができますか?
-
はい、argsと*kwargsは同じ関数内で同時に使うことが可能です。ただし、順番には注意が必要で、定義時は「通常の引数 → *args → キーワード引数 → **kwargs」の順で記述します。このルールを守ることでエラーを防げます。
- Q3. 可変長引数を使うと処理が遅くなることはありますか?
-
基本的にはほとんどのケースでパフォーマンスに大きな影響はありません。ただし、大量のデータを渡す処理や頻繁に呼び出される関数では、引数の取り扱い方次第で微小な差が出ることがあります。適切な使い方を心がけましょう。