[C언어/C++] memcpy 메모리 복사 함수 사용법과 예제 (주의사항 포함)
안녕하세요. BlockDMask 입니다.
오늘은 C언어, C++에서 메모리를 복사하는 함수 memcpy()에 대해서 알아보겠습니다.
본격적으로 memcpy 함수 시작해보겠습니다.
목차
✅ 1. memcpy 함수란?
memcpy는 memory + copy의 합성어로, 메모리 상의 데이터를 복사하는 함수입니다. 다른 말로 하면, 원본 메모리 블록의 데이터를 새로운 메모리 블록으로 바이트 단위로 복사하는 역할을 합니다.
헤더파일:
C언어 <string.h>, C++ <cstring>
함수 원형:
void* memcpy(void* dest, const void* source, size_t num)
매개변수 설명:
dest: 복사 받을 메모리를 가리키는 포인터source: 복사할 원본 메모리를 가리키는 포인터num: 복사할 바이트 크기
다시 말해 memcpy(dest, source, num) 는 source 메모리에 있는 데이터를 num 바이트만큼 dest로 복사합니다.
주의사항 ①:
문자열을 복사할 때 C언어 스타일 문자열은 끝을 알리는 \0 (NULL 문자)가 자동으로 복사되지 않습니다.
따라서 문자열 전체를 복사할 땐 문자열 길이 + 1 만큼 복사해야 합니다.
주의사항 ②:
복사 구간이 서로 겹치는 메모리 영역에서는 memcpy는 권장되지 않습니다. 이 경우 memmove()를 사용하는 것이 안전합니다.
(최신 시스템에서는 memcpy도 어느정도 안전하지만, 원칙적으로 이렇게 구분합니다)
✅ 2. int 배열 복사 예제
정수형 배열을 복사하는 간단한 예제입니다.
#include <string.h>
#include <stdio.h>
int main(void)
{
int src[] = { 1, 2, 3 };
int dest[3];
// 메모리 복사
memcpy(dest, src, sizeof(int) * 3);
// 원본 출력
printf("src : ");
for (int i = 0; i < 3; ++i)
printf("%d ", src[i]);
printf("\n");
// 복사본 출력
printf("dest: ");
for (int i = 0; i < 3; ++i)
printf("%d ", dest[i]);
return 0;
}
실행 결과:
src : 1 2 3
dest: 1 2 3
이렇게 memcpy를 통해 메모리 블록 단위로 잘 복사된 것을 확인할 수 있습니다.
전체를 복사할 때는 sizeof(int) * 배열크기 또는 sizeof(src) 로 계산 가능합니다.
✅ 3. char 문자열 일부 복사 예제
이번에는 문자열 일부만 복사해 보겠습니다.
#include <string.h>
#include <stdio.h>
int main(void)
{
const char* src = "BlockDMask";
char dest[] = "abcdefghijklmnop";
// 6글자만 복사
memcpy(dest, src, sizeof(char) * 6);
printf("src : %s\n", src);
printf("dest : %s\n", dest);
return 0;
}
실행 결과:
src : BlockDMask
dest : BlockDklmnop
원본 src 문자열에서 앞의 6글자 BlockD만 복사되었습니다.
이후 dest의 나머지 부분은 기존 값이 남아있으므로 klmnop가 이어진 것을 확인할 수 있습니다.
✅ 4. char 문자열 전체 복사 예제 (주의사항)
이번에는 문자열 전체를 복사할 때 발생할 수 있는 실수를 확인해봅니다.
#include <string.h>
#include <stdio.h>
int main(void)
{
char src[] = "BlockDMask";
char dest1[] = "abcdefghijklmnop";
char dest2[] = "abcdefghijklmnop";
// \0 없이 복사 (문자열 끝을 포함하지 않음)
memcpy(dest1, src, sizeof(char) * 10);
// \0 포함 복사 (문자열 끝까지 복사)
memcpy(dest2, src, sizeof(char) * 10 + 1);
printf("src : %s\n", src);
printf("dest1 : %s\n", dest1);
printf("dest2 : %s\n", dest2);
return 0;
}
실행 결과:
src : BlockDMask
dest1 : BlockDMaskklmnop
dest2 : BlockDMask
여기서 핵심은 \0 (문자열 끝 표시 문자)의 복사 여부입니다.
dest1에서는 문자열 끝\0이 복사되지 않아 기존 dest1 배열의 나머지 데이터가 남아 이어져 출력됩니다.dest2에서는\0까지 복사되어 정상적으로 문자열 끝에서 출력이 멈춥니다.
즉, 문자열 복사 시 전체를 안전하게 복사하려면 반드시 문자열 길이 + 1 만큼 복사해줘야 합니다.
이는 C언어 문자열이 항상 \0으로 끝난다는 규칙 때문입니다.
참고로 메모리 안에는 이렇게 저장됩니다:
- dest1:
BlockDMaskklmnop\0 - dest2:
BlockDMask\0klmnop\0
프로그래머가 일부러 \0 없이 복사하고 싶다면 길이만큼 복사하고,
문자열로 사용할 땐 \0까지 포함해서 복사해야 함을 꼭 기억하세요.
이상으로 C/C++에서 메모리 복사 함수 memcpy()의 원리와 사용법을 예제와 함께 알아보았습니다.
오늘도 읽어주셔서 감사합니다.
댓글
댓글 쓰기