[TIL] C++ - 메모리 레이아웃

MINO·2024년 11월 2일
0

2024-11-02


Visual Studio 를 통해, 알고리즘 문제를 풀다가 다음과 같은 기능을 발견하였다.
구조체 타입에 마우스 커서를 올려두니
크기, 맞춤 에 대한 정보와 메모리 레이아웃 에 대해 알 수 있었다.


크기, 맞춤메모리 레이아웃

크기(Size)와 맞춤(Allignment)

구조체나 클래스의 크기와 맞춤 은 데이터가 메모리에 배치될 때 중요한 요소이다.

컴파일러와 시스템 아키텍처에 따라 다를 수도 있다.


크기

특정 데이터 타입이나 객체가 메모리에서 차지하는 총 바이트 수를 의미


맞춤

데이터가 메모리에 어떻게 정렬되는지에 대한 기준을 의미

  • 맞춤을 통해 CPU가 데이터를 효율적으로 읽고 쓸 수 있도록 구조체의 멤버를 배치한다.
  • CPU 아키텍처와 데이터 타입에 따라 결정된다.
  • 구조체에서 메모리가 특정 바이트의 배수 주소에서 시작해야한다.

장점

  • CPU는 맞춤된 데이터에 대해 더 빠르게 접근할 수 있다.
    • 맞춤이 맞지 않으면, CPU 가 데이터를 여러 번 읽거나 추가적인 조작을 해야해서
      성능 저하가 발생할 수 있다.
  • 패딩을 통해 구조체의 멤버가 올바른 위치에 정렬되도록 한다.

예시

pair<int,int>

int 2개를 멤버로 가지는 구조.

각 int가 4bytes 이므로, pair<int,int> 의 크기는 4+4 = 8bytes 이다.
두 int 가 모두 4bytes 맞춤에 따라 정렬되므로, 추가적으로 패딩이 필요하지 않고 4bytes 로 맞춰진다.


pair<double,int>

double 과 int 를 멤버로 가지는 구조.

메모리 접근 효율성을 위해,
구조체의 전체 맞춤은 가장 큰 멤버의 맞춤인 double 의 크기인 8 bytes 에 맞춰진다.

따라서, int 는 8bytes 맞춤 규칙에 따라 4bytes 의 패딩이 추가되어
pair<double,int> 의 크기는 8 + 4 + 4 = 16 bytes 가 된다.


vector<int>

int 를 멤버로 가지는 자동으로 메모리가 할당되는 배열.

vector 의 기본 멤버인
1. 데이터 포인터 : 벡터가 저장하는 실제 요소(int) 를 가리키는 포인터, 8bytes
2. 크기 변수 : 현재 저장된 요소의 개수를 나타내는 변수, 8bytes
3. 용량 변수 : 벡터에 할당된 총 메모리 용량을 나타내는 변수, 8bytes
로 인해 기본적으로 8 + 8 + 8 = 24bytes 를 차지하고, 맞춤은 8bytes 가 되겠다.

내 PC 의 경우, 컴파일러의 최적화 및 메모리 정렬 규칙이 적용되어
추가적인 패딩이 이루어져 크기가 24 + 8 = 32bytes 이다.


vector<pair<int,int>>

pair<int,int> 를 멤버로 가지는 자동으로 메모리가 할당되는 배열.

vector 내부적으로 데이터 포인터, 크기, 용량을 저장하는 필드의 크기인 24bytes.
pair<int,int> 는 각각 4bytes 맞춤을 가지지만, vector 자체의 맞춤 규칙을 따라 8bytes 가 된다.

따라서, 크기는 24 + 8 = 32bytes, 맞춤은 8bytes 이다.



메모리 레이아웃

데이터 구조가 메모리에 어떻게 배치되는지를 의미한다.

  • 메모리에 데이터 구조를 저장할 때, 컴파일러가 특정 규칙에 따라 구성 요소를 배치한다.
  • 각 멤버가 몇 bytes 씩 차지하고 시작 주소가 어떻게 되는지를 도식화하여 보여준다.

필요성

  • 성능 최적화 : 캐시 최적화와 메모리 접근 효율성을 개선하기 위해 정렬(패딩)을 조정한다.
  • 메모리 사용량 예측 : 구조체가 차지하는 정확한 크기를 예측하여, 메모리 낭비를 줄일 수 있다.
  • 저수준 디버깅 : 특정 멤버의 메모리 주소나 오프셋을 정확히 알아야 하는 경우에 유용하다.

예시

pair<int,int>


pair<double,int>

0x0008번지부터 시작하는 int형은 4~7bytes 까지는 패딩된다.

vector<int>



TIL 마무리

대학교 2학년 때부터 쭉 써왔던 Visual Studio 였지만,
이런 기능을 제공하는지 몰랐었다.

메모리 관리와 성능 최적화에 있어서
자료형의 크기를 이해하고, 되도록 불필요한 패딩을 피하게끔 코드를 작성하여
메모리 공간을 절약해야겠다는 생각이 들었다.

profile
안녕하세요 게임 개발하는 MINO 입니다.

0개의 댓글