悪いデザインの基準

人生は非常にシンプルに機能します。多くの場合、賢くなるためには、愚かなことをしないだけで十分です。これはソフトウェア開発にも当てはまります。ほとんどの場合、何かをうまくやるには、下手にやらないだけで十分です。

ほとんどのプログラマーは、システムの設計が不適切だった部分を経験したことがあります。しかし、さらに悲しいことに、皆さんのほとんどは、自分がそのようなシステムの作成者だったことに気づくという悲しい経験をしているでしょう。私たちは最高のものを望んでいましたが、結果はいつも通りでした。

ほとんどの開発者は悪いアーキテクチャを望んでいませんし、多くのシステムでは、そのアーキテクチャがひどいと言い始める時点が来ます。なぜこうなった?アーキテクチャ設計は最初から悪かったのでしょうか、それとも時間の経過とともに悪くなってしまったのでしょうか?

この問題の根本は、「悪い」デザインの定義が欠如していることです。

プログラマーにとって最も重要な資質は、設計の品質とその「衰退」の理由を理解することだと私には思えます。他のほとんどの場合と同様、重要なのは問題を特定することであり、それを解決するにはテクノロジーが必要になります。

「悪いデザイン」の定義

同僚のプログラマーの前で自分のコードを自慢しようとすると、おそらく「誰がこんなことをするの?」「なぜそうなるの?」と嘲笑されるでしょう。「私だったら違うことをするだろう」これは非常に頻繁に起こります。

人はそれぞれ異なりますが、仲間のプログラマーのためにコードを書くことに変わりはありません。そのため、各機能を開発するプロセスでは、他の人がコードを見てレビューするフェーズが常に必要になります。

しかし、多くのことがさまざまな方法で実行できるとしても、すべての開発者が同意する一連の基準があります。要件を満たしていても 1 つ (または複数) の特性を示すコードは、悪い設計です。

悪いデザイン:

  • 変更はシステムの他の多くの部分に影響を与えるため、変更が困難です。(剛性、剛性)。
  • 変更が加えられると、システムの他の部分が予期せず壊れます。(脆弱性、脆弱性)。
  • 現在のアプリケーションからコードを取り出すのは非常に難しいため、コードを別のアプリケーションで再利用するのは困難です。(不動、不動)。

そして面白いのは、これらの特性のいずれも含まず (つまり、柔軟性、信頼性、再利用可能)、要件を満たし、同時にその設計が不適切なシステムを見つけるのはほぼ不可能であるということです。。

したがって、これら 3 つの特性を使用して、設計が「悪い」か「良い」かを明確に判断できます。

「悪いデザイン」の原因

何がデザインを堅く、もろく、動かせないものにするのでしょうか? モジュールの厳密な相互依存性。

簡単に変更できない場合、デザインは硬直的になります。この柔軟性は、織り込まれたシステム内のコード部分に対する単一の変更が、依存するモジュールの連鎖的な変更をもたらすという事実によるものです。これは、1 人がコードに取り組んでいるときに常に発生します。

これにより、商用開発プロセス全体が直ちに複雑になります。設計者や開発者が段階的な変更の数を予測できない場合、そのような変更の影響を見積もることは不可能です。したがって、彼らはそのような変更を無期限に延期しようとします。

そしてこれにより、変化にかかるコストが予測不能になります。このような不確実性に直面すると、マネージャーは変更を行うことに消極的になるため、設計は正式には硬直的になります。

ある時点で、プロジェクトは「事象の地平線」を通過し、厳格なアーキテクチャの「ブラックホール」に陥る運命にあります。

脆弱性とは、システムが 1 回の変更後に複数の場所で故障する傾向のことです。通常、新しい問題は、変化の場所とは概念的に無関係な場所で発生します。このような脆弱性は、システムの設計と保守に対する信頼を著しく損ないます。

これは通常、プライベート メソッドがない場合に当てはまります。すべてのメソッドを公開するだけで十分ですが、脆弱なアーキテクチャが出現する運命にあります。カプセル化は、ミクロレベルでこれに対処するのに役立ちます。しかし、マクロ レベルでは、モジュール式アーキテクチャが必要です。

プロジェクトのアーキテクチャが脆弱である場合、開発者は製品の品​​質を保証できません。

アプリケーションの一部を単純に変更すると、関係のない他の部分にバグが発生します。これらのエラーを修正すると、さらに多くの問題が発生し、エスコートのプロセスは自分の尻尾を追いかける有名な犬に変わります。

システムの必要な部分が他の不要な詳細と強く結びついている場合、デザインは動かなくなります。独自のコード、独自のアプローチ、ソリューションが多すぎます。

JUL ロガーを覚えていますか。その開発者は理由もなく独自のログ レベルを考案しました。これはまさにそのケースです。

既存のデザインを再利用することがいかに簡単であるかをデザイナーに理解するには、それが新しいアプリケーションでどれだけ簡単に使用できるかを考えるだけで十分です。

設計が緊密に結合されている場合、この設計者は、システムの必要な部分を不必要な詳細から分離するために必要な作業量に愕然とするでしょう。ほとんどの場合、そのような設計は再利用できません。これは、設計を分離するコストがゼロから開発するコストを上回るためです。

関連性

すべては変化しますが、すべては同じままです。(中国のことわざ)

非常に良い質問が上で提起されました。脆弱で厳格なシステムにはどのような危険があるのでしょうか? はい、そのようなプロジェクトを管理するプロセスは予測不能で制御不能になるためです。そして価格は法外です。

実際にどのくらいの時間がかかるかわからない場合、マネージャーは機能の追加にゴーサインを与えるかどうかをどのように判断すればよいでしょうか? タスクの実装にかかる時間と複雑さを適切に見積もることができない場合、タスクに優先順位を付けるにはどうすればよいでしょうか?

そして、私たちがお金を集めるときに、開発者は同じ技術的負債をどうやって返済できるのでしょうか?

コードの再利用やテストに関する問題も非常に関係します。単体テストは、テスト対象の単体に関するいくつかの仮定をテストするだけでなく、単体テストの凝集度を判断し、再利用の指標としても機能します。

この件に関する Bob Martin の言葉を次に示します。「コードを再利用するには、コードを再利用する労力が、最初から開発するコストよりも少なくなる必要があります。 」そうでなければ、誰もこの問題に関心を持ちません。

デザイン原則とパターンの使用には、デザインを優れたものにするという 1 つの目的があります。それらを使用しても何のメリットも得られない場合 (またはその逆が「良いデザイン」の原則に違反する場合)、あなたの温室に何か問題があり、おそらくそのツールが他の目的に使用され始めている可能性があります。