22

視聴後: The Clean Code Talks -- 継承、ポリモーフィズム、およびテスト

コードをチェックしたところ、いくつかの switch ステートメントをポリモーフィズムにリファクタリングできることに気付きましたが、switch ステートメントを列挙型でしか使用していないことにも気付きました。これは、オブジェクト指向設計では列挙型が「悪」であり、ポリモーフィズムで排除されるべきであることを意味しますか?

4

6 に答える 6

13

まず第一に、Java には多態的に使用できる優れた列挙型があります。私は Java プログラマーではないので、他の誰かが良い例を示すことができます (私にはできません)。また、ポリモーフィズムは往々にしてやり過ぎであることを考慮してください。私も講演を見たばかりで、すばらしい内容ですが、ガイドラインを提供するだけで、特効薬はありません。

特に、すべてのステートメントを置き換えることができるとは限りません。switchステート マシンは、列挙型が非常に有効なケースの 1 つです。私は構文解析でステート マシンをよく使用します。確かに、これはデザイン パターンとクラス ポリモーフィズムによって実現できます。しかし、それははるかに(はるかに)多くのコードであり、同じ仕事を実行しますが、遅くなるだけで、それほど読みやすくはなく、コードを再利用することなく、1 か所でのみ必要なソリューションです。ここでサブクラス化を使用しても、利点はありません。

繰り返しますが、これは例外です。一般に、サブクラス化は、それを適切にサポートする言語でのより良い解決策であることがよくあります。

編集: これは論争を引き起こす可能性があることに気付きました. もちろん、正規表現から Antlr などのパーサー ジェネレーター フレームワークまで、解析をカプセル化する優れたソリューションが多数あります。それらに問題はなく、些細なケースを除いて、これらはより良い解決策です。ただし、正規表現がサポートされておらず、パーサー ジェネレーターにもオーバーヘッドが発生する低レベル コード (明らかに Java ではありません) をよく使用します。

于 2008-12-19T19:49:00.530 に答える
13

列挙型が悪いのではなく、switch ステートメントです。これについてはC++ FAQ Bookで長い議論がありますが、要点は次のとおりです: 限られた領域を除いて --- たとえば、デバイスのレジスタから入ってくるデータの解釈 --- 大きなスイッチのくしがあなたを示唆しています。データを使用してサブタイプを区別します。その代わりに、サブタイプを使用するだけで、コンパイラーの助けを借りてそれを正しく保つことができます。また、(必然的に) ケースのセットを変更すると、コンパイラーが新しいケースを自動的に追加することも意味します。

于 2008-12-19T20:11:16.587 に答える
11
class Sunday extends DayOfWeek {}
class Monday extends DayOfWeek {}
class Tuesday extends DayOfWeek {}
class Wednesday extends DayOfWeek {}
class Thursday extends DayOfWeek {}
class Friday extends DayOfWeek {}
class Saturday extends DayOfWeek {}

列挙型は問題ありません。

于 2008-12-19T20:07:57.387 に答える
7

私は何かを悪と呼ぶのを躊躇します。「これをどれだけ重くするか」という問題です。

列挙型/スイッチは問題ありません-一部の領域では。クラス階層の設定はオーバーヘッドであり、問​​題に必ずしも必要ではありません。しかし、case ステートメントのコードが多いほど、より重いアプローチに移行する必要がある可能性が高くなります。

私の古典的な経験は、数年前にクラスのために書いたコンパイラです。私のルームメイトは私と同じクラスを持っていましたが、私たちは2つの非常に異なる方法でそれに取り組みました. 私は、ポリモフィズムに満ちた、重い OO アプローチを採用しました。彼は、列挙型と共用体を使用して、ヘビー C のアプローチを採用しました。彼のコードは、LOC に関して私のサイズの約 1/2 であり、彼のコードはコンパイラにとってより高速であり、彼のコードは機能しました。彼のコードは過度に設計されていなかったため、柔軟性がありました。これは、ソフトウェア設計における私にとって貴重な教訓でした。

于 2008-12-19T19:49:07.333 に答える
3

「これは、オブジェクト指向設計では列挙型が「悪」であり、ポリモーフィズムで排除されるべきであることを意味しますか?」

いつもの。

switch/enum コンストラクトは、多数のポリモーフィック構造のいずれかにすることができます。State Strategy、最も頻繁に使用される 2 つの一般的なものです。

于 2008-12-19T19:46:21.270 に答える
1

列挙型は、値が既知で数が少ない場合に役立つと思います。
また、列挙型はある意味で名前付き定数です。

列挙型には、他の状態が保存されていません (その値を除く)。
ポリモーフィズムは、条件の状態が異なる場合に役立ちます (条件は、単一の変数に依存するよりも多くの状態を必要とします)。

于 2008-12-19T19:46:40.707 に答える