私はこのプログラムをJavaで書きました
public class Why {
public static void test() {
System.out.println("Passed");
}
public static void main(String[] args) {
Why NULL = null;
NULL.test();
}
}
null
オブジェクトでメソッドを呼び出すとNullPointerException
が発生することを読みましたが、上記のプログラムでは発生しませんか?どうしてこれなの?私は何かを正しく理解していませんか?
test()
はstatic
メソッドです。 static
メンバーはタイプに属し、アクセスするためにインスタンスを必要としません。
static
メンバーは、型式を介して[〜#〜] only [〜#〜]にアクセスする必要があります。つまり、次のように書く必要があります。
Why.test(); // always invoke static method on the type it belongs to!
Javaでは、オブジェクト参照式を介してstatic
メンバーにアクセスできますが、これは[〜#〜] very [〜#〜]これは[〜#〜]ではない[〜#〜]static
メンバーアクセスの実際のセマンティクスであるため、誤解を招く可能性があります。
Why aNull = null;
aNull.test(); // DO NOT EVER DO THIS!
// invokes Why.test(), does NOT throw NullPointerException
オブジェクト参照式を介してstatic
メンバーにアクセスする場合、宣言されたタイプの参照のみが重要です。この意味は:
null
であるかどうかは関係ありません。null
でない場合、オブジェクトの実行時型が何であるかは関係ありません動的ディスパッチはありません! !!ご覧のとおり、インスタンスメンバーアクセスの両方のポイントで正反対のことが当てはまります。これが、static
メンバーが[〜#〜]決して[〜#〜]に「非static
"方法、それは実際に何をしているかについて非常に誤解を招くような外観を与えるからです。
this
を理解することが重要です!)IDEでさまざまな警告をオンにする必要があります。非静的な方法で静的メンバーにアクセスすることについての警告が表示される可能性があります。
(Why)(null).test()のようなことをすることができます、それはクラスを取得するために(Why)(null)だけを使用しています。
静的メソッドは、オブジェクトへの参照を必要としません。したがって、オブジェクトへの参照がnullであっても呼び出すことができます。これがmainメソッドの仕組みです。
オブジェクトから静的指定を削除して、nullポインタの例外を確認してください。
これは静的メソッドであり、インスタンスをインスタンス化せずにメソッドを呼び出すことができます。
静的変数とメソッドは、オブジェクトではなく、クラスに関連付けられています。クラスのすべてのインスタンスは、メモリ内の1つの固定された場所にあるクラス変数を共有します。
どのオブジェクトでもクラス変数の値を変更できますが、クラスのインスタンスを作成せずにクラス変数を操作することもでき、静的メソッドにも同じことが当てはまります。詳細については これを参照 。