クラスとは、強くて明確な責務(responsibility)を共有するデータとルーチンの集まりである。
— CODE COMPLETE 第6章 クラスの作成
プログラム全体を一気に頭に詰め込むべきではない。
プログラムの部分ごとに集中できるように、プログラムを整理して、一度に検討するプログラムの量は、最小限にとどめることを目指すべきである。
— CODE COMPLETE 5.2.1 ソフトウェアの鉄則:複雑さへの対処
有能なプログラマは自分の脳味噌のサイズがいかに制限されたものであるかをよく心得ています
— エドガー・W・ダイクストラ 謙虚なるプログラマ (The Humble Programmer)
Circle
に対する Shape
など )をプログラミングでは、抽象化がShapeのように用意されているわけではないので、
つじつまの合った抽象化を何とか考え出さなければならない。
適切な抽象オブジェクトを考え出すことは、オブジェクト指向設計における主な課題の1つである。
— CODE COMPLETE 6.4 クラスを作成する理由
クラスを作成する最も重要な理由は、プログラムの複雑さを低減することである。
クラスの抽象化の威力を利用しなければ、複雑なプログラムを頭で整理することは不可能である。
— CODE COMPLETE 6.4 クラスを作成する理由
全知全能のクラスを作成してはならない。
クラスがGet()ルーチンやSet()ルーチンを使って他のクラスからデータを取得することに明け暮れているなら
(つまり、他人の領分に首を突っ込み、あれこれ口出ししているようなら)、
それをゴッドクラスにまとめるよりも、他のクラスに整理する方がよいかどうか検討しよう
— CODE COMPLETE 6.4.1 望ましくないクラス
FooManager
BarHelper
FizzHandler
BuzzInfo
Supervisor
, Context
, Pool
, etc….
" は1行につき 1個まで(デメテルの法則)
何か新しいことをやりたいときに、
既存のクラスを 修正せずに そのまま、
簡単に利用出来る つくりになっていると素敵だね
クラス S
がクラス T
のサブクラスである場合に、
プログラム中で使われる T
のインスタンスは、
何ら修正を加えることなく S
のインスタンスに置き換えることが出来なければならない
public class Rectangle {
private int length;
private int breadth;
public int getLength() {
return length;
}
public void setLength(int length) {
this.length = length;
}
public int getBreadth() {
return breadth;
}
public void setBreadth(int breadth) {
this.breadth = breadth;
}
public int getArea() {
return this.length * this.breadth;
}
}
public class Square extends Rectangle {
@Override
public void setBreadth(int breadth) {
super.setBreadth(breadth);
super.setLength(breadth);
}
@Override
public void setLength(int length) {
super.setLength(length);
super.setBreadth(length);
}
}
サブクラスであることが制限にしか感じなくなったら怪しい
結局クラスごとの場合分け書いてたら怪しい
それは本当に is-a 関係なのか考えよう
java.util.ArrayList
kotlin.collections.ArrayList
実行時まで処理するドアの種類を知らないOpen()やClose()のような操作をサポートする言語の機能を「ポリモーフィズム」という。
— CODE COMPLETE 5.3.4 設計が単純になる場合の継承
■広範な型チェックよりもポリモーフィズムを選ぶ
case文の数が増えてきたら、継承を使って設計した方がよいという兆候かもしれない。
— CODE COMPLETE 6.3.2 継承(「is a」の関係)
class Bird {
// ...
double getSpeed()
switch (mType) {
case EUROPEAN:
return getBaseSpeed();
case AFRICAN:
return getBaseSpeed() - getLoadFactor() * mNumberOfCoconuts;
case NORWEGIAN_BLUE:
return (mIsNailed) ? 0 : getBaseSpeed(mVoltage);
}
throw new RuntimeException ("Should be unreachable");
}