私はチームのリードデザイナーです。つまり、私はコードの品質に責任があります。機能性、保守性、可読性。
時間が足りない場合、チームメンバーのコードをどの程度クリーンにする必要がありますか?
私の見解では、変更した古いコードをクリーンアップする必要があります。メソッドに行を追加することは、そのメソッドをクリーンアップすることを意味します。
しかし、新しいコードはどうですか?
別のコーダーが明日やって来て小さな変更を加えた場合、彼女はそれをクリーンアップする必要がないように、それをきらめくようにきれいにすることができます。しかし、これは、誰もそのコードの一部を再度読み取ることがなければ、きちんときれいにするために時間を浪費したことを意味します。
「ほぼきれい」を目指し、将来の訪問でさらにきれいにする必要がありますか?しかし、それは私たちが最初にそれを書いたときに私たちが持っていた理解に十分な価値を得られないことを意味します。
今、私は「スパークリングクリーン」に行きます。一部は私ほどうるさくない同僚のためのチュートリアルとして。
私の経験:
概念実証として書かれた20行を超えるコードは、このようにして証明された概念が必要な場合は書き直されませんが、多少曲げられます量産コードのニーズに合う。
通常、これは、すべてを適切に行う時間があるときに、後で書き直すという約束と一緒に行われます。しかし、今回は決して来ないので、このテストコードは製品コードに永久にスタックされますになります。
たとえば、2人月よりも大きいソフトウェアプロジェクトは、そのような概念実証のコードの少なくとも1つの部分に支えられており、それらの多くに大きなプロジェクトが構築されています。そして、誰もが通常これらのコードを置き換えようとはしていません-通常はアプリケーションの根本的な重要な機能であり、すべてをもたらすと脅します1つのエラーでダウンします。
遅かれ早かれ、あまりにも多くの大きなプロジェクトそのようなコードのトリップ。
私の解決策:
20行を超えるコードはすべて、堅固で防弾でなければなりません。全体を適切に設計し、ハックを使用して時間を節約し、適切な識別子の選択に力を入れ、必要に応じてすぐにリファクタリングします...エンチラーダ全体。
これらのスニペットの80%は確かにスローされていますが、残りはコードの中心になり、会社を10年先まで浮かび上がらせます。その見込み客は、小さな、一回限りのプログラムに注がれた努力の量を言い訳します。
私の経験では、新しいコードをクリーンにすることは実際にはそれほど難しくありません。通常、コードが何をすることになっているのか、それをどのように実装するのかなど、単一の明確な概念が頭にあります。そのため、これを明確に反映するようにコードを配置するのはかなり簡単です(少なくとも、現在の理解に従って-戻る6か月後に同じコードに変更すると、いくつかの驚きが明らかになります;-)。
問題は、既存のコードを変更または拡張する必要がある場合に発生します。その後、それはより複雑になり始め、元の明確なアーキテクチャ/設計ビジョンがぼやけてきているので、コードエントロピーを制御下にリファクタリングして維持するために意識的な努力を費やす必要があります。
可能な限りクリーンなコードを作成すると、将来の拡張やメンテナンスが確実に容易になります。将来の変更がある場合、それはです。そうでなければ、お気づきのように、努力は「無駄」です-少なくとも直接的な意味で。ただし、考慮すべき追加事項があります。
全体として、これらの引数は [〜#〜] yagni [〜#〜] の反対を導きます:この場合、あなたはそれが必要です。時間があれば、できるだけクリーンなコードを記述してください。 (しかし、より明確ではありません-ある時点でリターンを減少させるルールが適用されるので、停止してより良いことを見つける必要があります。同じ3行のコードを際限なく磨くのを避けるために、実際の改善を表す意味のある変更に集中する必要があります可読性/保守性。)
*健康な大人が歩くことがどれほど難しいかについて不平を言うのを聞いたことがありませんが、赤ちゃんや怪我人がそれを(再)学習しようとするのを目撃すると、それが実際にどれほど複雑な達成であるかがわかります。それでも、私たちのほとんどは、意識的にさえ意識することなく、常にそれを行っています。
場合によります。新しいコードと既存のコードの2つのケースを作成します。
新しいコードについては、テスト駆動開発(TDD)と無慈悲なリファクタリングを標準的な方法として使用することをお勧めします。リファクタリングによってできる限りシンプルにして、これ以上改善が考えられなくなったときにのみ停止します。これは、多くの努力のように聞こえるかもしれませんが、何度も報われることがわかります。言い換えれば、はい、それを「スパークリングクリーン」にします。
ただし、既存のコードについては、さらに注意が必要です。テストスイートの品質と範囲によって異なります。通常、既存のコードはかなり長い間使用されてきたコードです。これはまた、おそらくほとんどのバグが修正されたことを意味します。このコードを変更し始めたら、機能するものを壊さないようにする必要があります。最初にテストを書くことをお勧めします。それらのヒープは、既存のコードが何をしているかを明確に理解することを確実にするだけでなく、コードのクリーンアップを開始するときに、誤って何かを壊すことがないようにします。
アプローチの選択は、使用可能なツールによっても異なります。リファクタリングと単体テストのサポートは、言語によってまったく異なる場合があります。可能な限り最高のツールを入手してください。価格に関係なく、彼らはそれだけの価値があります。
レガシーコードの操作には、さらに多くの側面があります。 Mike Featherの本「レガシーコードで効果的に働く」 を読むことを検討することをお勧めします。幸運を!
過去数年間で、私は鉄則を発見しました:
コードは常に予想よりも長く存続します。
マーケティングで2週間の本番用に設計された重要ではないページの一部のテキストを変更できるように、30分で一緒に投げたその一発の使い捨てのものは、おそらく2年後に会社を辞めたときにもまだ使用されています。プロジェクト全体が終了するまで、あなたが作成した今のところ機能するデプロイメントスクリプトはほとんど使用されません。コマーシャルの代わりに、実際に使用されるまで、この小さな代替品を使用し、サードパーティのORMコンポーネントが機能しなくなったため、それ自体が実際のものになる可能性があります。
また、クリーンなコードを書くのに時間がかかりません。最初に高速でダーティなコードのトラックロードを記述してからクリーンアップする場合は問題ありませんが、クリーンな状態から始めて途中でクリーンに保つ場合は、多くの場合さらに高速です。
本当に良いミュージシャンがかつて私に言った:「常にできる限りベストを尽くしてください。ホテルの部屋でウォームアップをしているときでも、あなたが持っているすべてを与えてください。隣の部屋で聞いています。」
チームの各プログラマーにとって、答えは常に「先週書いたコードより少しクリーン」であるはずです。
多くの場合、組織のコーディング標準に特定のハードルールがあると、正式に行われるはずのことと実際に行われることが切り離されます。平均的なスキルを持つほとんどのプログラマーは、一晩で突然自分のやり方を変えることはできません。また、定期的に基準に達したとしても、休暇を取ることになります。現実の世界では、完璧よりも改善に焦点を合わせる方が現実的です。
From リファクタリング:既存のコードのデザインの改善 、p58;
- 初めて何かをするときは、それを行うだけです。
- 同じようなことを2回目に行うと、複製に失敗しますが、とにかく複製を行います。
- 同様のことを3回行うと、リファクタリングします。
執筆時には常に可能な限りクリーンにしてください。ずさんなコードを書く時間を節約するのは誤った経済です。バグを修正したりコードを変更したりするたびに、ショートカットごとに代償が払われます。
古いコードの屈折はあまり明確ではなく、その時のコーダーの判断に依存します。時々、他のコードと一貫性のある、よりクリーンでないスタイルで書くことが「正しい」。既存のコードの屈折は困難で時間のかかる作業です。 1つの修正のために、作業コードの大きなチャンクを書き直すのはおもしろくない場合があります。
重要なのは、再度作業する可能性が最も高いコードをクリーンアップすることです。
十分に因数分解されたコードでの作業は、よりfunであり、-望ましい結果を生成する可能性が高くなります。それらは両方とも重要です。
ただし、リファクタリングにはtimeが必要で、すべての編集にはriskの新しいバグが伴います。他の方法で作業する必要のないコードをリファクタリングすることは悪い考えです。
どのコードで作業する必要があるかを知る方法は? 変更は一緒に発生する傾向があります、チャーンの多いエリアで、他のエリアは長時間アイドル状態のままです。このフェノモンには多くの理由があります。 1つは、現在行っている変更はおそらく間違っているということですが、完了するまでそれを知ることはできません。
そのため、機能またはバグ修正に取り組むときは、次のシーケンスを使用します。
想像コードがどのように見えるか理想的変更したいので、変更は単純に1行の編集で、明らかに正しいですか?
リファクタリングのパスを想像して、その時点まで物事を進めてください。
一度に1つのリファクタリングを作成し、進行中にテストし、各リファクタリングを個別にチェックインし、「REFACTORING:」で始まる特別な変更の説明を追加します。これにより、意図的な動作の変更を探している場合、これを確認する必要がないことを明確にすることができます。また、ほとんどのリファクタリングは既知の名前で明確に定義されているため、後でこれらの変更を理解するのは簡単です。
単一の1行編集を行って、目的の機能変更を取得します。
このアプローチは、新しい機能を追加する場合と同様に、既存の機能を変更する場合にも機能します。1日目がすべて既存のコードであるためです。ただし、プログラムの機能の新しい領域に分岐する場合は、迅速かつ汚い実装を一緒に投入して、計画に関する実際のフィードバックを取得します。
たくさんあります警告:
deadlineが迫っている場合、リファクタリングのリスクがメリットを上回る可能性があります。判断が必要です。
時々コードはこれを機能させるために広範なリファクタリングを必要としますが、必要な機能またはバグ修正を十分に簡単に実装することが可能です。この場合、私はより明白で簡単なリファクタリングを行うことができますが、上記の理想は行いません。
高品質の自動化されたtestsがない場合、リファクタリングのリスクはより懸念されます。状況によってはリファクタリングが少なくなる場合があります。ただし、十分に因数分解されていないコードは単体テストが難しいため、注意しないと泥沼に陥ってしまいがちです。
私が必要とする確信が持てないいくつかのfuture変更に有益であると思われる構造へのリファクタリングを避けることに注意してください。目前の問題のみをリファクタリングします。ただし、この種の変更を行う必要があったのがこれが初めてでない場合は、将来の同様の変更を見越して、リファクタリングの範囲を広げることがあります。もう一度判断が必要です。
私は常に自分自身をコードで繰り返さないようにドライブしてきました-それは良いコードの中で最も重要なドライブの1つだと思います-ほとんどすべてがこれから派生しています。
そうすることで、コードをリファクタリングして冗長性を排除することも、最も教育的な実践の1つであることがわかりました。時間が経つにつれ、より多くのものを冗長として認識し、それらをリファクタリングするために使用するパターンやトリックが増えることを学びました。
その上、信じられないようなコード結合リファクタリングがスタックします。内部から始めて、類似のステートメントをいくつかリファクタリングしてデータ構造を使用します。これにより、他のコードとの類似性を識別でき、驚くほどの速度で上り坂になり、途中でバケットごとにコードを削減します。
では、余暇があまりなくても、機会があればどこでもこれを行わないのはなぜでしょうか。
書式設定やコメントなど、コード内の余分な "クリーン"のほとんどは、このプロセスからも発生します-繰り返しコードの5ページを文書化したい人はいますか?それらを単一の関数に分離したら、今度は文書化する価値があります!