Link

소유권(ownership)이란?

소유권은 러스트의 핵심 기능이다. 모든 프로그램은 실행 중인 동안에는 어떤 방법으로든 컴퓨터의 메모리를 관리해야 한다. 어떤 언어는 가비지 콜렉터를 이용해 더 이상 사용되지 않는 메모리를 지속적으로 찾아 자동으로 해제한다. 반면, 또 다른 언어는 프로그래머가 명시적으로 메모리를 할당하고 해제해 주어야 한다. 러스트는 제3의 방법을 사용한다. 즉, 메모리는 컴파일러가 컴파일 시점에 검사하는 다양한 규칙으로 이루어진 소유권 시스템에 의해 관리된다. 그래서 소유권과 관련된 기능은 프로그램의 실행 성능에 아무런 영향을 미치지 않는다.

스택(Stack)과 힙(Heap)

대부분 프로그래밍 언어 환경에서는 스택 메모리와 힙 메모리를 자주 신경 쓸 필요가 없다. 하지만 러스트 같은 시스템 프로그래밍 언어 환경에서는 값이 스택 메모리에 저장되었는지 힙 메모리에 저장되었는지에 따라 언어의 동작이나 의사결정에 큰 영향을 미친다.

스택에 저장하는 모든 데이터는 고정된 크기를 가져야 한다. 컴파일 시점에 크기를 알 수 없는 데이터나 런타임에 동적으로 크기가 변하는 데이터는 힙 메모리에 저장한다. 힙에 데이터를 넣는 동작은 메모리의 일정 공간을 할애할 것을 (운영체제에) 요청하는 것이다. 따라서 운영체제는 힙 메모리에서 일정한 공간을 찾아 사용 중인 메모리로 표시한 후, 해당 메모리의 주솟값인 포인터를 넘겨준다. 이 과정을 ‘힙 메모리 할당(allocating on the heap)’ 또는 단순히 ‘할당(allocating)’이라고 한다. 스택에 값을 푸시하는 동작에는 할당이 발생하지 않는다. 포인터는 이미 크기가 고정된 값이므로 포인터는 스택에 저장할 수 있지만, 실제 포인터가 가리키는 데이터가 필요할 때는 포인터가 가리키는 메모리를 따라가야 한다.

스택에 데이터를 푸시하는 것이 힙에 할당하는 것보다 빠른 이유는 운영체제가 새 데이터를 저장할 공간을 찾을 필요가 없기 때문이다. 새 데이터는 항상 스택의 가장 위(top)에 추가된다. 힙에 공간을 할당하는 것은 상대적으로 더 많은 작업이 필요하다. 운영체제가 먼저 데이터를 저장할 충분히 큰 공간을 찾은 후 다음 할당 작업을 위한 예약 작업을 수행해야 하는 이유다.

힙 메모리에 저장된 데이터에 대한 접근은 스택에 저장된 데이터에 접근하는 것보다 느리다. 그 이유는 포인터를 따라가야 하기 때문이다. 현대의 프로세서들은 메모리 사이를 왔다 갔다 하는 일이 더 적을수록 더 빠르게 동작한다.

코드의 어느 부분이 힙 메모리에 저장된 데이터를 사용하는지 추적하고 힙에 저장되는 데이터의 중복을 최소화해 사용하지 않는 데이터를 힙 메모리에서 제거하면 메모리 부족 문제를 해결할 수 있다. 러스트의 소유권 기능은 바로 이 문제를 해결하려는 방법이다. 일단 소유권을 이해하려면 스택과 힙에 대해 더 이상 고민할 필요는 없지만, 소유권이 힙 데이터를 관리하려고 존재한다는 사실을 이해한다면 소유권이 어떻게 동작하는지 설명하는 데 도움이 된다.

소유권 규칙

  • 러스트가 다루는 각각의 값은 소유자(owner)라고 부르는 변수를 가지고 있다.
  • 특정 시점에 값의 소유자는 단 하나뿐이다.
  • 소유자가 범위를 벗어나면 그 값은 제거된다.

변수의 범위(scope)

String 타입

메모리와 할당

(1) 변수와 데이터가 상호작용하는 방식: 이동(move)

(2) 변수와 데이터가 상호작용하는 방식: 복제(clone)

(3) 스택 전용 데이터: 복사(copy)

소유권과 함수

반환값과 범위