抽象クラス(Abstruct Class)
抽象クラスとは、
- 抽象メソッドを定義できる
- 抽象クラスは継承することで利用する。
- 抽象クラスから直接インスタンスを生成(new)できない
という特徴です。この2点以外は通常のクラスと同じです。抽象メソッドとは、処理実体のないメソッドのことです。つまり、メソッド名、引数、戻り値などは定義されていますが、その関数で実際にどのような処理をするかは記述していないという特徴を持ちます。
抽象クラスを利用するメリット
抽象クラスを利用するのは、メソッドの処理内容がその利用クラス(継承するクラス)によって、処理が異なってくる場合に有効です。
抽象クラスの記述例
以下のプログラムを入力してみましょう。
TempSample.java
/**
* 抽象クラスの定義
*/
abstract class human{
abstract void morning();
abstract void evening();
abstract void night();
public void life(){
morning();
evening();
night();
}
}
/**
* human を継承したクラス。ここで抽象メソッドを実装している
*/
class student extends human{
void morning(){
System.out.println("あかん、寝坊した");
}
void evening(){
System.out.println("大学でお勉強");
}
void night(){
System.out.println("バイトして寝る");
}
}
class worker extends human{
void morning(){
System.out.println("いつも早起き!");
}
void evening(){
System.out.println("バリバリ働いてます");
}
void night(){
System.out.println("今日も残業だー");
}
}
public class TempSample {
public static void main(String[] args) {
student st = new student();
st.life();
worker wk = new worker();
wk.life();
//ちなみにこういう呼び方もできます
hm = new worker();
hm.life();
hm = new student();
hm.life();
}
}
(解説)
- humanクラスは、抽象(abstract)クラスです。
- humanクラスでは、morining(),evening(),night()というメソッドが抽象クラスになっています
- humanクラスでは、life()というメソッドが定義されており、その中では morining(),evening(),night()の各メソッドを呼び出すことが定義されています。
- workerクラスとstudentクラスは、humanクラスを継承しています
- workerクラスとstudentクラスで、それそれの抽象クラスでの実際の処理内容を定義しています。
演習問題
上記クラス構造をUMLで書きなさい
ただし、抽象クラスはクラス名をイタリック風にするか、クラス名の下に {abstract} と記述してください。
抽象メソッドは、イタリック風に書いてください
継承によるポリモーフィズムの実現
ここで、継承に関する話に戻ります。オブジェクト指向言語にはポリモーフィズムと言われる特徴があります。
ポリモーフィズムとは、日本語に訳せば多様性とも呼ばれます。ちょっとむずかしいですが、簡単にいえば、
異なるオブジェクトや処理を共通的に扱う
という意味があります。継承関係にあるオブジェクトは、同一に扱うことができます。上記のプログラムを見てください。mainメソッドの最後のほうに、「ちなみにこういう呼び方もできます」というコメントの以下のプログラムを見てください。
上述のmainメソッドのクラスの部分を再掲
public class TempSample {
public static void main(String[] args) {
human hm;
student st = new student();
st.life();
worker wk = new worker();
wk.life();
//ちなみにこういう呼び方もできます
hm = new worker();
hm.life();
hm = new student();
hm.life();
}
}
変数 hm はhumanクラスです。ですが、wokerクラスやstudnetクラスをnewした結果を受け取っていますね。で、それぞれでlifeメソッドを実行していますが、その挙動は studentクラスやworkerクラスで実装された処理が行われています。
つまり、workerもstudentもhumanを継承したものであるから、つまりどっちもhumanとして扱えるということです。
注意点
クラスAがスーパークラス、クラスAのサブクラスがBとします。つまり、class B extends A という関係にあるとします。この時は以下のような関係になるので注意してください。
よい例、ダメな例
A a = new B(); // これはOK
B b = new A(); // これはダメ
また、クラスBでなにかのメソッドを追加した場合でも、A a = new B()と呼び出した場合は、追加したメソッドは使えないということに注意して下さい。