Skip to content.

Sections
Personal tools
You are here: Home » 技術文書 » リファクタリング » 不吉な匂い

Document Actions
不吉な匂い
(株)永和システムマネジメント    梅田 政利
作成日:初出:ソフトバンク『C MAGAZINE 2003/6』

不吉な匂いとは、リファクタリングを必要とするコードから感じられる雰囲気を、比喩で表したものです。 ここでは、感じ取った不吉な匂いに対して、どのような解決法を選ぶことができるかを取り上げます。 匂いとして示されているのは、次の22のケースです。ひとつずつ見ていきましょう。 また、解決法に添えられている数字は、参考書籍「リファクタリング」の何ページに記されているかを示しています。

   目次


   

重複したコード(76)

同じようなコードが2か所以上で見られたら、 1か所にまとめることを考えると良いプログラムになります。



長すぎるメソッド(76)

長いメソッドは理解するのが大変です。 対して、小さいメソッドに分けていくと、コードを追っていくのが大変になりますが、 適切なメソッド名を与えることで、内部の実装を見なくても 読み進めることが可能になります。 メソッドの長さを切り詰めることが重要なのではなく、メソッド名と実装の距離を埋めることを目指します。



巨大なクラス(78)

1つのクラスがあまりに多くの仕事をしている場合は、たいていインスタンス変数の持ちすぎになっています。



多すぎる引数(78)

引数があまりに多いと、1つ1つが何を意味しているのか理解しづらくなります。



変更の発散(79)

1つのクラスが互いに独立した理由で同じように変更され、その手順も異なります。つまり、 1つのクラスがさまざまな変更要求の影響を被ります。



変更の分散(80)

1つの変更要求に対して複数のクラスが影響を被ります。変更を行う度にあちこちのクラスが 少しずつ書き換わることになりますので、変更とクラスが1対1になるように修正しましょう。



属性、操作の横恋慕(80)

あるメソッドが自分のクラスよりも他のクラスに興味を持つような場合には、古典的な誤りを 犯しています。ただし、StrategyパターンやVisitorパターンのように、この匂いに当てはま らない定番のパターンもいくつかあります。



データの群れ(81)

数個のデータがグループとなって、クラスのフィールドやメソッドのシグネチャなど、さまざまな箇所に現れることがあります。こうした群れをなしたデータは、オブジェクトとして1箇 所にまとめるべきです。



基本データ型への執着(81)

オブジェクトにちょっとしたことをさせる場合には、小さなクラスを作ることが面倒に感じる ことがあります。住所を表すために、県、市、町、番地などをそれぞれStringとして人クラス のフィールドに作成するようなことはありますよね。こういったクラスが成長していくと、と ても理解しづらいクラスになってしまいます。



スイッチ文(82)

コードのあちこちに同じようなスイッチ文が見られたら要注意です。これでは新たな分岐を追 加したときに、すべてのスイッチ文を探して、似たような変更をしていかなければなりません。 ポリモーフィズムを使ってエレガントに解決しましょう。



パラレル継承(83)

「変更の分散」の特殊ケースです。新たなサブクラスを定義するたびに、 別の継承木にもサブクラスを定義しなければならない状況を示します。 一方の継承木のインスタンスが、もう一方の継承木のインスタンスを参照するように変更しましょう。



怠け者クラス(83)

十分な仕事をせず、理解や保守のためのコストに見合わないクラスがあります。リファクタリングによるクラスのダウンサイジングにより不要になる場合や、変更を予期して作成したクラスが役に立っていない場合もあります。



疑わしき一般化(83)

「いつかこの機能が必要になるさ」と誰かが言い、現在は必要としていない凝った仕掛けや特殊な状況を考えているようなときには、警戒が必要です。そのままでは、往々にして難解で保守しにくいソフトウェアができあがることになります。これらのしかけがすべて使われていれ ば価値はあるのでしょうが、実際はそうではありません。無用の長物ならば、削除したほうがましです。



一時的属性(84)

変数の値が特定の状況でしか設定されないオブジェクトと出会った場合、コードは非常に理解 しづらくなります。使われていない変数が、いつ、どのように使われるのかを解読するのは、 とても大変ですね。



メッセージの連鎖(84)

あるオブジェクトから受け取った値を他のオブジェクトに送り、 それに対して受け取った値をさらに他のオブジェクトに送る…という場合、 オブジェクトをナビゲートする過程の構造に、クライアントが強く依存することになります。



仲介人(85)

カプセル化はしばしば権限の委譲をもたらしますが、これが過剰となる場合もあります。



不適切な関係(85)

クラス同士が、その必要もないのに密接に結びついています。乱用される双方向関連や継承に よって起こります。結びつきを持つクラスが増えると、変更があったときにそれを伝えること が大変になるため、修正も大変になります。



クラスのインタフェース不一致(85)

処理は同じでシグニチャのみが異なるメソッドがあります。



未熟なクラスライブラリ(86)

クラスライブラリの修正が不可能である場合に、どのように振る舞いを追加するかの指針とな るリファクタリングがあります。



データクラス(86)

属性とsetter/getter以外を持たないクラスは単なるデータ保持用であるため、他のクラスか らのアクセスを過剰に受けがちです。開発の初期段階では、こういったクラスの属性はpublic で定義されることもあります。カプセル化を忘れないようにしましょう。



相続拒否(87)

サブクラスは親の属性と操作を継承するのが普通ですが、ほんの一部しか利用していない場合 があります。



コメント(87)

コメントを書くのはとても良いことで、コードの読解に役に立ちます。しかし、非常に丁寧に 書かれているコメントは、わかりにくいコードを補うために書かれていることもあります。コ メントの必要性を感じたときにはリファクタリングを行って、コメントを書かなくても内容が わかるようなコードを目指しましょう。



つづき





この記事への評価にご協力をお願いします。

良かった 普通 イマイチ