エラーメッセージ+テンプレート:簡単なヒント ちょっとした歌詞
私はすぐに、このトピックがC ++と長い間友達であり、強いプログラマーにとって有用ではないことを警告しなければなりません。 私の目標は、他の人のライブラリを多数のテンプレートで使用しているときに、エラーメッセージが表示されたときにわずかなパニックに陥る小さな人々を助けることです。 実践が示すように、多くの場合、すべてが見た目ほど怖くはなく、問題が何かを理解するのに役立ちます。
このようなメモを書くというアイデアは、Boost :: Spirit2-複雑な文法、豊富なセマンティックアクション、属性値によるASTの作成などを積極的に使用するプログラムを作成する過程で生まれました。 ある時点で、多くのエラーを修正するのに1〜2分かかりましたが、同様の場合のプロジェクトの作業の開始時には、状況を分析するのに最大1時間かかることがありました。
すべてはgccでの作業に基づいて記述されていますが、used%compiler_name&を使用して類推することは難しくないと思います。
共有する時間です!
何が助けになりますか?
致命的なエラー
まず、コンパイラオプションを有効にする必要があります。これにより、エラーが致命的になります。 gcc の場合、 これらは-Wfatal-errors です。 メタプログラミングの場合、一度に複数のエラーメッセージを調べてもあまり意味がありません。最初のエラーメッセージを修正すると、多くのエラーメッセージが影響を受ける可能性があります。 そして、テキストの壁はずっと低くなります。
根
よく見ると、テンプレートエラーメッセージの構造はほぼ次のとおりです。
In file included from %header path%, from %header path%, ... from %source filename%: %header path%: In function '%full name%' %header path%: instantiated from '%full name%' ... %source filename%: instantiated from %full name% ... %header path%: error : %error description%
さらに詳しく見てみると、含まれているヘッダーファイルの階層全体を実行する「インスタンス化元」ブロックが最も大きく、最も役に立たないことがわかります。 私たちは、ライブラリ関数を呼び出してエラーが発生したことによってどのような迂回が発生するかについて、ほとんど関心を持ちません。 しかし、彼女は、それがどのようなエラーであり、コードの特定の行(%source filename%の「インスタンス化元」ブロック)がそれを生成したことに関心があります。
そして、これは非常に少し読みやすいです。 コード内の行を見るだけで十分な場合もあります。そのため、すべてが消え始め、すぐに愚かな誤字が表示され、そのようなinが生じます。 エラーメッセージを読む必要さえありません。そのような状況でも、何も賢明なことは言わないでしょう。
typedefはtypedefです
問題のあるコードで使用される基本的なtypedef型の検索と置換のルールを手元に用意しておくと便利です。 短いstd :: basic_string <char> でも、ベクターとキューのペアのリストのベクターは言うまでもなく 、 std :: stringの 形式のほうがはるかに良く見えます。 たとえば、vimでは、数行より長い場合に毎回エラーメッセージを実行する単純な置換スクリプトを記述し、それを読みやすくすることができます。
読書ソース
エラーがテンプレートコードにある場合は、ソースからほとんど離れています。 問題が何であるかわからないときは、コンパイラーが不満を言っているライブラリヘッダーファイルの部分を開き(%header path%:error :)、詳しく見てみる価値があります。 原則として、非常に残酷なブーストライブラリであっても、小さな断片は個別に読み取りおよび理解できます。
次のエラーメッセージで恐怖を見るのをやめ、これらの簡単な方法ですぐに分析し始めた後、デバッグ時間は桁違いに短縮されました。 私もあなたにお願いします。
どのようなトリックを使用しますか? コメントのトピックに関するヒントを読んでうれしいです。 C ++の設計上の欠陥をまとめて扱うことを提案します。
All Articles