Kotlinの抽象クラス・インターフェースの違いと使い分けを初心者向けにやさしく解説!
生徒
「Kotlinで“抽象クラス”とか“インターフェース”って出てきましたけど、何が違うんですか?」
先生
「それはKotlinのクラス設計でとても重要なポイントです。両方とも“共通のルール”を決めるものですが、使い方や目的が少し違うんですよ。」
生徒
「具体的にどんな時に使い分ければいいんでしょうか?」
先生
「では、Kotlinの抽象クラスとインターフェースについて、特徴と違いを一緒に見ていきましょう!」
1. 抽象クラスとは?Kotlinでの基本
Kotlinの抽象クラス(abstract class)とは、「共通の機能や動きをまとめておくけれど、そのままでは使えないクラス」のことです。あくまで“設計図”のような存在で、実際に動かすには子クラスで具体的な中身を書き足します。
たとえば「動物」という大きなグループを考えると、どの動物も眠りますが、鳴き方は動物ごとに違いますよね。このとき、「眠る」処理は共通で、「鳴く」処理だけそれぞれの動物に任せるような形が抽象クラスです。
abstract class Animal {
// 鳴き方は動物によって違うので、中身は書かずに約束だけ
abstract fun makeSound()
// 眠る動作は共通なので、そのまま使える
fun sleep() {
println("眠っています")
}
}
抽象クラスのポイントは、abstractを付けた関数には中身がないこと。これが「設計図だけがある状態」です。実際に使うには、子クラスで具体的な処理を必ず書く必要があります。
もう少しイメージしやすい例を見てみましょう。
class Cat : Animal() {
override fun makeSound() {
println("ニャーと鳴いています")
}
}
fun main() {
val cat = Cat()
cat.makeSound() // 子クラスで作った処理
cat.sleep() // 親クラスの共通機能
}
ニャーと鳴いています
眠っています
このように、抽象クラスは「共通の機能を持ちつつ、部分的に子クラスへ任せる」ために使われます。コードを整理しやすくなるので、Kotlinでしっかり覚えておきたい仕組みです。
2. 抽象クラスを継承して使う
抽象クラスは、そのままでは使えない“設計図”なので、実際に動かすには子クラスで継承します。そして、abstractが付いた関数は、必ず子クラス側で中身を書く必要があります。これをoverrideと呼びます。
イメージとしては「親がざっくりルールを決めて、子が具体的なやり方を決める」ようなものです。では、先ほどのAnimalを使って、犬のクラスを作ってみましょう。
class Dog : Animal() {
override fun makeSound() {
println("ワンワン!")
}
}
makeSound()に中身が追加され、「犬が鳴くときの処理」が完成しました。この時点でようやく実行できる形になっています。
fun main() {
val dog = Dog()
dog.makeSound() // 子クラスで作った処理
dog.sleep() // 親クラスの共通機能
}
ワンワン!
眠っています
ここで注目したいのは、子クラスで書き直した関数と、親クラスのまま使える関数が共存していることです。Kotlinでは、このように「共通部分は親に置き、違う部分だけ子クラスごとに作る」という書き方ができるので、コードの重複を減らし、読みやすく整理できます。
3. インターフェースとは?Kotlinでの基本
インターフェース(interface)も、「クラスに必要な機能のルール」を決めるしくみです。
ただし、インターフェースには「状態(プロパティ)」を持たせることができず、「機能(関数)」だけを決めるのが基本です。
簡単に言えば「やり方だけを約束する契約書」です。
interface Flyable {
fun fly()
}
4. インターフェースの実装方法
インターフェースを使いたいクラスは:を使ってinterfaceを「実装」します。
class Bird : Flyable {
override fun fly() {
println("パタパタ飛んでいます")
}
}
fun main() {
val bird = Bird()
bird.fly()
}
パタパタ飛んでいます
インターフェースの関数は必ずoverrideで実装しないといけません。
5. 抽象クラスとインターフェースの違い
ここで、Kotlinの抽象クラスとインターフェースの違いを整理しておきましょう。
- 抽象クラスは「機能(関数)」と「状態(プロパティ)」の両方を持てる。
- インターフェースは主に「やるべきこと(関数)」だけを書く。
- クラスは1つの抽象クラスしか継承できないが、インターフェースは複数実装できる。
6. インターフェースの複数実装ができる例
Kotlinでは、インターフェースをいくつも同時に実装できます。
interface Walkable {
fun walk()
}
class Human : Walkable, Flyable {
override fun walk() {
println("歩いています")
}
override fun fly() {
println("想像の中で飛んでいます")
}
}
fun main() {
val person = Human()
person.walk()
person.fly()
}
歩いています
想像の中で飛んでいます
このように、WalkableとFlyableという2つのインターフェースを同時に使えます。
7. どちらを使うべき?使い分けのポイント
Kotlinで抽象クラスとインターフェースを使い分けるときは、次のようなポイントで判断します。
- 共通のプロパティ(状態)を持たせたい → 抽象クラス
- 複数の動作ルールを柔軟に追加したい → インターフェース
- 他のクラスをすでに継承している → インターフェース(多重継承が可能だから)
どちらも「共通ルール」を決めるためのものですが、役割と使い方が少しずつ違います。
8. 抽象クラスとインターフェースの使い方を身近な例で
例えば、「家電」という抽象クラスがあり、共通で電源を入れる関数とメーカー名という情報があるとします。
一方、「ネット接続できる機能」はどんな家電でも持てるように、インターフェースとして用意します。
abstract class Appliance(val brand: String) {
abstract fun turnOn()
}
interface NetworkCapable {
fun connectToWifi()
}
class SmartTV(brand: String) : Appliance(brand), NetworkCapable {
override fun turnOn() {
println("$brandのテレビを起動します")
}
override fun connectToWifi() {
println("Wi-Fiに接続しました")
}
}
fun main() {
val tv = SmartTV("ソニー")
tv.turnOn()
tv.connectToWifi()
}
ソニーのテレビを起動します
Wi-Fiに接続しました
このように、抽象クラスとインターフェースを組み合わせることで、柔軟で分かりやすい設計ができます。
まとめ
Kotlinのクラス設計において、「抽象クラス」と「インターフェース」は非常に重要なキーワードです。今回の記事では、それぞれの役割や違い、使い分けの考え方を初心者向けにやさしく解説しました。
抽象クラスは、共通する処理や状態(プロパティ)を持ちつつ、子クラスで処理内容を具体的に実装させたいときに使います。一方でインターフェースは、「何ができるか」という動作(関数)のルールだけを定めたいときに利用します。つまり、抽象クラス=共通の設計図+機能実装、インターフェース=行動の契約書と覚えておくとわかりやすいです。
特にKotlinでは、クラスはひとつの抽象クラスしか継承できませんが、インターフェースは複数同時に実装できるという特徴があるため、柔軟な設計が求められる現場ではよく併用されます。以下は、抽象クラスとインターフェースを組み合わせた実践的なコード例です。
abstract class Vehicle(val name: String) {
abstract fun start()
fun stop() {
println("$name を停止します")
}
}
interface Electric {
fun charge()
}
class EVCar(name: String) : Vehicle(name), Electric {
override fun start() {
println("$name のエンジンを起動します")
}
override fun charge() {
println("$name を充電中です")
}
}
fun main() {
val tesla = EVCar("テスラ")
tesla.start()
tesla.charge()
tesla.stop()
}
テスラ のエンジンを起動します
テスラ を充電中です
テスラ を停止します
このように、抽象クラスによって共通の処理(startやstopなど)を提供し、インターフェースによって追加の動作(charge)を柔軟に定義できる設計は、現実のアプリ開発でも多く見られます。
プログラミング初心者のうちは、「継承って難しい」「overrideって何?」と感じるかもしれませんが、動物や乗り物、家電などの例でイメージをつかみながら学ぶと理解しやすくなります。また、「プロパティが必要なら抽象クラス」「動作だけならインターフェース」といった判断基準を持っておくと、設計の幅がぐっと広がります。
Kotlinでオブジェクト指向を学ぶには、まずこの2つの違いと使い方をしっかり理解することが大切です。今回の内容をもとに、実際のプロジェクトでも応用してみてください。
生徒
「抽象クラスとインターフェースって、どちらも似てるけど、使い方がぜんぜん違うんですね。」
先生
「そうです。共通する動きや状態をまとめたいなら抽象クラス、行動のルールだけを決めたいならインターフェースが向いていますよ。」
生徒
「あと、インターフェースは複数同時に使えるのが便利ですね!家電とか乗り物の例がとてもわかりやすかったです。」
先生
「その調子です。設計力をつけるには、こうした基本をしっかり理解しておくことが大切です。今後は実際にコードで書いてみるともっと理解が深まりますよ。」
生徒
「はい!次は自分でも抽象クラスとインターフェースを組み合わせて何か作ってみます!」
先生
「とてもいいですね。練習を重ねることで、自然に使い分けができるようになりますよ。」
Kotlinを基礎からしっかり学びたい人や、 Java経験を活かしてモダンな言語にステップアップしたい人には、 定番の入門書がこちらです。
基礎からわかるKotlinをAmazonで見る※ Amazon広告リンク
この記事を読んだ人からの質問
プログラミング初心者からのよくある疑問/質問を解決します
Kotlinの抽象クラスとインターフェースの違いがまだよく分かりません。簡単に言うとどう違うのですか?
抽象クラスは「共通の機能や状態を持つ親クラス」として使い、インターフェースは「複数のクラスに共通の機能ルールを与える契約書のようなもの」です。
Kotlinで抽象クラスを使う具体的なメリットは何ですか?
Kotlinで抽象クラスを使うと、複数の子クラスに共通する処理やプロパティをひとつの親クラスにまとめることができ、コードの再利用や保守がしやすくなります。
【未経験OK】Kotlinで始めるプログラミング入門|ゼロから「動く喜び」を体験する60分
「プログラミングを始めたい」を形にする。最新言語Kotlinで楽しむ、ものづくりの第一歩。
本講座は、プログラミング経験が全くない方のためのエントリー講座です。「コードを書くってどういうこと?」という基本から、世界中で使われている最新言語Kotlin(コトリン)を使って、実際にプログラムを動かすまでを体験します。難しい理屈よりも、まずは「自分の手で動かす楽しさ」を最短距離で実感していただきます。
具体的な体験内容と環境
【つくるもの】
簡単な言葉を入力すると自動で返答してくれる「対話型ミニプログラム」や、計算を自動化する「便利ツール」をゼロから作成します。黒い画面に自分の書いた文字が表示される瞬間は、最高の感動体験です。
【開発環境】
プロのエンジニアが実際に使っている開発ツールIntelliJ IDEA(インテリジェイ)をインストールします。ボタン一つで日本語化し、初心者でも迷わず操作できる「魔法の設定」を一緒に行います。
この60分で得られる3つの体験
プロと同じ道具を揃えることで、明日から一人でもプログラミングを続けられる環境が整います。
「変数」や「型」といった難しい言葉も、身近な例え話で解説。モヤモヤをゼロにします。
Kotlinは英語に近くて読みやすいのが特徴。自分でコードを読んで、間違いを見つけるコツも伝授します。
※本講座は、パソコン操作が不安な方でも安心して受講いただける完全マンツーマンです。あなたのペースに合わせて、一つずつ丁寧に進めていきます。
Kotlinで始めるプログラミング入門|ゼロから「動く喜び」を体験