객체의 참조만 복사하는 방식. 새로운 객체를 생성하지만 객체 내에 포함된 필드의 주소값만 복사하기 때문에 원본 객체와 복사된 객체가 같은 참조를 가리키게 된다.
기본형 필드는 값을 그대로 복사한다.
참조형 필드는 참조하는 객체의 주소값만 복사한다. 즉 복사된 객체와 원본 객체는 같은 객체를 가리킨다.
메모리 효율적이지만, 원본 객체나 복사된 객체 중 하나에서 참조하고 있는 객체를 변경하면 다른 객체에도 영향을 미친다.
class Person {
String name;
int age;
Person(String name, int age) {
this.name = name;
this.age = age;
}
}
class Main {
public static void main(String[] args) {
Person person1 = new Person("John", 25);
Person person2 = person1; // 얕은 복사
person2.name = "Alice"; // person2의 이름을 변경
System.out.println(person1.name); // 결과: "Alice" (person1도 영향을 받음)
}
}
깊은 복사는 객체의 모든 필드를 새롭게 복사하는 방식. 기본형 필드뿐만 아니라 참조형 필드까지도 새로운 객체로 복사하여, 원본 객체와 복사된 객체가 독립적인 객체가 된다.
class Person implements Cloneable {
String name;
int age;
Person(String name, int age) {
this.name = name;
this.age = age;
}
// 깊은 복사를 위한 메서드
@Override
protected Object clone() throws CloneNotSupportedException {
return new Person(this.name, this.age); // 새로운 객체 생성
}
}
class Main {
public static void main(String[] args) throws CloneNotSupportedException {
Person person1 = new Person("John", 25);
Person person2 = (Person) person1.clone(); // 깊은 복사
person2.name = "Alice"; // person2의 이름을 변경
System.out.println(person1.name); // 결과: "John" (person1은 영향 없음)
}
}
얕은 복사는 성능 면에서 유리할 순 있지만 참조형 객체에 대해 의도하지 않은 변경이 일어날 수 있어 주의해야 한다. 깊은 복사는 안전하지만 더 많은 메모리를 사용하고 복사 과정이 복잡할 수 있다.
제어자는 클래스, 변수, 메서드의 선언부에 사용되어 멤버 또는 클래스에 사용, 외부에서 접근하지 못하도록 제한한다.
public class 자식클래스 extends 부모클래스 {
}
extends키워드를 사용하여 정의할 수 있다