オブジェクト指向プログラミングとは?【わかりやすい解説&トレーニング法紹介】
プログラミングの講師をしていて、よく「オブジェクト指向ってよく分からない」という相談をよく受けます。
多くの方の悩みを聞いて感じたのは…
「オブジェクト指向の本質」を理解していないと人が多いと感じました。
そもそもオブジェクト指向とは…?
オブジェクト指向とは、「モノの概念(オブジェクト)」を基準にしてプログラムを考えていく手法のことです。
この記事を読むことで、
オブジェクト指向とはそもそも何か?を直感的に知ってもらうだけでなく、誰でもオブジェクト指向脳になるトレーニングを紹介しております。
この記事は、以下の方におすすめです。
- オブジェクト指向についてぼんやりとしか理解していない。
- オブジェクト指向の用語は聞いたことがあるが…なんとなく苦手意識を持っている
- オブジェクト指向でプログラムを書けるようになりたい
- オブジェクト指向の勉強方法を知りたい
目次
1. オブジェクト指向のプログラミングの考え方
オブジェクト(モノの概念)とは?
例えば、携帯電話、コップ、パソコン、メール、人間、会社、商品、友達、日本…などの具体的なモノだけでなく、ゲームのルール、サービス、アプリケーション、仮想通貨、生き物、社会などの目には見えないけど、抽象的なものや概念として存在するも含めて、全てオブジェクトとしてプログラムを作ることができます。
よく勘違いされること…
「オブジェクト指向」=「カプセル化、継承、ポリモーフィズム」ではありません。 あくまでこれらは、オブジェクト指向でプログラムを書く時に、より効率的にプログラムを書くための道具(おまけ)に過ぎません。
オブジェクト指向で大事なことは、
「どういうモノの概念(オブジェクト)を定義」してプログラムを作成するかということが、非常〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜に大事です!!!
今回は、この「どういうモノの概念(オブジェクト)を定義」するのかについて、実際にワークをしながら体験してもらえればと思っています。
2. オブジェクト指向脳の作り方
オブジェクト指向プログラミングをできるようになるには、オブジェクト指向脳を作ることが大事です。なぜなら、プログラムを考えるスタート時点から全く異なるからです。
そもそもオブジェクト指向とよく対比されるのが、「手続き型プログラミング」です。こちらは、1つのファイルに上から下までプログラムが実行できるように書く手法のことです。
手続き型プログラミングの例:
String user1 = "Mike"
String user2 = "Emily"
JANKEN_TIMES = 5;
int winUser1 = 0;
int winUser2 = 0;
int handUser1 = 0;
int handUser2 = 0;
for (int i=0; i < JANKEN_TIMES ; i++){
Random rnd = new Random();
handUser1 = rnd.nextInt(3);
handUser2 = rnd.nextInt(3);
if (handUser1 % 3 == (handUser2 + 1) % 3){
winUser1++;
}else if(handUser1 == (handUser2 + 2)% 3){
winUser2++;
}
}
if (winUser1 > winUser2){
System.out.println(user1 + "の勝ち");
}
else if (winUser1 < winUser2){
System.out.println(user2 + "の勝ち");
}else{
System.out.println("同点");
}
しかし、オブジェクト指向のプログラムを書く場合は、このようなコーディングはしません。
最初に行うのは、オブジェクトの定義をすることです。
社会人一年目の研修では、基本的な構文(if文やfor文、配列など…)を「手続き型プログラミング」で学んだ後に、
いきなり「オブジェクト指向」という新しい手法でプログラムを書くのだから、混乱するのは当たり前です。
また、研修では「考え方」よりも「プログラムの書き方」しか教えないため、「なぜ、そのように書くのか?」を理解できずに1年経っても苦手意識が残ったままという人も多いのではないでしょうか?(実は私もそのうちの一人でしたw)
このように、オブジェクト指向のプログラムの書き方は根底から違うので、オブジェクト指向脳を使ったプログラムの書き方を学んでいきましょう。
それでは、早速オブジェクト指向脳を使ってプログラムを書くやり方について説明します。
STEPは大きく3つです。
ここからは実際にワークをしてオブジェクト指向脳トレーニングをしていきましょう。
STEP1:作りたいサービスのモノの概念を洗い出しする
例えば、ジャンケンゲームをプログラムで作ろうとした場合、どのようなモノの概念があるかを考えます。
例えば…
ジャンケンをするプレーヤー、ジャンケンの手(グー、チョキ、パー)、ジャンケンそのもの概念などが容易に挙がるかと思います。
それ以外にも例えば…
実際にはいないですが、ジャンケンを仕切ったり勝敗を決める審判や、ジャンケンプレーヤーの中にもコンピューター、人間という概念なども挙げられます。
基本的に、どのようなモノの概念を採用するかでプログラム自体も大きく変わります。
どのようなモノの概念を定義したら良いかは、経験を積んでいけばわかってきますが…
トレーニングをしたい人のために2つのワークを用意したので、ぜひ、オブジェクト指向脳を身に付けてもらえればと思います。
ワーク1:オブジェクトを探してみよう!
最初のワークは、オブジェクト探しゲームです。以下の2つのワークをそれぞれ取り組んでいきましょう。
ワーク1−1
- 将棋のゲームについて、存在するモノの概念を3つ以上挙げましょう。
ワーク1−2
- ECサイト(思い浮かばない人はAmazon)について、存在するモノの概念を3つ以上あげましょう。
チクタクチクタク……
みなさん、3つ以上挙がりましたでしょうか?
ワークの回答例としては…
■1−1:
将棋、ルール、駒、将棋の盤、プレーヤー、敵…
■1−2:
商品、本、カテゴリー、アカウント、ユーザー、商品一覧、発送手法…
などがあげられるかと思います。
このように、作りたいアプリケーションやサービスについて、
「どのようなモノの概念があるか」を洗い出すことが
オブジェクト指向プログラミングの第一歩になります。
STEP2:モノの概念のHAVEを定義する
先ほど定義したモノの概念について、深掘りしていく作業を行います。
最初は、そのモノの状態(ステータス)を表すものを考えます。
例えば、人間というモノの概念には、「名前、年齢、性別、国籍、職業、健康状態、モチベーション…」などがあります。
コップでいうと、「大きさ、水の最大容量、メーカー、色、現在入っている水の量...」などがあります。
このようにステータスを表すものは、HAVEになります。
STEP3:モノの概念のDOを定義する
最後に、DOを定義するです。
DOとは、そのオブジェクトが「する」ことや「される」ことをさします。
例えば、人間オブジェクトのDOには、「話す、聞く、見る、歩く、走る、寝る、食べる…」などがあります。
コップオブジェクトについては、「水を増やす、水を減らす、割られる..」などがあります。
ワーク2:オブジェクトのHAVEとDOを探してみよう!
それでは、オブジェクトのHAVEとDOを定義するワークとして、以下のワークをしてみましょう。
ワーク2−1
- 将棋の駒におけるHAVEとDOをそれぞれ2つずつ以上あげましょう。
ワーク2−2
- ECサイトのユーザーについて、HAVEとDOをそれぞれ3つ以上あげましょう。
チクタクチクタク……
それぞれHAVEとDOを見つけることができましたでしょうか?
例えばの回答を以下に載せますので、挙がらなかった人は確認してみましょう。
■2-1
HAVE:
種類、裏表、敵味方、進み方、取られたかどうか、初期位置..
DO:
進む、裏になる、相手のコマを取る、取られる、復活する、初期配置に設置する..
■2-2
HAVE:
アカウント名、ID、パスワード、メールアドレス、クレカ、住所、アカウントの無料・有料、ログイン中かどうか…
DO:
検索、購入、パスワード変更、お気に入り登録、住所を入力、クレカ情報変更…
以上で、オブジェクト指向脳を作るトレーニングは終了です。
実は、今のトレーニングがまさにオブジェクト指向でプログラミングをするための基礎です。
オブジェクト指向プログラミングの最初の一歩にこのトレーニングをしたら、誰でもオブジェクト指向を使ってプログラムを書くことができます。
実際にコードに落とし込むには、以下のように、表現してあげれば良いです。
(例)将棋のコマ
/* クラス */
class Koma{
/* フィールド */
String name; // 将棋の駒の名前
boolean isSenko; // 先手のコマor後手のコマ
boolean isOmote; // 表or裏
int[] moveScope; // 稼働範囲
boolean isRemoved; // 取られたかどうか
int[][] initPosition; // 初期配置
/* メソッド */
void move(); // 移動する
void changeSide(); // 裏面になる
void getKoma(); // コマを取る
void removeKoma(); // コマが取られる
void revival(); // 復活する
void init(); // 初期位置に配置する
}
上記のように1つのオブジェクトを「クラス」で表し、
「フィールド」をHAVE
「メソッド」をDO
で表現するだけです。
よければ、ご自身の作りたいサービスを思い浮かべて上記のワークをやってみて欲しいです!
オブジェクト指向プログラミングは、いきなりコードを書くのではなく…
「オブジェクトを定義すること」が第一歩であることがわかってもらえたかと思います。
ここが理解できたあなたは、もうすでにオブジェクト指向脳が出来上がっている状態です。
3. オブジェクト指向の今後のおすすめ勉強方法
最後にオブジェクト指向脳の使い方がわかったら、今後のおすすめ勉強方法についてお話しします。
私のおすすめは大きく2つです。
- 人の書いたコードを見ながら、自分で作りたいものを作る(初級)
- オブジェクト指向のデザインパターンを使ってみる(中級)
人の書いたコードを見ながら、自分で作りたいものを作る(初級)
オブジェクト指向プログラミングで一番大事なことは、最初のオブジェクトの定義です。
「他人がどのような設計でオブジェクトを定義しているのか」は非常に勉強になります。
初心者の方は特に、どのようなオブジェクトがあるのか、どのようなHAVEとDOが定義されているのかをみるようにしてください。
そして、自分の作りたいアプリケーションを0から設計してみるのが非常に良いと思います。
それを行う理由は、以下の通りです。
- モチベーションが高く取り組めるし、愛着が湧く
- わかったつもりになっているところが明確になる
- 設計の考え方が身につく
オブジェクト指向脳の考え方ができれば、設計も同じような頭の使い方をすれば良いので、非常に効率よく成長することができます。
オブジェクト指向のデザインパターンを使ってみる(中級)
みなさんは、「オブジェクト指向のデザインパターン」というのを聞いたことがありますでしょうか?
正直、自分は社会人一年目では全く知りませんでした。
実際に、オブジェクト指向でプログラムを書こうとしたときに、以下のような悩みが出てくるかと思います。
- ポリモーフィズムって実際どうやって使うのか…
- 継承ってこの使い方で合っているのか…
- いろんなオブジェクトを定義してごちゃごちゃになっている
- 複数のオブジェクトを関連させたいけど、どうしたら良いか…
要するに、
「オブジェクト指向をどうやって使ってコーディングしていいかわからない。」
ということです。
基礎文法の知識が身につくと、誰しもがぶち当たる壁かと思います。
この悩みを抱えたら、手にして欲しい本がこちらです。
正直、この本を読んだ後、確実にレベルアップします。
なぜなら、このオブジェクト指向のデザインパターンは、言って仕舞えば先人の天才たちの知恵袋です。
オブジェクト指向のうまい使い方がテンプレートとして集約されています。
実際に、標準ライブラリのコードの中身を見ると、これらのデザインパターンが多く使われています。
全てのパターンを暗記する必要はないですが…いくつか実際にコーディングして動かしてみると、とても良いと思います。
最後に、そちらの本にも書いてあるオブジェクト指向プログラミングをする上でのあり方について触れたいと思います。
そレは、映画監督 もしくは 世界の神様になることです。
映画監督は、舞台の俳優さんを選んでセリフを決めます。
神様は、人や動物、自然などを想像して役割を与えます。
これらと同様に、プログラミングの世界も好きなものを想像し、好きな役割を与えることができます。
これが、オブジェクトを定義し、特徴(HAVE)や機能(DO)を与えることなのです。
オブジェクト指向を身につけて、自分の世界を作ることを楽しんでもらえると良いなと思っています。
好評であれば、オブジェクト指向の実際のコーディングの基礎知識についても記事にできればお思いますので、ご期待ください。
人気記事 Springbootの環境構築から Hello worldまで on Mac
人気記事 DockerでMySQLとphpAdminのコンテナを作るやり方