【Java】newした瞬間に準備完了!「コンストラクタ」でコードをスッキリさせよう
はじめに
みなさんどうも、おげんです。
前回の記事では、設計図(クラス)から実体(オブジェクト)を召喚する方法を学びました。
でも、実際にコードを書いてみて、私は少しだけ「面倒だな…」と感じてしまったんです。
というのも、せっかく new でカレーを召喚しても、その後にわざわざ「名前はこれ!」「辛さはこれ!」と1行ずつ指定してあげないと、中身が空っぽのままだったからです。
「召喚したその瞬間に、中身もバシッと決まっていたら楽なのに」
そんな私の願いを叶えてくれたのが、今回紹介する 「コンストラクタ」 という仕組みです。
これを使えば、オブジェクトが生まれた瞬間に、必要なデータをすべてセットしておくことができます。
いわば、オブジェクトにとっての「誕生祝い」のような、とっても大切な処理について一緒に見ていきましょう!
newの後の代入作業をスッキリさせたい人- コードの中に突然出てくる
thisという言葉に混乱している人 - Javaの「初期化」という考え方をしっかり理解したい人
コンストラクタは「工場出荷時の設定」
新しくスマホを買った時のことを思い出してみてください。
これまでのやり方(手動で設定)
店員さんから「中身が真っ白なスマホ」を渡されます。
家に帰ってから、自分で一生懸命「壁紙はこれ」「言語は日本語」「着信音はこれ」と、一つずつ設定していくイメージです。
Javaでいうと、new した後に何行も代入文(mildCurry.name = "..." など)を書いていた状態ですね。
コンストラクタのやり方(オーダーメイド)
注文する時に「壁紙はこれで、設定はこうしておいて!」と伝えておきます。
すると、手元に届いた(newした)瞬間から、すでに自分好みの設定が完了している状態で使い始めることができます。
なぜこれが嬉しいのか?
私がコンストラクタを知って「これはいい!」と思った理由は2つあります。
- 設定漏れがなくなる 手動でやっていると、「あ、名前を入れ忘れた!」というミスが起きがちです。コンストラクタを使えば、設定を強制できるので、不完全な「中身が空っぽのオブジェクト」が生まれるのを防げます。
- コードが短くなる 今まで4行かかっていた準備が、たった1行で終わります。
いわば、オブジェクトがこの世界に誕生する瞬間に、「あなたはこういうデータを持って生まれてきてね!」と約束を交わすようなものなんです。
書き方のルール(クラス名と同じ名前にする!)
コンストラクタを作るには、絶対に守らなければならない3つの鉄則があります。
① 名前は「クラス名」と一字一句同じにする
これが一番のルールです。
クラス名が Curry なら、コンストラクタの名前も必ず Curry にします。
大文字・小文字も完全に一致させる必要があります。
② 「戻り値」を書かない
メソッドなら void や int と書く場所に、何も書きません。
「戻り値を書かないのは、もう『そのクラス自身』を作って返すことが決まっているから」と考えると、私はスッキリ納得できました。
③ new した時に自動で動く
自分で「今からコンストラクタを動かします!」と呼ぶ必要はありません。
new Curry() と書いた瞬間に、Javaが裏側で勝手にこの中身を実行してくれます。
補足:デフォルトコンストラクタ
実は、今までコンストラクタを書いていなかった時も、Javaが裏側で「中身が空っぽのコンストラクタ」を勝手に用意してくれていました。
これを 「デフォルトコンストラクタ」 と呼びます。
でも、今回のように「自分好みの設定」をしたい場合は、自分で明示的に書いてあげる必要があるんです。
引数付きコンストラクタの魔法
「引数」とは、メソッドやコンストラクタに渡す「材料」のことでしたね。
これを使うと、new と同時にデータを流し込めるようになります。
ここで一つ、大切なポイントがあります。
「使う時に1行で済ませるためには、設計図(クラス)側で事前の下準備が必要」ということです。
「最初に少しだけ頑張って設計図を書いておけば、あとは何度呼び出してもたった1行で済む」
これこそが、プロのエンジニアが大切にしている効率化の考え方なんです。
それでは、どれくらいコードがスッキリするのか比較してみましょう。
これまでの書き方(手動設定:計3行)
Curry mildCurry = new Curry();
mildCurry.name = "おこさまカレー";
mildCurry.spicy = 1;この書き方だと、毎回3行のコードを書かなければなりません。
設計図を作る人の作業(クラス側の準備)
まずは設計図側で、「名前と辛さをセットにするんだよ」というルール(コンストラクタ)を定義してあげます。
class Curry {
String name;
int spicy;
// ここで準備を頑張る!
Curry(String name, int spicy) {
this.name = name; //名前
this.spicy = spicy; //辛さ
}
}このクラスができてしまえば、あとは呼び出すだけで機能します。
引数付きコンストラクタの書き方(たった1行!)
準備ができたら、呼び出すコードは1行で大丈夫です!
// カッコの中に材料を入れるだけ!
Curry mildCurry = new Curry("おこさまカレー", 1);データの入れ忘れをブロック!
これ、ただ短くなるだけじゃないんです。
引数付きのコンストラクタを定義すると、「名前(String型)と辛さ(int型)を入れないと、そもそもnew(召喚)させてもらえない」という強力なルールをJavaに敷くことができます。
もし誰かが new Curry(); とだけ書いてデータを入れようとしなかったら、Javaが「材料が足りないよ!」とエラーを出して教えてくれます。
「あとで設定しようと思って忘れてた…」という、初心者(というか私)が一番やりがちなミスを未然に防いでくれる、とっても優しい仕組みなんです。
「this」という言葉の正体
コンストラクタを書くとき、よくこんなコードを見かけます。
class Curry {
String name; // ① クラスの変数(フィールド)
Curry(String name) { // ② 外から来た材料(引数)
this.name = name; // これは何?!
}
}「name = name; でいいじゃん!」と思いますよね。
でも、実はこれだとJavaが「どっちのnameのこと?」と迷ってしまうんです。
「this」は「この自分」を指す看板
Javaの世界では、同じ名前の変数があるとき、「より近くにある方(引数)」を優先して使ってしまうというルールがあります。
そこで、this. という看板の登場です。
this.name:「この自分(クラス)が持っているname箱」のこと。name:「外から(引数として)やってきたname材料」のこと。
名前を揃えられるメリット
「じゃあ、引数の名前を shiryoName とかに変えれば this はいらないんじゃ?」
確かにその通りです。でも、プロの世界では「名前を揃える」ことが推奨されます。
「名前」を入れる箱には、やっぱり「name」という名前の材料を入れるのが一番自然で分かりやすいからです。
this を使うことで、「外から来た『名前(name)』を、自分自身の『名前(name)』の箱にしっかり入れますよ!」と、迷いなく指示できる。
これが this の正体なんです。
まとめ:コンストラクタは「誕生の儀式」
今回は、オブジェクトが生まれる瞬間に魔法をかける「コンストラクタ」について学びました。
- コンストラクタは、
newした瞬間に自動で動く特別な処理。 - 名前は必ず 「クラス名と同じ」 にし、戻り値(voidなど)は書かないのがルール。
- 引数付きコンストラクタを使えば、1行でデータのセットが完了してコードがスッキリ!
thisは「自分自身」を指す看板。外から来たデータと自分の箱を見分けるために使う。
コンストラクタを使いこなせるようになると、「データの入れ忘れ」というケアレスミスをJavaに未然に防いでもらえるようになります。
プログラミングは、いかに楽をして、かつミスを減らす仕組みを作るかの積み重ねです。
コンストラクタはそのための第一歩。ぜひ、自分のコードでも「誕生の儀式」を書いてみてくださいね。
今回も最後まで読んでいただき、ありがとうございました。
一歩ずつ、着実にエンジニアの階段を登っていきましょう!
