Java

【クラスの中で定義するクラス】インナークラス

インナークラスとは???

Javaでは、クラス宣言ブロックの中にさらにクラス宣言を書くことがゆるされています。内側に宣言されたクラスのことをインナークラスと言います。インナークラスと言ってもその宣言場所によって3つに分類されます。メンバ(フィールドとメソッド)と同じように、private,protected, publicなどのアクセスレベル修飾子をつけることができます。さらに、インナークラスは、インナークラスが属しているクラスのフィールドやメソッドを参照することができます。つまり、あるクラス内のメンバにアクセスするクラスを宣言する場合にインナークラスを宣言します。そして内部クラスを持つクラスのことをアウタークラスとも言います。

  • メンバクラス

・クラスブロックの中

  • ローカルクラス

・メソッドブロックの中

  • 匿名クラス

・文の中(式の一部)
(親クラス名を指定)

メンバクラス

今までは、、メンバはフィールドとメソッドでしたが、、、、
これからは、そこにメンバクラスも仲間入りです。

staticではない(インスタンス化しないと使用できない)

staticで宣言されていないインナークラス単体でnew(インスタンス化)すると、完全に別なクラスとして扱われるために、エラーになります。しかし、staticで宣言されたインナークラスは、実体がそのインナークラスが属するアウタークラスにあるため、インナーククラスをインスタンス化してもエラーにはなりません。ただ、staticで宣言されていないインナークラスでも、アウタークラスのインスタンスがあればnew(インスタンス化)は可能になり、アウタークラスのインスタンスと必ずつながっているため非staticのメンバにもアクセスできるようになります。

staticである(インスタンス化しなくても使える)

staticで宣言されたインナークラスは、staticで宣言されたアウタークラスのメンバーにのみアクセスできます。

staticで宣言されたインナークラスは、実体はアウタークラスにあるので、、アウタークラスをインスタンス化した場合、そのアウタークラスのインスタンスとは、繋がっていないので、非staticのメンバにはアクセスできません。staticで宣言されたアウタークラスのメンバの実体は、アウタークラスにあるためアクセスできます。

ローカルクラス

メソッドブロック内で宣言されるクラス定義で、その宣言されたメソッド内でのみ利用可能になります。

ローカルクラスの特徴

・finalとabstract以外の修飾は行えない(必要がない)
・外部クラスのメンバにアクセス可能
・自身を取り囲むメソッド内のローカル変数についてはfinalがついたものにのみアクセス可能(java8以降では、再代入が行われていないなら暗黙的にfinalとみなされエラーにならない)

匿名クラス

普通のクラスやメンバクラスは、classキーワードでまず宣言してからその後newでインスタンス化してから利用しますが匿名クラスは、宣言と利用を同時に行います。つまり、宣言すると同時にインスタンス化もやっちゃいます。

上の例のnew Object(){匿名クラスの内容}にある、Objectと言うのは匿名クラスが継承している親クラスを指定している。

一般化すると

new 匿名クラスの親クラス指定(){
匿名クラスのメンバ定義
}

参考サイト

Qiita-インナークラス・メンバークラス

HatenaBlog-匿名クラスとかローカルクラスとか

<>TECHACADEMYmagazine-匿名クラスの使い方