コンストラクタ
メソッド(関数)だよ
クラスをnewしたときに実行されるよ
オブジェクト指向なプログラミング言語で出てくるよ
簡単に書くよ
コンストラクタ(英:constructor)とは
オブジェクト指向
(「モノ」に注目した考え方)なプログラミング言語で出てくる用語のひとつ
であり
インスタンス
(オブジェクト指向の話で出てくる概念のひとつでクラスを具現化した実体)を作ったタイミングで実行されるメソッド
(「オブジェクトの操作を定義したもの」だけど、動きとしては関数と同じ)のこと
です。
もう少し身も蓋もない言い方をすると
クラス
(オブジェクト指向の話で出てくる概念のひとつで「設計図」っぽいやつ)をnew
(インスタンスを作る行為)した瞬間に実行される関数
(処理のまとまり)のこと
です。
詳しく書くよ
順番に見ていきましょう。
まずは予備知識として
・関数
・オブジェクト指向
・クラス
・インスタンス
・メソッド
・newする
について説明します。
「そんなの説明されなくても知ってるよ!」な人は適当に読み飛ばしてください。
関数は「何かを入れると何かをやって何かを返してくれる、処理のまとまり」です。
一般的には、入力を受けて処理をやり、その結果として出力があります。
ついでなので書いておくと、関数に入れる値は「引数(ヒキスウ)」と言います。
関数から出てくる値は「戻り値」です。
ちょっと汚い話で恐縮ですが、人間は、ご飯を食べて、ウンチを出します。
人間が関数だと考えてください。
ご飯に相当するものが引数です。
ウンチに相当するものが戻り値になります。
オブジェクト指向は「『モノ』に注目した考え方」です。
「どんなやつで、どう動く」に注目した考え方です。
詳細は、用語「オブジェクト指向」の説明を ご覧ください。
オブジェクト指向の理念に沿って作られたプログラミング言語を「オブジェクト指向プログラミング言語」と言います。
有名どころでは、Javaなんかがオブジェクト指向プログラミング言語です。
オブジェクト指向プログラミング言語では
・クラス
・インスタンス
・オブジェクト
の3つの用語が よく出てきます。
この3つは とても大事です。
ざっくりとで良いので関係性を覚えておいてください。
専門家の人からは怒られそうですが、ものすごい大雑把に説明すると
クラス:設計図
インスタンス:実際に作った物
オブジェクト:モノ(クラスとかインスタンスとかを、ふんわりと表現したもの)
です。
クラスは「設計図」です。
「それって、どんなもの?」を示しています。
ピヨ太君の頭の中にある「ピヨピヨ時計は こんな感じだな」がクラスです。
インスタンスは「実際に作ったもの」です。
クラス(設計図)に書かれた「それって、どんなもの?」を形にしたものを指します。
実際に作ったピヨピヨ時計がインスタンスです。
オブジェクトは……モノですよ、モノ。
結構ざっくりとした使われ方をする用語です。
「クラスとかインスタンスを ふんわりと表現したもの」くらいに解釈してください。
よく分からない人は忘れてしまって かまいません。
メソッドは、教科書的な説明をすれば「オブジェクトの『操作』を定義したもの」です。
ただし、今回は
クラス内に定義した関数のこと
と解釈してください。
その方がイメージしやすいと思います。
「newする」は「クラスからインスタンスを作る行為」を指す慣例的な表現です。
インスタンスを作るときは「New演算子」という演算子を使います。
だからでしょう。
以上を踏まえて
クラスをnewしたとき(インスタンスを作ったとき)に実行される関数
が「コンストラクタ」です。
実際の処理を見た方が手っ取り早いと思うので、Javaで書いたソースコード(プログラムの元ネタ)をもとにして説明します。
まずは最初の状態です。
「Hello world」を表示するJavaのソースコードが ありました。
public class test01{
public static void main(String[] args){
System.out.println("Hello World");
}
}
ここに「Piyota」クラスを追加してみます。
//「Piyota」クラス
class Piyota {
String name;
void setName(String _name){
this.name = _name;
}
String getName(){
return this.name;
}
}
public class test01{
public static void main(String[] args){
System.out.println("Hello World");
}
}
「Piyota」クラスには「name」という名前のメンバ変数があります。
メンバ変数が何か気になる方は、用語「メンバ変数」の説明を ご覧ください。
また「setName()」「getName()」という名前のメソッドがあります。
さて、この「Piyota」クラスですが、そのままでは使えません。
クラスは、あくまで設計図です。
この設計図をもとにして実際のもの(インスタンス)を作る作業が必要になります。
いわゆる「newする」必要があるのです。
Javaの場合、設計図から実際のものを作るときは、例えば以下のように書きます。
Piyota p = new Piyota();
簡単に説明しておくと
Piyota p
の部分は
「Piyota」クラスの形をした物が入る箱を作って、それに「p」という名前を付けるよ
の意味です。
プログラミングにおける「=」は「代入」を意味します。
右側のものを左側に入れる操作をします。
new Piyota();
の部分は
「Piyota」クラスを実際に作るよ!
を意味します。
全体としては
「Piyota」クラスを実際に作って、それ(を入れた箱)に「p」という名前を付けるよ!
な処理になります。
このnewする処理を先ほどのソースコードに追加してみましょう。
class Piyota {
String name;
void setName(String _name){
this.name = _name;
}
String getName(){
return this.name;
}
}
public class test01{
public static void main(String[] args){
//newする
Piyota p = new Piyota();
System.out.println("Hello World");
}
}
そして「Piyota」クラスの「name」の値を画面に表示してみます。
class Piyota {
String name;
void setName(String _name){
this.name = _name;
}
String getName(){
return this.name;
}
}
public class test01{
public static void main(String[] args){
Piyota p = new Piyota();
//画面表示
System.out.println(p.getName());
System.out.println("Hello World");
}
}
このプログラムを実行すると、どうなるでしょうね?
実行結果は以下のようになります。
null
Hello World
「null」は「何もないよー」を意味する表現です。
「Piyota」クラスの「name」には何も値が設定されていません。
確かに、そうですね。
「name」には何も入れていません。
何も入っていなくて当たり前です。
さぁ、長らくお待たせしました。
いよいよコンストラクタの登場です。
コンストラクタは
クラスをnewした瞬間に実行される関数
です。
あと、ついでなので書いておくと、Javaにおけるコンストラクタは
・クラス名と同じ名前にする必要がある
・戻り値(関数から戻す値)は返せない
というルールがあります。
それでは先ほどのソースコードに「Piyota」クラスのコンストラクタを追加してみましょう。
class Piyota {
String name;
//コンストラクタ
Piyota(){
}
void setName(String _name){
this.name = _name;
}
String getName(){
return this.name;
}
}
public class test01{
public static void main(String[] args){
Piyota p = new Piyota();
System.out.println(p.getName());
System.out.println("Hello World");
}
}
ついでなので、コンストラクタの中で「name」に値「piyota」を設定しておきます。
class Piyota {
String name;
Piyota(){
//値設定
this.name = "piyota";
}
void setName(String _name){
this.name = _name;
}
String getName(){
return this.name;
}
}
public class test01{
public static void main(String[] args){
Piyota p = new Piyota();
System.out.println(p.getName());
System.out.println("Hello World");
}
}
このプログラムを実行すると、以下のような結果になります。
piyota
Hello World
先ほど「null」だった「name」の値が「piyota」になりました。
これはコンストラクタ内で
this.name = "piyota";
を実行して値を設定しているからです。
えっ?
本当にnewした瞬間に実行されているのか?ですか?
疑り深いですねー。
それでは以下のようなソースコードではどうでしょうか。
class Piyota {
String name;
Piyota(){
//メッセージ出力
System.out.println("constructor");
this.name = "piyota";
}
void setName(String _name){
this.name = _name;
}
String getName(){
return this.name;
}
}
public class test01{
public static void main(String[] args){
//メッセージ出力
System.out.println("before new");
Piyota p = new Piyota();
//メッセージ出力
System.out.println("after new");
System.out.println(p.getName());
System.out.println("Hello World");
}
}
このプログラムを実行すると以下のような結果になります。
before new
constructor
after new
piyota
Hello World
いかがでしょう。
before new
↓
constructor
↓
after new
の順番で表示されていますよね。
コンストラクタがnewした瞬間に動いていることが分かります。
このように、コンストラクタは
クラスをnewした瞬間に実行される関数
です。
最初にやっておかなくちゃいけない処理、例えばメンバ変数の初期化処理などでよく活用されます。
注意点として、コンストラクタには戻り値が返せなかったりな制限があります。
あまり複雑なことはやらせない方が良いでしょう。
さらに専門的な話になってしまいますが、Javaには「継承」という概念があります。
何も考えずにコンストラクタを定義してしまうと、親クラスのコンストラクタを上書きしてしまう場合があります。
ご注意ください。
super();
と書くと、親クラスのコンストラクタを呼び出せます。
親クラスのコンストラクタも生かしておきたい場合は、自分で定義したコンストラクタ内で呼び出してあげてください。
一言でまとめるよ
まぁ「コンストラクタ」って単語が出てきたら「クラス
(オブジェクト指向の話で出てくる概念のひとつで「設計図」っぽいやつ)をnew
(インスタンスを作る行為)した瞬間に実行される関数
(処理のまとまり)なんだな~」と お考えください。






