반응형
Java에서 List
의 내용을 복사하는 방법은 여러 가지가 있습니다. List
를 복사할 때 중요한 것은 얕은 복사(Shallow Copy)와 깊은 복사(Deep Copy)의 차이를 이해하는 것입니다.
- 얕은 복사(Shallow Copy): 리스트의 원소들에 대한 참조만 복사합니다. 즉, 원본 리스트와 복사된 리스트는 동일한 객체를 참조합니다.
- 깊은 복사(Deep Copy): 리스트의 원소들까지 새롭게 복사하여 원본과 복사된 리스트가 독립적인 객체를 갖도록 합니다.
1. 얕은 복사(Shallow Copy)
얕은 복사를 수행하는 간단한 방법은 ArrayList
의 생성자나 Collections.copy
메서드를 사용하는 것입니다.
예시: ArrayList
생성자 사용
import java.util.ArrayList;
import java.util.List;
public class ShallowCopyExample {
public static void main(String[] args) {
List<String> originalList = new ArrayList<>();
originalList.add("Apple");
originalList.add("Banana");
originalList.add("Cherry");
// 얕은 복사
List<String> shallowCopy = new ArrayList<>(originalList);
System.out.println("Original List: " + originalList);
System.out.println("Shallow Copy: " + shallowCopy);
// 원본 리스트 변경
originalList.set(0, "Avocado");
System.out.println("Modified Original List: " + originalList);
System.out.println("Shallow Copy after modification: " + shallowCopy);
}
}
예시: Collections.copy
사용
Collections.copy
는 미리 크기가 설정된 리스트에 복사할 수 있습니다.
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
public class ShallowCopyExample {
public static void main(String[] args) {
List<String> originalList = new ArrayList<>();
originalList.add("Apple");
originalList.add("Banana");
originalList.add("Cherry");
// 크기가 동일한 빈 리스트 생성
List<String> shallowCopy = new ArrayList<>(originalList.size());
Collections.addAll(shallowCopy, new String[originalList.size()]);
// 얕은 복사
Collections.copy(shallowCopy, originalList);
System.out.println("Original List: " + originalList);
System.out.println("Shallow Copy: " + shallowCopy);
// 원본 리스트 변경
originalList.set(0, "Avocado");
System.out.println("Modified Original List: " + originalList);
System.out.println("Shallow Copy after modification: " + shallowCopy);
}
}
2. 깊은 복사(Deep Copy)
깊은 복사를 수행하려면 리스트의 각 원소를 개별적으로 복사해야 합니다. 이 작업은 복제할 객체가 Cloneable
인터페이스를 구현했거나, 각 객체의 복제 생성자를 호출하는 방법으로 수행할 수 있습니다.
예시: Cloneable
인터페이스 사용
Cloneable
인터페이스를 구현하는 객체를 복사하는 예시입니다.
import java.util.ArrayList;
import java.util.List;
class Fruit implements Cloneable {
String name;
public Fruit(String name) {
this.name = name;
}
@Override
protected Object clone() throws CloneNotSupportedException {
return super.clone();
}
@Override
public String toString() {
return name;
}
}
public class DeepCopyExample {
public static void main(String[] args) {
List<Fruit> originalList = new ArrayList<>();
originalList.add(new Fruit("Apple"));
originalList.add(new Fruit("Banana"));
originalList.add(new Fruit("Cherry"));
// 깊은 복사
List<Fruit> deepCopy = new ArrayList<>();
for (Fruit fruit : originalList) {
try {
deepCopy.add((Fruit) fruit.clone());
} catch (CloneNotSupportedException e) {
e.printStackTrace();
}
}
System.out.println("Original List: " + originalList);
System.out.println("Deep Copy: " + deepCopy);
// 원본 리스트의 객체 수정
originalList.get(0).name = "Avocado";
System.out.println("Modified Original List: " + originalList);
System.out.println("Deep Copy after modification: " + deepCopy);
}
}
예시: 복제 생성자 사용
각 객체가 자체적으로 복제 생성자를 제공하는 경우
import java.util.ArrayList;
import java.util.List;
class Fruit {
String name;
public Fruit(String name) {
this.name = name;
}
// 복제 생성자
public Fruit(Fruit another) {
this.name = another.name;
}
@Override
public String toString() {
return name;
}
}
public class DeepCopyExample {
public static void main(String[] args) {
List<Fruit> originalList = new ArrayList<>();
originalList.add(new Fruit("Apple"));
originalList.add(new Fruit("Banana"));
originalList.add(new Fruit("Cherry"));
// 깊은 복사
List<Fruit> deepCopy = new ArrayList<>();
for (Fruit fruit : originalList) {
deepCopy.add(new Fruit(fruit));
}
System.out.println("Original List: " + originalList);
System.out.println("Deep Copy: " + deepCopy);
// 원본 리스트의 객체 수정
originalList.get(0).name = "Avocado";
System.out.println("Modified Original List: " + originalList);
System.out.println("Deep Copy after modification: " + deepCopy);
}
}
요약
- 얕은 복사: 리스트 객체 자체만 복사하고 내부 객체는 동일한 참조를 유지합니다.
- 깊은 복사: 리스트 내부의 객체도 모두 새롭게 복사하여 원본과 독립적인 객체를 생성합니다.
복사 방식은 리스트에 포함된 객체의 특성에 따라 결정해야 하며, 각각의 경우에 대해 신중하게 고려해야 합니다.
반응형
'언어 > Java' 카테고리의 다른 글
[ Java ] 조건문 if (1) | 2024.06.17 |
---|---|
[ Java ] ClassPath 설정하기 (0) | 2024.06.15 |
[ Java ] List 사용하기 (1) | 2024.06.13 |
[ Java ] 자바 대입연산자 사용하기 (1) | 2024.06.09 |
[ Java ] 삼항 연산자 사용해보기 (0) | 2024.06.09 |