web-dev-qa-db-ja.com

コメントアウトされたコードは本当に悪いのですか?

私が読んだコードの品質に関するほとんどすべてのテキストは、コメント化されたコードが悪いことであることに同意しています。通常の例は、誰かがコード行を変更し、古い行をコメントとして残したことです。これは、後でコードを読む人を混乱させるためです。もちろん、それは悪いことです。

しかし、コメントアウトしたコードを別の状況で残してしまうことがよくあります。計算幾何学または画像処理アルゴリズムを記述しています。この種のコードを理解し、潜在的なバグを見つけるには、中間結果を表示することが非常に役立ちます(たとえば、画面に一連のポイントを描画するか、ビットマップファイルを保存します)。デバッガーでこれらの値を確認することは、通常、数の壁(座標、生のピクセル値)を確認することを意味します。あまり役に立たなかった。デバッガビジュアライザーを毎回作成するのはやり過ぎです。最終製品に視覚化コードを残したくはありません(パフォーマンスが低下し、通常はエンドユーザーを混乱させるだけです)が、それも失いたくありません。 C++では、#ifdefそのコードを条件付きでコンパイルしますが、これには大きな違いはありません。

/* // Debug Visualization: draw set of found interest points
for (int i=0; i<count; i++)
    DrawBox(pts[i].X, pts[i].Y, 5,5);
*/

この:

#ifdef DEBUG_VISUALIZATION_DRAW_INTEREST_POINTS
for (int i=0; i<count; i++)
    DrawBox(pts[i].X, pts[i].Y, 5,5);
#endif

したがって、ほとんどの場合、視覚化コードをコメント化したままにし、視覚化されているものを示すコメントを付けます。 1年後にコードを読んだとき、私は通常、視覚化コードのコメントを外して、文字通り「何が起こっているのかを見る」ことができて嬉しいです。

私はそれについて気分を悪くすべきですか?どうして?優れたソリューションはありますか?

更新:S. Lottがコメントで質問

どういうわけか、すべてのコメント付きコードを「過度に一般化」して、デバッグと無意味で古いコードを含めていますか?なぜ一般化しすぎた結論を下しているのですか?

私は最近、ロバート・マーティンズの「クリーンコード」を読みました。

コメントアウトコードほど厄介なプラクティスはほとんどありません。これを行わないでください。

本のパラグラフをもう一度見ました(p。68)。資格はなく、コードをコメント化するさまざまな理由を区別していません。だから私は、このルールが一般化しすぎているのか(または本を誤解しているのか)、または私が何をしているのは悪い習慣なのか、何らかの理由で知りませんでした。

53
nikie

コメントアウトとは対照的に#ifdefの利点は、(大規模プロジェクトでは)定義をmakeまたはconfigファイルにリストできるため、手動でコメントを外してビルドし、再作成する必要がないことです。 -多くの場所にある場合はコメントしてください。これの欠点は、プロジェクトのDEFINEを変更すると、通常、変更されたファイルだけでなく、全体を再構築することになることです。

けれども...「コメントアウトされたコードは悪いことだ」とは本当にデッドコードを指していると思います。おそらく時間?それは本当にあなたのために行っている状況についてではありません。

58
TZHX

コメントアウトされている場合は、それが腐敗する可能性があります。突然再び必要になると判断した場合、コンパイルされなくなったか、変更されている間に変更されるように書き直す必要があることがわかります。

コードを残したまま、必要のない場合にコンパイラーが最適化できるようにコードを最新の状態に保つことでメリットが得られますand追加されたバイナリを処理する必要がないサイズまたは実行時のパフォーマンス。

たとえば、Cでは、これは腐敗のリスクがあります。

/*
doSomeDebugStuff();
*/

そしてこれも:

#if 0
doSomeDebugStuff();
#endif

しかし、コンパイラによって常に有効性がチェックされるため、これは適切ですが、最適化される可能性があります。

if (0)
{
  doSomeDebugStuff();
}

編集:他の人が指摘するように、テストには0ではなく意味のある記号を使用するのがさらに良いです。

25
Graham Borland
// The problem with commented out code is that it can hide what you're actually
// trying to say in a wall of text.  Syntax highlighting may help, but you're 
// still left with this huge ginormous wall of text in front of you, searching
// through it for what the actual answer is. You'd think that mentally it'd be 
// really easy to disregard the comments, but in actual usage, it's a lot harder
// than a one Word answer that can tell you what you're looking for. It's tough.
/* Sometimes they'll even through you off with different comments. */ Yes.
// It's really tough to deal with people that don't like to use source control, 
// that would rather comment lines and lines of code instead of deleting the 
// code and checking in revision.  Cue irrelevant paragraph about the reason why 
// I wrote this instead of just deleting the entire block and replacing it 
// with my intention. Maybe I was hedging my bets? Cue misspelled wrod.  
18
George Stocker

廃止されたコメント化されたコードと、デバッグビルド(または条件付きでコンパイルされた別の「特別な」ビルド)でのみ使用されるコードは区別する必要があると思います。後者は一般的な方法であり、何も問題はありません。

前者はソースベースに存在すべきではありません。バージョンコントロールシステムが古いものを追跡しているので、それを元に戻したい場合に備えてください。

15
Alex Budovski

コーディングには「常に」はほとんどありません:)ガイドラインの背後にある理由を十分に理解していて、それを破る正当な理由がある場合は、そうしてください。

たとえば、「カミカゼリファクタリング」を実行するときにコードをコメントアウトし、元に戻すか、古いコードがしばらくの間どのように機能していたかを思い出すために視覚的なリマインダーが必要です。このようなインスタンスでは、後でコメントを削除することが重要ですが、そうしないと、コードが乱雑になります。

11
Homde

使用方法クラスを示すために、コメントにコードを挿入する場合があります。これは、以前実行していたコメントアウトコードとは大きく異なります。

8
Ian

私は多くのコードレビューを行っていますが、理由にかかわらず、コメント付きコードには実際の言い訳はありません。デバッグの目的でコメント付きコードを使用している場合、リリースモードで無効になっている、またはトレースレベルがある(常にリリースバージョンでトレースできるようになっている)トレースメカニズムを作成するか、単にデバッガーを使用できます。

他の人がコードを読んだとき-特に元の作者が休暇中にバグを修正しようとしてストレスを感じているとき-特にエラーが誤ってのものである場合、コードを読むのは非常に混乱するので、コメント付きコードは悪いです//を行の先頭に配置します.../*を使用しても、そこにあるべきであるかどうかを誤ってコメントする可能性があります。

コードをクリーンで読みやすくするには、コメント付きのコードを削除します。重要なコードとそうでないコードを読む必要がないため、プログラムをそのまま読むことはすでに困難です。

3
AndersK

はい、そうです。

プロダクションリリースでは不要なデバッグコードがあっても、コメントアウトしないでください。 #ifdefを使用することをお勧めします。これは、#defineマクロを使用するか、個別のビルド構成を使用することで、デバッグのオンとオフを簡単に切り替えることができるためです。これは間違いなく、コードに移動し、デバッグコードのすべてのブロックを手動でコメント/コメント解除する必要がありません。

また、一部のデバッグブロックをオンにして他のブロックをオンにしない柔軟性が必要な場合は、デバッグブロックを「デバッグレベル」にグループ化する必要があります。

より良い解決策は、プリプロセッサをまったく使用せず、定数やifステートメントなどのネイティブ言語機能を使用することです。だから代わりに

#define DEBUG0
#ifdef DEBUG0
  // debugging code
#endif

あなたが持つことができます

const bool DEBUG0 = true;
if(DEBUG0)
{
  // debugging code
}

これを行う利点は、プリプロセッサを使用するよりも、デバッグコードが常にコンパイラによってチェックされることです。これにより、周りのコードを変更したときに、それが回転する可能性が低くなります。

最新のコンパイラーは到達できないコードを最適化するため、ブールフラグをfalseにしてもパフォーマンスに影響はありません。最悪の場合、コンパイラに関する警告が表示されることがあります。

2
Dima

私はあなたがしていることがうまくいっているとは思いませんが、少なくともactualのコメントを付けて、何をしているのか、なぜ、どのように、いつ使用するのかを説明する必要がありますそれ。

個人的に私は通常、この種のことを、問題のコードの周りのある種のIF DebugMode = TRUEタイプの取り組みに入れ、それをコマンドライン/起動パラメーターとして設定します。私にとっては、コードがそこにある理由とそれを設定する方法がわかりやすいのですが、インスタンスでは、たとえ小さな比較であっても避けたいパフォーマンスの問題があるかもしれません。

だから私はあなたが何をしているのかを完全に間違っているのではなく、必要な悪として見ているでしょう。あなたがそれを合理化する方法を見つけることができれば、明らかにそうしますが、私はそれについて自分を打ち負かすことはありません。

1
Jon Hopkins

コメントアウトされたコードがコードのにおいだと見なされる理由の1つは、それを配置したプログラマーがソース管理を理解していないか、何も使用していないことを示しているためだと思います。どちらも、彼らが行っている他の多くのことにも疑問を投げかけています。

正当な理由がある場合はおよび正当な理由である理由を説明し、それがおそらく正常に機能していることがわかる。悪い知らせだと一般的に考えられているほとんどのことは、右手にとっても便利なツールです。問題は、それらの手は自分が持っていると思っている人よりも珍しいことです。

0
glenatron

それは、プログラマーの心がその時にどのように働いていたかの履歴を提供するのに役立ちます。しかし、今日のユビキタスなソース管理では、それを最終版のままにする理由はありません。以前のバージョンには、参照する必要がある場合に備えて、古いコードが含まれています。

0
5arx

ここには絶対的なものはないと思います。短いスニペットである場合、コメントアウトしたコードを時々残します特にすぐに再びコメント解除する合理的な可能性がある場合。基本的に私は、実際のコードの読みやすさを妨げない限り、そしてどこでも増殖しない限り、これらのスニペットを残します。

私が絶対に拒否するのは、コメント化されたコードの完全な方法です。はい、以前に見たことがあります。WTF。彼らはソースリビジョン天国で休むことができます;-)

0
Andres F.