チュートリアル: Visual Studio を使用して C++ コードをデバッグする
この記事では、段階的なチュートリアルで Visual Studio デバッガーの機能について説明します。 アプリケーションをデバッグするときは、通常、デバッガーがアタッチされた状態でアプリを実行します。 デバッガーには、プログラムの実行中にコードが何を行っているかを調べるさまざまな方法が用意されています。 コードをステップ実行し、変数に格納されている値を確認し、変数にウォッチを設定して、値がいつ変化するかを確認できます。 デバッガーは、コードの実行パスを確認し、コードの分岐が実行されていることを確認するのに役立ちます。
このチュートリアルでは、次の操作を行います。
- デバッガーを起動し、ブレークポイントで一時停止する
- デバッガーでコードをステップ実行するコマンドについて説明します
- データ ヒントとデバッガー ウィンドウで変数を検査する
- コールスタックを調べる
デバッグを初めて使用する場合は、このチュートリアルを開始する前に、初心者向けのデバッグ を読んでください。 デバッガー機能の上位レベルのビューが必要な場合は、「デバッガーのを最初に確認する」を参照してください。
前提 条件
Visual Studio 2022
バージョン 17.12 以降。C++ ワークロードを使用したデスクトップ開発がインストールされています。 - Visual Studio 2022 を無料でインストールするには、Visual Studio のダウンロード ページに移動します。
- Visual Studio を無料でインストールするには、リリースとビルド履歴の ページで詳細を確認してください。
Visual Studio が既にある場合は、対話型開発環境 (IDE) 内からワークロードをインストールできます。
[ツール]>[ツールと機能を取得] を選択します。
Visual Studio インストーラーで、ワークロード タブを選択します。
[C++ によるデスクトップ開発] ワークロードを選んでから、[変更] を選びます。
プロンプトに従ってインストールを完了します。
このチュートリアルでは、C++ デモ アプリケーションを使用し、C++ 構文を示すスクリーンショットを示します。 示されている機能のほとんどは、Visual Studio でサポートされている C#、Visual Basic、F#、Python、JavaScript、およびその他の言語にも適用できます。 注意すべきいくつかの制限事項があります。
F#: 編集続行 機能はサポートされていません。
F# と JavaScript: Autos ウィンドウはサポートされていません。
プロジェクトを作成する
Visual Studio で C++ コンソール アプリケーション プロジェクトを作成するには、次の手順に従います。 プロジェクトの種類には、すぐに開始するために必要なすべてのテンプレート ファイルが用意されています。
Visual Studio
[スタート ] ウィンドウ ([ファイル] [スタート ウィンドウ] ) で、[新しいプロジェクト作成] を選択します。 言語 フィルターを C++に設定し、 Platform フィルターを Windowsに設定します。 [検索 ボックス コンソールと入力し、結果の一覧で コンソール アプリ テンプレートを選択します。
手記
コンソール アプリ テンプレートが表示されない場合は、[新しいプロジェクトの作成] ウィンドウからインストールできます。 「探しているものが見つかりませんか?」のセクションを検索結果の後に表示される に見つけ、[その他のツールと機能をインストールする] を選択します。 Visual Studio インストーラーで、C++ ワークロードを使用したデスクトップ開発 を選択し、インストールを更新します。 詳細については、「前提条件の」セクションを参照してください。 [次 を選択して、構成ページに進みます。
新しいアプリの [プロジェクト名] と [ソリューション名] に「get-started-debugging」と入力します。 既定の Location を選択するか、環境内の別のパスを参照します。
[Create] を選択して、新しい Node.js プロジェクトを作成します。
Visual Studio によって新しいプロジェクトが作成され、ソリューション エクスプローラーでプロジェクト階層
アプリケーションを作成する
コード エディターで get-started-debugging.cpp ファイルを編集して、プロジェクト用の新しいアプリケーションを作成します。
テンプレートによって提供される既定のコンテンツを次のコードに置き換えます。
#include <string>
#include <vector>
#include <iostream>
void SendMessage(const std::wstring& name, int msg)
{
std::wcout << L"Hello, " << name << L"! Count to " << msg << std::endl;
}
int main()
{
std::vector<wchar_t> letters = { L'f', L'r', L'e', L'd', L' ', L's', L'm', L'i', L't', L'h' };
std::wstring name = L"";
std::vector<int> a(10);
std::wstring key = L"";
for (int i = 0; i < letters.size(); i++)
{
name += letters[i];
a[i] = i + 1;
SendMessage(name, a[i]);
}
std::wcin >> key;
return 0;
}
デバッガーを起動する
これで、更新されたコードのデバッグを開始する準備ができました。
デバッグ セッションを開始するには、F5 を選択するか、デバッグ > 開始を選びます。 [デバッグ] ツール バーで [デバッグの開始]
を選択することもできます (実線の緑色の矢印アイコン)。
F5 キーボード ショートカットは、デバッガーがアプリ プロセスにアタッチされた状態でアプリケーションを起動しますが、コードで確認する特別な機能はまだありません。 アプリが読み込まれるだけで、コンソールの出力が表示されます。
Hello, f! Count to 1 Hello, fr! Count to 2 Hello, fre! Count to 3 Hello, fred! Count to 4 Hello, fred ! Count to 5 Hello, fred s! Count to 6 Hello, fred sm! Count to 7 Hello, fred smi! Count to 8 Hello, fred smit! Count to 9 Hello, fred smith! Count to 10
このチュートリアルの後半では、デバッガーでこのアプリを詳しく見て、その他のデバッグ機能を確認します。
デバッグ ツール バーの Stop
(赤い四角形のアイコン) を選択してデバッガーを停止します。 Shift + F5 キーボード ショートカットを使用することもできます。
実行中のアプリケーションのコンソール ウィンドウで任意のキーを選択し、enter
選択してウィンドウを閉じます。
ブレークポイントを設定してデバッガーを起動する
ブレークポイントを設定し、デバッガーで選択したポイントで一時停止してみてください。
コード エディターで get-started-debugging.cpp ファイルに戻り、
main
関数のfor
ループを見つけます。for (int i = 0; i < letters.size(); i++) { name += letters[i]; a[i] = i + 1; SendMessage(name, a[i]); }
コード ステートメント
name += letters[i];
を含む行の左側の余白を選んで、そのステートメントの行にブレークポイントを設定します。 Visual Studio は、ブレークポイントの設定を示すために、余白に赤い円を追加します。
ヒント
コード行にカーソルを置き、F9 を選択して、その行のブレークポイントを切り替えることもできます。
ブレークポイントは、信頼性の高いデバッグの最も基本的で重要な機能の 1 つです。 ブレークポイントは、Visual Studio で実行中のコードを中断する場所を示します。 実行が一時停止されると、変数の値を確認したり、メモリの動作を調べたり、コードの分岐が実行されているかどうかを確認したりできます。
F5
を選択するか、 [デバッグの開始] を選択して、デバッガーでアプリを起動します。Visual Studio によってアプリの実行が開始されます。 デバッガーが設定されたブレークポイントに達すると、デバッグ プロセスが一時停止します。
Visual Studio は、デバッガーが一時停止されているコード ステートメントを表すために、余白の赤いブレークポイントの円に黄色の矢印を追加します。 プログラムの実行が一時停止され、指定されたステートメントが処理を待機しています。
手記
F5 アクションは、アプリケーションの現在の実行状態を基準にしています。 アプリが実行されておらず、F5
選択した場合、デバッガーはアプリを起動し、最初に設定されたブレークポイントに達するまで実行を続行します。 この動作は、デバッグ>デバッグの開始 コマンドにマップされます。 アプリが既に実行されていて、F5 選択した場合、デバッガーが次のブレークポイントまたはプログラムの終了に達するまでアプリの実行が続行されます。 この動作は、デバッグ>Continue コマンドにマップされます。
ブレークポイントは、詳細に調べるコード行またはコードセクションがわかっている場合に便利な機能です。 条件付きブレークポイントなど、設定できるさまざまな種類のブレークポイントについては、「適切な種類のブレークポイントを使用する」を参照してください。
デバッガーでコードをステップ実行する
デバッガーでコードを参照する便利な方法は、
次の手順では、ステップ コマンドでキーボード ショートカットを使用してコードをすばやく操作する方法について説明します。 (同等のメニュー アクションはかっこで示されています)。
デバッガーでアプリを起動するには、F5
を選択するか、[デバッグの開始] を選択します。 main
関数のfor
ループでデバッガーが一時停止している間に、F11 (デバッグ > ステップ イン) 2 回選択して、SendMessage
メソッドの呼び出しに進みます。F11 を 2 回選択した後、コード ステートメントの
SendMessage(name, a[i]);
まで実行が続行されます。もう一度 F11
選択して、 メソッドにステップ インします。 黄色のポインターが
SendMessage
メソッドに進むことがわかります。F11 キーボード ショートカットを使用すると、ステップ イン コマンドが開始され、アプリの実行が一度に 1 ステートメントずつ進みます。 実行フローを最も詳細に調べるのに適した方法です。 既定では、デバッガーは非ユーザー コードをスキップします。 より詳しい情報については、「Just My Code」を参照してください。 このチュートリアルの後半では、コードをすばやく移動する方法について説明します。
SendMessage
メソッドを調べた後は、ステップ アウト コマンドを使用してデバッグを続行できます。 Shift + F11 キーを押します ([デバッグ] > [ステップ アウト])。このコマンドは、現在のメソッドまたは関数が戻るまでアプリの実行を再開 (およびデバッガーを進めます) します。
コマンドが完了すると、デバッガーは、
SendMessage
メソッド呼び出しで、main
メソッドのfor
ループで一時停止します。F11 を数回選択して、再び
SendMessage
メソッドの呼び出しに戻ります。デバッガーがメソッド呼び出しで一時停止している間に、F10 キーを押します ([デバッグ] > [ステップ オーバー])。
今回は、デバッガーが
SendMessage
メソッドにステップ インしていないことを確認してください。 F10 ショートカットを使用すると、アプリ コード内の関数やメソッドにステップインすることなくデバッガーが進みます (コードは引き続き実行されます)。SendMessage
メソッドの呼び出しで (F11 キーではなく) F10 キーを押すと、SendMessage
の実装コードをステップ オーバーします。 この方法は、現在検査する必要のない過去のコードを移動する場合に便利です。 コード内を移動するさまざまな方法の詳細については、「デバッガー内のコード内を移動する」を参照してください。
Run to Click を使用してコードを参照する
デバッガーでコードを操作するもう 1 つの方法は、Run to Click 機能を使用することです。 このアクションは、一時的なブレークポイントの設定に似ています。
デバッグ セッションを続行します。
F5
選択して、コード内のブレークポイントに進みます。 コード エディターで、
SendMessage
メソッド定義までスクロールし、std::wcout
関数にカーソルを合わせます。コード ステートメントの左側に「実行してクリック
」(緑色の矢印アイコン)が表示されるまで、カーソルを合わせて待ちます。 アイコンの上にマウス ポインターを置くと、ツールヒント "Run execution to here"が表示されます。
[クリックで実行]
を選びます。
デバッガーは、指定された位置に実行を進めます。 この例では、デバッガーは
std::wcout
関数の呼び出しに到達します。
クリックで移動 アクションは、アプリコード内の見える範囲をすばやく移動するのに便利です。 この機能は、コード エディターで開いている任意のファイルで使用できます。
アプリをすばやく再起動する
デバッグ ツール バー [再起動] (円形の矢印アイコン) を選択して、アプリをすばやく再起動します。 [デバッグ]
再起動 機能は、アプリを停止してデバッガーをもう一度起動するよりも効率的です。
[再起動for
ループ内で設定したブレークポイントでデバッガーが再び停止します。
データ ヒントを使用して変数を検査する
変数の検査に役立つ機能は、デバッガーを使用する際の最も便利な利点の 1 つです。 多くの場合、問題をデバッグするときに、変数が特定の時点で予期される値を格納しているかどうかを検出しようとしています。 Visual Studio には、このタスクを完了するのに役立ついくつかの方法が用意されています。
デバッグ セッションを続行します。
name += letters[i]
ステートメントでデバッガーが一時停止している間は、letters
変数にカーソルを合わせます。 変数名の左側にある展開/折りたたみ矢印を選択し、ポップアップ メニューでそのプロパティを表示します。データ ヒント 機能には、変数に含まれるすべての要素が表示されます。 既定値
size={10}
注意してください。次に、
name
変数にカーソルを合わせると、現在の値である空の文字列 (""
) が表示されます。F5 (デバッグ>続行) を数回選択して、
for
ループを数回繰り返し実行します。 デバッガーがブレークポイントで一時停止するたびに、name
変数にカーソルを合わせ、現在の値を確認します。変数の値は、
for
ループの反復ごとに変化し、f
、fr
、fre
などの値が表示されます。
[自動変数] ウィンドウと [ローカル] ウィンドウを使用して変数を検査する
変数と値を検査するもう 1 つの方法は、Autos ウィンドウと [ローカル] ウィンドウを使用することです。 既定では、これらのウィンドウは、アプリのデバッグ中に Visual Studio IDE のコード エディターの下に表示されます。
コード エディターの下にある [自動] ウィンドウに注目してください。
デバッグ セッション中にウィンドウが表示されない場合は、Windows
Autos デバッグ 選択してウィンドウを開きます。 自動変数 ウィンドウには、現在の行または前の行で使用されているすべての変数とその現在の値が表示されます。 特定のプログラミング言語では、変数とプロパティに固有の動作を示すことができることに注意してください。 詳細については、Visual Studio 言語ガイダンスの
を参照してください。 次に、ローカル ウィンドウを見てみましょう。 既定では、このウィンドウは Autos ウィンドウの横に配置されます。
デバッグ セッション中にウィンドウが表示されない場合は、[デバッグ]
[Windows ローカル] 選択してウィンドウを開きます ローカル ウィンドウで、
letters
変数を展開して、含まれている要素を表示します。ローカル ウィンドウには、現在の スコープ、つまり現在の実行コンテキストにある変数が表示されます。
変数を監視する
特定の変数の動作を監視する場合は、ウォッチを設定できます。
コード エディターで、
デバッガーでアプリの実行中に name
変数を監視すると、その値の変化を確認できます。 他の変数ウィンドウとは異なり、ウォッチ ウィンドウには、監視している変数が常に表示されます。 監視対象の変数がスコープ内にない場合、変数名は淡色表示されます。
呼び出し履歴を調べる
Visual Studio の 呼び出し履歴 ウィンドウには、メソッドと関数が呼び出される順序が表示されます。 このウィンドウは、Eclipse などの一部の IDE のデバッグパースペクティブに似ています。 既定では、コード エディターの下のデバッグ セッション中に、呼び出し履歴が右下ペインに表示されます。
デバッガーが
for
ループで一時停止している間に、[呼び出し履歴] ウィンドウを選択して、現在の呼び出し元の構造を確認します。デバッグ セッション中にウィンドウが表示されない場合は、Windows
呼び出し履歴 デバッグ 選択してウィンドウを開きます。 F11 (デバッグ>ステップ イン) を数回押して、デバッガーが
SendMessage
メソッドで一時停止するのを確認します。呼び出し履歴 ウィンドウをもう一度見てください。
呼び出し履歴 ウィンドウで、上部の行に現在の関数 (このアプリの
SendMessage
メソッド) が表示されます。 2 行目は、SendMessage
メソッドがmain
メソッドから呼び出されたことを示しています。
呼び出し履歴は、アプリの実行フローを調べて理解するのに適した方法です。
コード行をダブルクリックして、ソース コードを参照します。 このアクションにより、デバッガーによる検査中の現在のスコープも変更されますが、デバッガーは進まれません。
[呼び出し履歴] ウィンドウでプログラミング要素の右クリック メニューにアクセスします。 たとえば、指定した関数にブレークポイントを挿入し、カーソルに対して実行を使用してデバッガーを進め、ソース コードを参照できます。 詳細については、「呼び出し履歴を表示し、デバッガーの [呼び出し履歴] ウィンドウを使用する」を参照してください。
実行フローを変更する
Visual Studio のデバッガーのもう 1 つの機能は、アプリの実行フローを変更できることです。
std::wcout
関数 実行するには、F11 (デバッグ>ステップ イン) を 2 回選択します。SendMessage
メソッドの呼び出しでデバッガーが一時停止している間に、変数の左側にある黄色の矢印 (実行ポインター) を選択してドラッグし、矢印を前のコード ステートメント (std::wcout
) に移動します。F11 をもう一度選択します。
デバッガーは、
std::wcout
関数を再実行します。 ターミナル出力でプロセスを追跡できます。実行フローを変更することで、異なるコード実行パスをテストしたり、デバッガーを再起動せずにコードを再実行したりすることができます。
注意
この機能を使用する場合は注意が必要です。 黄色の矢印を選択すると、Visual Studio のツールヒントに、実行の変更が意図しない結果を招く可能性があることを示す警告が表示されます。 シナリオによっては、他の警告も表示される場合があります。 ポインターを移動しても、アプリケーションを以前のアプリの状態に戻すことはできません。
F5
選択して、アプリの実行を完了します。
関連コンテンツ
- Visual Studio デバッガーの を最初に確認する
- Visual Studio デバッガー を使用してコード間を移動する
- 適切な種類のブレークポイント (.NET、.NET Framework、C++、すべての言語) を使用