はじめに
今回の記事では、プログラミングの基本をふまえて、「クラス」をより便利に使うための「インスタンス変数」「コンストラクタ」について説明していきます。つまずきやすい部分(実際に筆者がつまずいた部分)を中心に、初心者にもわかりやすく順を追って説明していきます。
もくじ
- はじめに
- おさらい・・・クラスとインスタンスの振り返り
- クラスで変数も使ってみたい! ・・・便利な「インスタンス変数」
- 「インスタンス変数」の定義の仕方・・・「コンストラクタ」という特殊なメソッドを使おう
- クラスとインスタンスを作ってみよう!・・・RPGキャラクターを作って動かしてみる
- まとめ
おさらい ~「クラス」と「インスタンス」の振り返り~
プログラムを現実世界のモノに見立てようとする考え方をオブジェクト指向といい、その基本には「クラス」と「インスタンス」がありました。
「クラス」という設計書のような鋳型を定義して、それをもとに「インスタンス」という実体をつくることで、クラスに書かれているメソッド(処理)を呼び出すことができました。この「クラス」と「インスタンス」を使うことによって、複雑な処理をひとまとめに整理することができ、プログラムの管理や変更が楽になります。
クラスのなかで変数を定義するには? 便利な「インスタンス変数」
前回までは、「クラス」にメソッドを定義し、「インスタンス」を作成することでメソッドを呼び出すことができました。それでは、クラスではどのように変数を扱うのでしょうか?
☆便利な「インスタンス変数」
さっそく例をあげていきます。今回は、クラスを使ってRPGのゲームキャラクターを作成していきます。キャラクタークラスをもとにして、騎士と魔法使いのインスタンスを作ってみます。
Pythonのクラスにはインスタンス変数とよばれる変数があります。これは、ひとつのインスタンス内のメソッドで共有できる変数です。これらの変数の値は、そのインスタンス内のメソッドからしかアクセスできません。どういうことかというと…
上の画像では「名前」「HP」がインスタンス変数です。
たとえば、キャラクタークラスから騎士インスタンスを作って、「××が攻撃した!」「××が防御した!」というメソッドを呼び出すとします。
このとき、騎士インスタンスのインスタンス変数:名前は「アーサー」なので、「アーサーが攻撃した!」というふうに参照できます。しかし、騎士インスタンスで呼ぶメソッドで魔法使いインスタンスの名前を参照することはできないので、「オズが攻撃した!」とは表示できません。
つまり、どういう属性の値を持つか、どういう処理をするかはすべてのインスタンスで同じですが、インスタンスがもっている具体的な値はそれぞれ別ということになります。
「インスタンス変数」を作ろう …「コンストラクタ」というメソッドを使う
インスタンス変数は、「コンストラクタ」と呼ばれる特殊なメソッドを使って定義します。これは、インスタンスが作成されるタイミングで勝手に実行されるメソッドです。
コンストラクタはこのように書きます。
initはinitialize(初期化)の略であり、「コンストラクタによって、インスタンスに初期値を入力しておく」と捉えると分かりやすい!
pythonにおけるコンストラクタには_ _init_ _という表記があり、これは変更することができません。左右のアンダーバーは、「これは特殊なメソッドですよ」ということを示しています。また、「self.name」「self.hp」の部分がインスタンス変数です。インスタンス変数にはselfをつけます。
上の図ではコンストラクタに引数(self, name, hp)がありますが、引数があることによって各インスタンス変数の値をバラバラにセットしておくことができます。
・引数なしのコンストラクタ・・・固定値など 全部同じ値をもったインスタンス変数になる
例:いくつインスタンスを作っても名前が「アーサー」
・引数ありのコンストラクタ・・・引数によってインスタンス変数の初期値を変えられる
例:引数によってインスタンスでの名前を「アーサー」「オズ」などに変更しておける
コンストラクタで定義したインスタンス変数を、メソッド間で共有することができ、また書き換えることも容易にできます。インスタンス変数は、インスタンスから直接参照することもできます。
☆コンストラクタを設定しなかったらインスタンス変数はどうなる?
・・・コンストラクタを使わないと、インスタンス変数に値が入らないので、名前:なし、HP:0の幽霊のようなキャラクターしか作成することができません。
クラスとインスタンスを作ってみよう! RPGキャラクターを作って動かす
クラスにおけるインスタンス変数について学んだところで、クラスにおけるデータの扱いと処理がそろいました。さっそくクラスを作って遊んでみましょう!
これまでの例に挙げたように、RPGのキャラクタークラスを使ってキャラクターを動かしていきます。騎士と魔法使いをつくり、それぞれに攻撃や防御をさせるところまでをクラスを用いて実際にプログラムを書いてみます。
まずはもととなるキャラクタークラスを作っていきます。
class Character():
作るキャラクターには、名前・HP・役職の情報を持たせたいとします。この情報はキャラクターによってバラバラになるので、インスタンス変数(名前,HP,役職)として、コンストラクタを使って定義していきます。今回は、作成するキャラクターごとに名前やHPが違うので、引数ありのコンストラクタを使います。
def __init__(self, name, HP, job): 引数に入ってきた値を、インスタンスの初期値に代入する
self.name = name
self.HP = HP
self.job = job
つぎに、すべてのインスタンス(キャラクター)で共通するメソッド(攻撃、防御)をクラスに定義していきます。××は攻撃した!というメッセージを出して表したいので、××の部分にインスタンス変数:名前を入れます。
def attack(self):
print('{}は攻撃した!'.format(self.name))
def defence(self):
print('{}は防御した!'.format(self.name))
self.nameはインスタンス変数なので、例えば騎士インスタンスではオズという名前は使えません。また、攻撃メソッドと防御メソッドのどちらでもself.nameが使えているように、インスタンス内のどのメソッドでも同じ値が入ります。
これでクラスの定義は完了しました。さっそくインスタンスを作り、メソッドを呼び出していきます。
Arthur = Character('アーサー', 100, '騎士')#ここで引数に入れた値がコンストラクタに渡る
Oz = Character('オズ', 80, '魔法使い')
Arthur.attack()
Oz.defence()
表示は以下になります。
以上でクラスによるプログラミングは完了です。今回表示したのは名前と行動だけでしたが、このクラスを使えば、「攻撃メソッドに数値を設定して、体力の値(インスタンス変数)によって攻撃に数値を増減する」など、変更を加えることがとても楽になります。
まとめ
オブジェクト指向の考え方の基本に「クラス」と「インスタンス」があります。
「クラス」で定義したメソッドは「インスタンス」という実体を作成すると呼び出すことができます。
インスタンスによってバラバラの値を持つ変数を「インスタンス変数」と呼び、これは「コンストラクタ」という特殊なメソッドを使ってクラス内で定義することができます。
インスタンス変数はそのインスタンス内のどのメソッドでも同じ値を使用することができ、インスタンスから直接参照することも可能です。
クラス内でメソッドとインスタンス変数を定義できるようになると、クラスを使ってより幅広く柔軟にプログラミングすることができます。
次回は、オブジェクト指向における応用の考え方について詳しく解説していきます。
ここまで読んでくださってありがとうございました!
コメント