クラスの定義とオブジェクトの使用の要点
内容の確認日: 2026-10-03
この分野では、クラスを定義してオブジェクトを作り、使うまでの基本が問われます。範囲が広く、出題項目は「クラスの定義とオブジェクトの生成、使用」「メソッドのオーバーロード」「コンストラクタの定義」「アクセス修飾子 (public, private) の適用とカプセル化」「static 変数および static メソッド」の 5 つです。
「参照型の変数には何が入っているか」と「static とインスタンスの違い」の 2 つを理解すると、この分野の問題の多くが解けるようになります。
オブジェクトの生成とフィールドの既定値
クラスは設計図で、new で作った実体がオブジェクト (インスタンス) です。フィールドは、初期値を書かなくても型ごとの既定値で初期化されます。数値型は 0、boolean は false、String などの参照型は null です。null を文字列と連結すると "null" という文字列になります。
class Book { String title; int pages; boolean read;}public class Main { public static void main(String[] args) { Book b = new Book(); System.out.println(b.title + " " + b.pages + " " + b.read); }}java Main null 0 false
null が入った参照型の変数でメソッドを呼んだりフィールドを読んだりすると、実行時に NullPointerException が発生します。
参照のコピーと引数の渡され方
参照型の変数に入っているのは、オブジェクトそのものではなく、オブジェクトの場所を指す参照です。b = a と代入すると参照がコピーされ、a と b は同じオブジェクトを指します。その後 b に別のオブジェクトを代入しても、a には影響しません。
class Counter { int value;}public class Main { public static void main(String[] args) { Counter a = new Counter(); Counter b = a; b.value = 5; System.out.println(a.value); b = new Counter(); b.value = 9; System.out.println(a.value); }}java Main 5 5
メソッドの引数も同じで、Java では常に値のコピーが渡されます。int などのプリミティブ型は値そのものがコピーされるので、メソッドの中で変えても呼び出し元は変わりません。配列やオブジェクトは参照がコピーされるので、メソッドの中で要素やフィールドを変えると、呼び出し元から見ても変わっています。
public class Main { static void change(int n, int[] arr) { n = 100; arr[0] = 100; } public static void main(String[] args) { int x = 1; int[] nums = {1}; change(x, nums); System.out.println(x + " " + nums[0]); }}java Main 1 100
メソッドのオーバーロード
同じクラスに、名前が同じで引数の数・型・並び順が違うメソッドを複数定義することをオーバーロードと呼びます。どれが呼ばれるかは、渡した引数の型で決まります。ぴったり一致するものがなければ、char → int のように型を広げて一致するものが選ばれます。
public class Main { static void show(int n) { System.out.println("int: " + n); } static void show(double d) { System.out.println("double: " + d); } static void show(String s) { System.out.println("String: " + s); } public static void main(String[] args) { show(10); show(10.0); show("10"); show('A'); }}java Main int: 10 double: 10.0 String: 10 int: 65
引数が同じで戻り値の型だけが違うメソッドは、オーバーロードになりません。呼び出し側からどちらを呼ぶか区別できないため、コンパイルエラーです。引数の名前だけが違う場合も同様です。
public class Main { static int calc(int a) { return a; } static double calc(int a) { return a; } public static void main(String[] args) { System.out.println(calc(1)); }}javac Main.java
コンパイルエラー (3 行目): calc(int) がすでに定義されている (戻り値の型だけの違いではオーバーロードにならない)
コンストラクタ
コンストラクタは、new でオブジェクトを作るときに実行される特別なメソッドで、フィールドの初期化に使います。名前はクラス名と同じにし、戻り値の型を書きません。void Book() のように戻り値の型を書くと、コンストラクタではなく「クラスと同じ名前の普通のメソッド」になってしまいます。
コンストラクタを 1 つも書かないクラスには、引数なしのデフォルトコンストラクタが自動で追加されます。しかし、コンストラクタを 1 つでも書くと、デフォルトコンストラクタは追加されません。そのため、引数ありのコンストラクタだけを定義したクラスを new Book() で作ろうとするとコンパイルエラーです。
class Book { String title; Book(String title) { this.title = title; }}public class Main { public static void main(String[] args) { Book b = new Book(); }}javac Main.java
コンパイルエラー (10 行目): Book には引数なしのコンストラクタがない
this.title = title; の this は、そのオブジェクト自身を表します。引数とフィールドの名前が同じときに、フィールドの方を指すために使います。また、コンストラクタの中で this(...) と書くと、同じクラスの別のコンストラクタを呼び出せます。this(...) はコンストラクタの最初の文に書かなければなりません。
class Item { String name; int price; Item() { this("未設定", 0); System.out.println("引数なし"); } Item(String name, int price) { this.name = name; this.price = price; System.out.println("引数あり"); }}public class Main { public static void main(String[] args) { Item item = new Item(); System.out.println(item.name + " " + item.price); }}java Main 引数あり 引数なし 未設定 0
アクセス修飾子 public と private
public を付けたメンバ (フィールド・メソッド・コンストラクタ) は、どのクラスからでも使えます。private を付けたメンバは、そのクラスの中からだけ使えます。同じパッケージ・同じファイルの別のクラスからでも使えません。
private の制限は「クラス単位」です。同じクラスの中のコードであれば、別のインスタンスの private フィールド (例えば、引数で受け取った同じクラスのオブジェクトの other.x) にもアクセスできます。
フィールドを private にして、public なメソッドを通して操作させるのがカプセル化の基本です。なお、トップレベルのクラス (ファイルの一番外側のクラス) には private は付けられません。
static 変数と static メソッド
static を付けたフィールド (static 変数) は、オブジェクトごとではなくクラスに 1 つだけ存在し、すべてのインスタンスで共有されます。static を付けないフィールド (インスタンス変数) は、オブジェクトごとに別々です。
class Member { static int count = 0; int id; Member() { count++; id = count; }}public class Main { public static void main(String[] args) { Member m1 = new Member(); Member m2 = new Member(); System.out.println(m1.id + " " + m2.id + " " + Member.count); }}java Main 1 2 2
static 変数や static メソッドは、クラス名.名前 で使います。インスタンスがなくても使えます。m1.count のように変数を通して書くこともできますが、指しているのはクラスに 1 つの同じ変数です。
static メソッドの中からは、インスタンス変数やインスタンスメソッドを直接使えません。static メソッドは特定のオブジェクトに属さないので、「どのオブジェクトの値か」が決まらないためです。main メソッドも static なので、同じクラスのインスタンス変数を直接読むとコンパイルエラーになります。
public class Main { int value = 10; public static void main(String[] args) { System.out.println(value); }}javac Main.java
コンパイルエラー (5 行目): static メソッドの main から、インスタンス変数 value を直接参照できない
逆に、インスタンスメソッドからは static 変数や static メソッドを自由に使えます。
試験でよくある引っかけ
コンストラクタに戻り値の型を書く
void Book() { }はコンストラクタではなく普通のメソッドです。new Book()では呼ばれません。デフォルトコンストラクタが消える
引数ありのコンストラクタだけを定義すると、引数なしの
new Book()はコンパイルエラーです。this(...)の位置this(...)はコンストラクタの最初の文でなければなりません。前に別の文があるとコンパイルエラーです。戻り値の型だけが違うメソッド
引数が同じで戻り値の型だけが違うメソッドは、オーバーロードではなく重複した定義としてコンパイルエラーです。
参照のコピー
b = aの後にb.valueを変えると、a.valueも変わります (同じオブジェクトを指しているため)。staticメソッドからインスタンス変数mainなどのstaticメソッドから、インスタンス変数を直接使うとコンパイルエラーです。
問題で確認する
この分野の問題を、解説つきで読めます (登録不要)。
出典・参考
- Oracle University 日本「1Z0-818-JPN (Java SE Bronze) 試験」
- Java 言語仕様 (Java SE 11) 8.8「Constructor Declarations」
- Java 言語仕様 (Java SE 11) 8.4.9「Overloading」
- The Java Tutorials「Understanding Class Members」
コード例は、試験の対象バージョンで実際にコンパイル・実行して結果を確認しています。