Pythonにおけるデバッグについて【初心者向け解説記事】
Workteria(ワークテリア)では難易度の高いものから低いものまで、スキルや経験に合わせた案件を多数揃えています。会員登録は無料ですので、ぜひ会員登録してご希望の案件を探してみてください!
フリーランス/正社員のエンジニアとして活躍するには、ご自身のスキルや経験に合わせた仕事を選ぶことが大切です。ご希望の案件がみつからない場合はお気軽にお問い合わせください!ユーザ満足度の高いキャリアコンサルタントが在籍していますので、希望条件や悩み事などなんでもご相談ください。ご希望にピッタリの案件をご紹介させていただきます。
Pythonにおけるデバッグとは?
デバッグとは、プログラムの誤り(バグ)を見つけ出し、それを修正する作業のことを指します。全てにおいて完璧な人間がいないように、完璧なプログラマーもいません。誰であってもどこかでバグを引き起こすことがあるものです。バグはプログラムの動作に影響を及ぼす可能性があり、プログラムが意図した通りに動作しない原因となるため、デバッグはソフトウェア開発において不可欠な作業となります。
デバッグの基本的な概念
プログラムがエラーを出力したり、期待した結果と異なる動作を示したりした場合、デバッグを行いバグを修正することで、問題を解決します。デバッグのプロセスは主に、バグの特定、問題の原因の分析、解決策の実装、修正のテストの4つのステップから成り立っています。
デバッグが必要な理由
バグはプログラムの動作を不安定にするだけでなく、データの破損やセキュリティの問題を引き起こす可能性もあります。したがって、プログラムの正確さと信頼性を確保するためには、デバッグが不可欠となります。また、プログラムがどのように動作しているかを理解する上でも、デバッグは有用な手段です。
Pythonのデバッグツール紹介
Pythonにはデバッグを助けるための多くのツールが用意されています。それらのツールを利用することで、効率的にデバッグを行うことが可能となります。
print関数を用いたデバッグ
print関数は最も基本的なデバッグツールの一つです。変数の値を出力して確認することで、プログラムの途中経過を把握することが可能です。
# 変数の値を確認する例
var = "Hello, World!"
print(var)
loggingモジュールの利用
print関数に比べて、loggingモジュールはより高度な出力制御やエラーレベルの設定などが可能で、デバッグだけでなく、実行時の挙動の記録にも使用できます。
import logging
logging.basicConfig(level=logging.DEBUG)
logging.debug("This is a debug message")
logging.info("This is an info message")
logging.warning("This is a warning message")
logging.error("This is an error message")
logging.critical("This is a critical message")
これを実行すると、以下のように出力されます。
DEBUG:root:This is a debug message
INFO:root:This is an info message
WARNING:root:This is a warning message
ERROR:root:This is an error message
CRITICAL:root:This is a critical message
pdb(Pythonデバッガ)の使用
pdbは、Pythonのデバッグツールの一つです。pdbを利用すると、プログラムを逐次実行したり、特定の場所(ブレークポイント)でプログラムの実行を一時停止させて変数の値を確認したり、ステップごとにプログラムを実行したりすることができます。
pdbの開始
以下のように、デバッグを開始する場所にpdb.set_trace()を挿入することでデバッガを起動できます。
import pdb
def add_numbers(x, y):
sum = x + y
pdb.set_trace() # ここでデバッガが開始される
return sum
add_numbers(1, 2)
pdbコマンド
デバッガを開始すると、対話型プロンプトが表示されます。ここでは、以下のようなコマンドを使ってデバッグを行うことができます。
- n(ext): 次の行に移動します。
- s(tep): 関数内部に入るためのコマンドです。
- c(ontinue): 次のブレークポイントまで実行を続けます(あるいはプログラムの終了まで)。
- q(uit): デバッガを終了します。
- p(rint): 引数に続く式を表示します。例えばp xを入力すれば、変数xの値を表示します。
- l(ist): 現在の位置周辺のコードを表示します。
- h(elp): ヘルプを表示します。具体的なコマンドの説明を見るためにはh <コマンド>と入力します。
PyCharmなどの統合開発環境(IDE)を用いたデバッグ
PyCharmなどの統合開発環境(IDE)にはデバッガが組み込まれており、グラフィカルなインターフェイスからデバッグ操作を行うことができます。ブレークポイントの設定や変数の値の確認、逐次実行などを直感的に行うことができます。
デバッグ手順の一例
リスト内の数値を合計する関数にバグがあるとします(実際はsum関数およびavg関数を用いることで容易に実装できます)。pdbを使用してデバッグをしてみましょう。
def complex_sum(num_list):
total = 0
for num in num_list:
total += num
average = total / len(num_list)
return f"合計:{total}, 平均:{average}"
print(complex_sum([1, 2, 3, 4, 5]))
print(complex_sum([]))
これを実行すると以下のように出力されます。
合計:15, 平均:3.0
Traceback (most recent call last):
File "C:/***/***.py", line 9, in <module>
print(complex_sum([]))
File "C:/***/***.py", line 5, in complex_sum
average = total / len(num_list)
ZeroDivisionError: division by zero
デバッグの準備: デバッグ対象の特定
最初に、デバッグの対象となるバグを特定します。エラーメッセージやプログラムの出力、挙動などから、バグがどの部分に存在するかを探し出します。
上記の例では、9行目でエラーが発生していることがわかります。そして、その9行目のエラーは5行目のコードによって引き起こされていることがわかります。
「ZeroDivisionError」が出ていますので、数字を0で割ったことが原因だと考えられます。
ブレークポイントの設定
デバッガにはブレークポイントという機能があり、ここでプログラムの実行を一時停止し、その時点での変数の値などを確認できます。デバッグ対象のコードの前後にブレークポイントを設定し、どのようにバグが発生するかを探ります。
import pdb
def complex_sum(num_list):
total = 0
for num in num_list:
total += num
pdb.set_trace() # ブレークポイントを設置
average = total / len(num_list)
return total, average
print(complex_sum([1, 2, 3, 4, 5]))
print(complex_sum([]))
変数の監視・評価
デバッガを用いて、コードの実行中に変数の値がどのように変化するかを確認します。これにより、変数の値が期待したものになっているか、途中で不適切な値になっていないかをチェックします。
上記のコードを実行すると、以下のようにコンソールに出力されます。
C:/***/***.py
> C:/***/***.py(8)complex_sum()
-> average = total / len(num_list)
(Pdb)
コンソールに「p total」および「p len(num_list)」と入力すると、以下のように出力されます。
(Pdb) p total
0
(Pdb) p len(num_list)
0
num_listが空であるため、len(num_list)が0であることが分かり、これがZeroDivisionErrorを引き起こしている原因であることが確認できます。
コードの修正
これらの情報を元に、空のリストを与えられたときは別の処理を行うように修正します。
def complex_sum(num_list):
if len(num_list) == 0:
return 0, 'Error: Empty List'
total = 0
for num in num_list:
total += num
average = total / len(num_list)
return total, average
print(complex_sum([])) # (0, 'Error: Empty List')
デバッグ時の注意点
デバッグを行う際には、以下のような点に注意することが重要です。
常に最新のコードを使用する
コードの修正が頻繁に行われる開発環境では、常に最新のコードを使用してデバッグを行うことが重要です。古いコードでデバッグを行ってしまうと、すでに修正されたバグを再修正してしまうことになります。
デバッグ対象を限定する
バグの原因を追求する際には、対象となる範囲を限定することが重要です。問題のある部分を特定し、その部分のみを対象にデバッグを行うことで、効率的にバグを特定し、修正することができます。
変更を小さく、一つずつ行う
コードの変更を行う際には、小さな変更を一つずつ行うことが重要です。大きな変更を一度に行うと、新たなバグが発生する可能性があります。小さな変更を一つずつ行い、その都度テストを行うことで、バグの導入を防ぐことができます。
分からない時は、他の人に聞いてみる
チームで開発を行っている場合は、一人がバグについて何時間も悩んでいると作業を停滞させてしまいます。30分など自分で調査を行う時間を決めて、それでも解決しない場合は上長やチームメンバなど他人に聞くのが一番です。
バグについて他人に共有する際は、ただバグが起きたことを伝えるのではなく、バグの種類や実行ログ、関連するソースコードなど必要な情報をそろえましょう。
また、個人で開発を行っている場合でも、StackOverFlowなどの質問サイトに質問を行うことで解決できることもあります。最近はChatGPTなどの大規模言語モデルを活用する方法もあります。
まとめ
デバッグはプログラムのエラーを見つけ、修正する重要なプロセスです。Pythonではprint関数やloggingモジュール、pdb、IDEなどのツールを利用してデバッグを行うことができます。デバッグを効率的に行うためには、最新のコードを使用し、デバッグ対象を限定し、小さな変更を一つずつ行うことが重要です。
また、どうしても解決できない場合は勇気をもって他の人を頼りましょう。「聞くは一時の恥、聞かぬは一生の恥」といいます。
【著者】
フォワードソフト株式会社のエンジニア。Java、Python、JavaScript、C#などの言語の他、クラウドやネットワーク技術を勉強しています。PythonやVBAを使った自動化で楽をする方法を考えるのが好きです。 最近はジェネレーティブAIの業務利用に関する検証を行っています。 資格を通じて知識を吸収することを心がけており、セキュリティスペシャリスト、データベーススペシャリスト、応用情報技術者、Oracle Certified Java Programmer Gold SE 11、Pythin3 エンジニア認定試験、HTML5プロフェッショナル認定試験レベル2、AWSプラクティショナーなどの情報資格を保有しています。
正社員/フリーランスの方でこのようなお悩みありませんか?
- 自分に合う案件を定期的に紹介してもらいたい
- 週2、リモートワークなど自由な働き方をしてみたい
- 面倒な案件探し・契約周りは任せて仕事に集中したい
そのような方はぜひ、Workteriaサイトをご利用ください!
定期的にご本人に合う高額案件を紹介
リモートワークなど自由な働き方ができる案件多数
専属エージェントが契約や請求をトータルサポート