上司はいつも、良いプログラマーは、自分が変更したコードが信頼でき、正しく、完全に自己検証されていることを確認できるはずだと言ってきました。変更が引き起こすすべての結果と影響を完全に理解する必要があります。何度も何度もテストすることで、この種のプログラマになるために最善を尽くしましたが、バグはまだ残っています。
どうすればゼロバグプログラマになり、コードのすべての文字が何を引き起こし、どのような影響を与えるのかを知ることができますか?
上司はいつも、良いプログラマーは、自分が変更したコードが信頼でき、正しく、完全に自己検証されていることを確認できるはずだと言ってきました。変更が引き起こすすべての結果と影響を完全に理解する必要があります。何度も何度もテストすることで、この種のプログラマになるために最善を尽くしましたが、バグはまだ残っています。
どうすればゼロバグプログラマになり、コードのすべての文字が何を引き起こし、どのような影響を与えるのかを知ることができますか?
回答:
まったくコーディングしないでください。
それが、あなたがバグゼロのプログラマーになれる唯一の方法です。
プログラマは人間であるため、バグは避けられません。バグを防ぐために最善を尽くし、バグが発生したときに迅速に対応し、ミスから学び、最新の状態を保つことしかできません。
些細なプログラムでは、バグをゼロにすることは不可能です。
非常に接近することは可能ですが、生産性は低下します。そして、特定のハイリスクソフトウェアにとってのみ価値があります。スペースシャトルのソフトウェアは、私の心に来ます。しかし、その生産性は1日に数行程度です。あなたの上司がそれを望んでいるとは思わない。
このソフトウェアにはバグがありません。人間が達成したのと同じくらい完璧です。これらの統計を検討してください。プログラムの最後の3つのバージョン(それぞれ420,000行の長さ)には、それぞれ1つのエラーしかありませんでした。このソフトウェアの最後の11バージョンには、合計17個のエラーがありました。
ソフトウェアのアップグレードを行って、シャトルが全地球測位衛星でナビゲートできるようにします。この変更には、プログラムのわずか1.5%、つまり6,366行のコードが含まれます。その1つの変更の仕様では、電話帳よりも厚い2,500ページが実行されます。現在のプログラムの仕様は30ボリュームを満たし、40,000ページを実行します。
「ゼロバグプログラマー」はサイレントシンガーのような矛盾表現ですが、過去60年ほどのプログラミングで知恵が抽出され、次のような優れたプログラマーになります。
TDDのポイントは、そのコード行を必要とするテストがない場合、1行のコードを記述しないことです。そして、それを極端にするには、受け入れテストを書くことで常に新しい機能の開発を開始します。ここで私はキュウリのスタイルのテストを書くことが理想的であることを発見しました。
TDDアプローチには、少なくとも2つの利点があります。
それは不可能であるため、バグがゼロであることは証明されていません(すでに他の無数の回答で指摘されています)。しかし、TDDを学んで上手になった後(はい、それは練習が必要なスキルでもあります)、徹底的にテストされているので、自分のコードにはるかに高い自信を持っています。さらに重要なことは、機能を壊すことを心配せずに、完全に理解していない既存のコードを変更できることです。
しかし、TDDはあなたをずっと助けてくれません。システムのアーキテクチャとそのアーキテクチャの落とし穴を完全に理解していないと、バグのないコードを書くことはできません。たとえば、複数のリクエストを同時に処理するWebアプリケーションを作成している場合、複数のリクエスト間で変更可能なデータを共有できないことを知っておく必要があります(パフォーマンスを向上させるために変更可能なデータをキャッシュする初心者トラップに陥らないでください)。
TDDが得意な開発チームは、欠陥の少ないコードを提供すると信じています。
はい、コードにバグがないことは不可能ですが、バグを減らすことは不可能ではありません。「それは馬鹿げている、いつもバグがあるだろう」という態度は、コード内のバグの数を減らすことを避けるための警官です。完璧な人はいませんが、私たちはより良くなるよう努力することができ、また努力すべきです。改善のための私自身の努力の中で、私は次の点が役立つことを発見しました。
個人的には、バグのないプログラミングのために努力することは、(時間とお金の両方で)より高価であると思われます。ゼロバグ、またはほぼゼロバグに到達するには、開発者に徹底的なテストを依頼する必要があります。これは、パッチレビューのためにコードを送信する前にすべてを回帰テストすることを意味します。このモデルは、費用対効果が高いとは思いません。開発者にデューデリジェンステストを実施させ、詳細なテストはQAチームに任せてください。その理由は次のとおりです。
コードを書くとき、それに対して記録されるバグがあることを受け入れます。それがQAプロセスを持っている理由であり、それはすべて開発者であることの一部です。もちろん、これは最後のセミコロンを書いてすぐに何かを提出することを意味しません。作業の質を確保する必要がありますが、やりすぎる可能性があります。
ピアレビューやテストを行わずに、常に最初に自分のタスクを正しく実行できる専門職をいくつ挙げることができますか?
バグはありませんか?Lispが必要なようです(懐疑的な道を進み、ミュージックビデオを避けてください)。
主流のコーディング環境(Java、C#、PHPなど)でバグのないコードを実現するのは非常に困難です。短い制御された反復で、十分にテストされ、ピアレビューされたコードの生成に焦点を当てます。
コードをできるだけシンプルに保つことは、バグを回避するのに役立ちます。
コード分析ツール(FindBugs、PMDなど)を使用していることを確認してください。これは、厳密なコンパイラ警告と組み合わせて、コードに関するあらゆる種類の問題を明らかにします。彼らがあなたに言っていることに注意し、本当にバグの性質を理解するよう努めてから、そのバグを再び導入する方法でコーディングするのが不自然に感じるようにプログラミングのイディオムを変更するための手順を実行します。
すべて「まったくコーディングしないでください。」答えはポイントを完全に欠いています。また、あなたの上司は間違いなくバカではないようです!
私は、自分のコードが何をするのか単に知らないプログラマーをどれほど頻繁に見たか覚えていません。彼らの唯一の開発哲学は、試行錯誤のようでした(そして、多くの場合、コピー/貼り付け/変更も)。試行錯誤は問題を解決する有効な方法ですが、多くの場合、問題の領域を分析してから、使用するツールの理解に基づいて非常に具体的なソリューションを適用できます。初めて展開する前に問題を解決しただけでなく、ほとんどのコーナーケース(潜在的なバグ)も解決しました。コードにバグがないことを保証できますか?もちろん違います。しかし、あなたが遭遇したり読んだりするすべてのバグについて、次に何かを書いたり変更したりするときに考えたいことを追加することができます。これを行うと、結果として、ほとんどバグのないコードの記述方法について多くの経験を積むことができます。-旅のお手伝いをすることができる優れたプログラマーになる方法に関するリソースがたくさんあります...
個人的には、すべての行を説明できないコードをコミットすることはありません。すべての行には理由があります。それ以外の場合は削除する必要があります。もちろん、呼び出すメソッドの内部動作を想定することもあります。そうしないと、フレームワーク全体の内部ロジックを知る必要があります。
上司は、既存のシステムで記述したコードの結果と影響を理解する必要があると完全に言っています。バグが発生しますか?はい、もちろん。しかし、これらのバグは、使用しているシステム/ツールに対する理解が不完全であるためであり、バグを修正するたびにカバレッジが向上します。
他のコメントがすでに正しく指摘しているように、バグのない重要なソフトウェアはありません。
ソフトウェアを常にテストしたい場合、そのテストではバグがないことを証明するだけであり、バグがないことを証明することができます。
作業ドメインに応じて、ソフトウェアの正式な検証を試みることができます。正式な方法を使用すると、ソフトウェアが仕様に正確に適合していることをかなり確信できます。
もちろん、それはソフトウェアがあなたが望むことを正確に行うという意味ではありません。ほぼすべての場合、完全な仕様を作成することもできません。基本的に、エラーが発生する可能性のある場所を実装から仕様に変更します。
したがって、「バグ」の定義に応じて、正式な検証を試すか、ソフトウェアでできるだけ多くのバグを見つけようとします。
私は他のものに同意します。ここに私が問題にアプローチする方法があります
ゼロバグプログラマになるように努力できます。コードを書いているときはいつでも、バグのないプログラマになるよう努めています。しかし、私はしません
私が書いているソフトウェアにとっては法外な費用がかかるため、私はこれらのことをしません。これらのことをすれば、おそらくバグをゼロに近づけることができるでしょうが、ビジネスには意味がありません。
インフラストラクチャの大部分が使用する内部ツールを作成します。私のテストとコーディングの基準は高いです。ただし、バランスがあります。バグをゼロにすることは期待していません。なぜなら、そのような時間を1つの仕事に費やすことはできないからです。X-Rayマシン、ジェットエンジンなどを制御するソフトウェアを作成している場合、状況は異なる可能性があります。ソフトウェアが破損した場合、命が失われるため、そのレベルの保証は行いません。
保証のレベルをソフトウェアの使用目的に合わせます。NASAシャトルが使用するコードを記述している場合、バグ許容度はゼロであることが合理的です。追加の非常に高価なプラクティスを追加するだけです。
「バグゼロ」プログラマになるための良い第一歩は、バグに対する態度を変えることだと思います。「起こる」、「QAとテスターを改善する」、「開発者がテストを嫌う」と言うのではなく、
バグは受け入れられません。バグを排除するために自分の力であらゆることを行います。
これがあなたの態度になれば、バグはすぐになくなります。バグを排除する方法を見つけるための検索では、テスト駆動開発に遭遇します。多くの本、ブログ投稿、より良いテクニックについて無料のアドバイスを提供する人々を見つけるでしょう。練習を通してスキルを向上させることの重要性がわかります(カタのコーディングや自宅で新しいことを試すなど)。自宅でクラフトの仕事を始めるので、仕事でのパフォーマンスが向上します。 そして、うまくいけば、良いソフトウェアを書くことができるとわかると、あなたのクラフトに対するあなたの情熱が成長するでしょう。
ある意味で、あなたの上司は正しいです。バグがゼロに近いソフトウェアを作成することは可能です。
しかし、問題は、(ほぼ)バグのないプログラムを書くコストが非常に高いことです。次のようなことをする必要があります。
要件の正式な仕様を使用します。Z、VDM、またはその他の数学的に適切な表記法を使用した形式。
定理証明手法を使用して、プログラムが仕様を実装していることを正式に証明します。
広範なユニット、リグレッション、およびシステムテストスイートとハーネスを作成して、あらゆる方法でバグをテストします。(そして、これだけでは不十分です。)
持っている多くの人が(公式・非公式)要件を確認し、ソフトウェア(および証明)。テスト、および展開。
上司がこのすべての費用を支払う準備をすることは非常にありそうにありません...またはすべてを行うのにかかる時間を我慢します。
バグのないプログラムを作成する手順は次のとおりです。
テストではバグがあることを証明することしかできませんが、それ以外のことを証明することは通常は役に立ちません。フィードバックについて-コインを作るコイン作成機があり、平均で10代ごとにコインに欠陥がある場合。そのコインを取り出して平らにし、再びマシンに挿入できます。リサイクルされたブランクはそれほど良いものではないが、おそらく受け入れられることを明らかにしたコイン。100代ごとに2回スタンプを押す必要があります。マシンを修正する方が簡単ですか?
残念ながら、人は機械ではありません。優れた、欠陥のないプログラマーを作成するには、多くの時間を費やし、発生したすべての欠陥についてトレーニングと反復を行う必要があります。開発者は、実際に学習して適用するのが難しいことが多い正式な検証方法のトレーニングを受ける必要があります。ソフトウェア開発の経済学もそれに対して働いています-あなたが彼が別の雇用者にジャンプするのを見るためだけに欠陥をより少なくすることができるプログラマを訓練することに2年を投資しますか?完璧なコインを作る機械を購入するか、10個のコードモンキーを雇って同じコストで一連のテストを作成できます。この徹底的なプロセスを、あなたの資産である「マシン」とみなすことができます-優秀な開発者の広範なトレーニングに投資しても報われません。
すぐに許容できる品質のソフトウェアを開発する方法を学習しますが、遅いために完璧なコードを作成する開発者の市場がないという単純な理由で欠陥がない人になることはおそらくないでしょう。
防御的なプログラム:http : //en.wikipedia.org/wiki/Defensive_programming
誰かが防御的なプログラミングの慣習に従うと、変更は簡単に追跡可能になります。これを、開発中の厳密なバグレポート、およびdoxygenなどの堅実なドキュメントと組み合わせると、すべてのコードが実行していることを正確に把握し、発生したバグを非常に効率的に修正できるはずです。
これは、一般的な骨折だけでなく、優れた方法論を誤解した結果でしょうか?
つまり、上司が「欠陥ゼロの方法論」(セクション5を参照)を聞いたことがあり、それが何を意味するのかわからない可能性があるということです。
もちろん、それはバグの賛成で、新機能の開発を延期する管理用不便だあなたがに入れているはずの...
そして、良いプログラマがない」ので、あなたが文句を言わないものを取得もちろんので、もちろん、それは、彼のボーナスを脅かしますバグがある」...
バグを見つけて修正できる限り(もちろん、理由の範囲内で)バグを作成しても構いません。
大手ソフトウェア会社が最高の開発者を獲得する方法を知っていると仮定すると(バグプログラマーのように)、マイクロソフトのソフトウェアにはバグがないはずだと推測できます。しかし、私たちはそれが真実とは程遠いことを知っています。
ソフトウェアを開発し、特定のレベルの低優先度のバグに到達すると、製品をリリースして後で解決します。
単純な計算機よりも複雑なものを開発している場合を除き、すべてのバグを一緒に回避することはできません。地獄にもNASAは彼らの車両とバグの冗長性を持っています。ただし、壊滅的な障害を回避するために、非常に厳密なテストが行われています。しかし、それでもソフトウェアにバグがあります。
バグは、人間の性質が誤りであるのと同じように避けられません。
バグがないことは、100%安全なシステムを持っているようなものです。システムが100%安全であれば、それはもはや役に立ちません(おそらく、大量のコンクリートの中にあり、外部にまったく接続されていません。有線でも無線でもありません。 、バグのない複雑なシステムはありません。
私たちは人間であり、間違いを起こしやすいという答えを見るだけです。これは非常に真実です...
バグのないプログラムを作成できると思いますが、それらは通常、すでに10回または12回作成したプログラムです。同じプログラムをゼロから最初に書くとき、あなたはすでにそれを行う方法を知っています:あなたは問題を知っています、あなたはテクニックを知っています、あなたはライブラリ、言語を知っています...あなたは心の中でそれを見ます。すべてのパターンがすべてのレベルにあります。
私はプログラミングを教えるので、これは非常に単純なプログラムで私に起こります。私にとってはシンプルですが、学生にとっては難しいものです。そして、私は黒板で何度も何度もやった問題の解決策について話しているのではありません。もちろん、私はそれらを知っています。私が本当によく知っている概念(私が教える概念)を使って何かを解決する300行のプログラムを意味します。私はこれらのプログラムを計画なしで作成し、それらは機能するだけで、すべての詳細を知っていると感じています。TDDはまったく必要ありません。コンパイルエラーが2〜3回発生します(ほとんどがタイプミスなどです)。私は小さなプログラムに対してこれを行うことができますし、一部の人々はより複雑なプログラムに対してもそれを行うことができると信じています。Linus TorvaldsやDaniel J. Bernsteinのような人は、このような明快さを持っていると思います。彼らはバグのないコーダーに最も近い人です。もし、あんたが物事を深く理解することができると思います。私が言ったように、私はこれを簡単なプログラムに対してのみ行うことができます。
私の信念は、あなたが常にあなたのレベルをはるかに超えたプログラムをしようとすると(私はそれを何年も費やしました)、あなたは混乱して間違いを犯すだろうということです。問題を最終的に理解すると、ソリューションが機能しないことに突然気づき、問題の解決やコードのひどさを妨げるほど複雑な変更を加えなければならないような大きな間違い。TDDはこの場合に適していると思います。自分が取り組んでいる問題を理解していないことを知っているので、あらゆる場所にテストを置き、強固な基盤があることを確認してください。ただし、TDDは10,000フィートのビジョンを解決しません。常に完全にクリーンなコードで円を描くことができます。
あなたが新しい何かをしようとするが、それがある場合は、ちょうどあなたのレベルを超えて、あなたのプログラムが完璧かほぼ完璧かもしれません。どのプログラムがあなたの「知識フロンティア」にあるかを知ることは本当に難しいと思いますが、理論的にはそれが学習するための最良の方法です。実際、プログラムを一から書き直しています。一部の人々はそうしますが、3回目は自明でないプログラムを繰り返すとき、あなたは初めてのように興奮しないので、あなたは多くの時間と忍耐を必要とします。
したがって、私のアドバイスは、そのことだけのためにバグのないプログラムを書くことができるまで、あなたが何かを理解するとは思わないことです。そして、あなたが深く知っているこれらの概念の2つを同じプログラムに組み合わせてみてください。私はあなたが最初に正しくそれを得るとほぼ確信しています。最善の方法の1つは、自明ではないソフトウェアを書き直すことです。これは、最初は多くの労力を費やしました(現在、Androidアプリでこれを行っています)。もう一度始めるたびに、ちょっとした楽しみを加えるために何かを変更したり、何かを追加したりして、ますます良くなっていくと言うことができます。
私見のバグと突然の不可解なアルゴリズムアーティファクトは、コーディングプロセス中に表示される必要があります。これらは、コードの進化を促し、強制します。
ただし、(通常はテスト後に)宣言の前に使用される可能性のあるすべての変数をチェックし、出現する可能性のあるすべてのエラーを処理することができます-考慮された機能のリクエストを受け取るまで、プログラムをゼロバグにするあなたがプログラムのアーキテクチャを議論していたときは不可能です;)
たぶんあなたが得るバグの性質についてもっと考えてみてください。バグが一般的に軽微な見落としである場合は、より良いテストと少しのコード校正に焦点を当てることが役立ちます。
しかし、バグが最適でないプログラミングの決定によるものである場合は、より良い設計により多くの労力をかける必要があるかもしれません。この場合、テストに依存しすぎてソフトウェアの品質を上げることは可能だと思います。不足しているコードにパッチを適用すると、将来のメンテナンスがより複雑になるからです。一方では、バグを見つけて修正するにつれてバグが減りますが、他方では、将来のバグに備えて地面を準備します。
見落としの問題または設計の問題があるかどうかを判断する1つの方法は、バグを修正するのにどれだけの労力が必要かを検討することです。修正が大きくなる傾向がある場合、または修正をよく理解していないと感じる場合、それは改善できるコード設計を示しています。
それは、コードについてのある種の良い趣味に帰着すると思います。それは、練習とレビューで開発でき、同様の問題を抱えている人々について読むことができます。
最終的には、バグをまったく期待しないのは無益ですが、既にある程度の低レベルになっていない限り、バグ数を減らそうとしても害はありません。キャッチできないバグ。
つまり、「コードの作成中にバグがゼロ」->それは素晴らしい目標ですが、かなり不可能です。
しかし、もしあなたが言うなら: "提供されたコードのバグはゼロ"->それは可能であり、私はそのような環境で働いた。
必要なのは、非常に高いコード品質とほぼ100%のテストカバレッジ(単体テスト+受け入れテスト+統合テスト)だけです。
私の意見では、それを学ぶのに最適な本はGOOSです。しかし、もちろん本では十分ではありません。いくつかのユーザーグループに移動して、これについて議論する必要があります。コース、会議など。ゼロバグの品質は簡単ではありません。
まず第一に、高品質に本当に興味があり、その代価を払ってくれる上司が必要です。
別のエンジニアとペアリングします。失敗したテストを記述します。失敗したテストに合格するには、入力するすべての文字が必要です。コードをリファクタリングして、よりシンプルにします。別の失敗したテストなどを書いてください。