Program/C#

C# 얕은복사, 깊은복사

사막여유 2024. 11. 14. 22:02
728x90

복사에는 얕은복사와 깊은복사 이렇게 2가지의 방법이 있습니다.

간단하게 정리하면
얕은복사 ( Shallow Copy )는 참조를 복사하는 것이고
깊은복사 ( Deep Copy )는 데이터의 값을 복사하는 것 입니다.

 

깊은복사

깊은복사는 위에서 설명한대로
A라는 변수에 1,2,3 이라는 데이터가 있었을 때
변수에 담겨있는 1,2,3이라는 데이터만 가져와서 
새로운 변수로 복사하는 것을 의미합니다.

 

얕은복사

얕은복사 또한 위에서 설명한대로
A라는 변수에 1,2,3 이라는 데이터가 있었을 때
변수에 담겨있는 1,2,3이라는 데이터를 가져오는게 아니고
A라는 변수가 사용하고 있는 메모리의 참조값을 가져오는 것을 의미합니다.

좀 더 딥하게 컴퓨터 사이언스 측면에서 보게되면 
프로그램으로 어떤 변수를 만들고 그 변수에 데이터를 저장하게 되면
컴퓨터에 있는 RAM이라는 메모리에 저장이 되게 됩니다.

메모리는 비어있는 거대한 아파트라고 볼 수 있는데 값을 저장하게 되면
비워져있는 아파트 호실부터 차례대로 데이터에 해당하는 값들이 들어가게 되는거죠.

 

그러면 얕은 복사에서는 해당 아파트의 몇호실부터 몇호실까지 그 데이터가 들어가있는지를 
확인해서 가져가는 것을 뜻합니다.
그에 반해서 깊은 복사는 해당 아파트의 호실에 들어가있는 데이터 자체를 그대로 복사해서
다른 호실로 옮겨가는 것을 뜻하는 것이구요. 

 

C#에서의 코드를 보겠습니다.

 

using System;

class Person
{
    public string Name { get; set; }
    public Address Address { get; set; }

    public Person() { }

    public Person(string name, Address address)
    {
        Name = name;
        Address = address;
    }

    // 얕은 복사
    public Person ShallowCopy()
    {
        return (Person)this.MemberwiseClone();
    }

    // 깊은 복사
    public Person DeepCopy()
    {
        return new Person(
            this.Name,
            new Address(
                this.Address.Street,
                this.Address.City
            )
        );
    }
}

class Address
{
    public string Street { get; set; }
    public string City { get; set; }

    public Address() { }

    public Address(string street, string city)
    {
        Street = street;
        City = city;
    }
}

class Program
{
    static void Main()
    {
        // 원본 객체 생성
        var original = new Person("홍길동", 
            new Address("강남대로", "서울"));

        // 얕은 복사
        var shallowCopy = original.ShallowCopy();
        
        // 깊은 복사
        var deepCopy = original.DeepCopy();

        // 원본 객체의 Address 수정
        original.Address.City = "부산";

        // 결과 출력
        Console.WriteLine($"Original City: {original.Address.City}");       // 부산
        Console.WriteLine($"Shallow Copy City: {shallowCopy.Address.City}");// 부산 (원본 변경이 영향)
        Console.WriteLine($"Deep Copy City: {deepCopy.Address.City}");      // 서울 (원본 변경이 영향없음)
    }
}

 

위 예시와 같이 깊은복사는 새로운 클래스를 생성한 뒤 해당 새로운 클래스를 return하기 때문에
기존에 있는 클래스의 데이터에는 영향을 주지 않지만

얕은 복사는 MemberwiseClone이라는 메서드를 사용하였고,
origin.Address.City의 내용을 변경하였을 때 위 아파트의 그림처럼 각 호실 내부에 있던 데이터 자체가 
변했기 때문에 변경된 내용으로 바뀌어 출력되는 것을 볼 수 있습니다.

 

이처럼 얕은 복사와 깊은 복사는 데이터를 다루는 방식에 큰 차이가 있습니다.

얕은 복사는 메모리 주소만을 참조하여 효율적이지만 원본 데이터 변경 시 영향을 받을 수 있고,
깊은 복사는 완전히 독립된 새로운 데이터를 생성하여 안전하지만 상대적으로 더 많은 리소스를 사용합니다.

따라서 상황에 따라 적절한 복사 방식을 선택하는 것이 중요하다고 할 수 있습니다.

728x90

'Program > C#' 카테고리의 다른 글

C# 병렬처리3 _ Mutex  (0) 2024.11.23
C# 병렬처리2 _ Monitor  (0) 2024.11.22
C# 병렬처리1 _ lock  (0) 2024.11.20
C# Bitmap  (1) 2024.11.18
C# 병렬처리1 _ Parallel  (0) 2024.11.11