Notice
Recent Posts
Recent Comments
Link
«   2024/07   »
1 2 3 4 5 6
7 8 9 10 11 12 13
14 15 16 17 18 19 20
21 22 23 24 25 26 27
28 29 30 31
Tags
more
Archives
Today
Total
관리 메뉴

Visual Studio

memset의 함정 (은근 착각하기 쉬움) 본문

Programming Language

memset의 함정 (은근 착각하기 쉬움)

emacser 2022. 6. 19. 18:56
void *memset(void *dest, int c, size_t count);

memset은 dest 포인터에서 count 만큼의 바이트를 c 값으로 초기화하는,

c에서 유용하고 또 상당히 많이 사용하는 함수이다.

그런데 memset에는 c에 미숙한 사람이 헷갈리기 쉬운 두가지 함정이 있다.

1. memset의 두번째 파라미터는 int 타입으로 받지만 unsigned char로 형변환되어 사용된다.

초기화에 사용되는 값인 c는 int 타입으로 받는데,

이 값은 사실 unsigned char로 형변환되어 사용된다.

 

실제로 255 이상의 값을 넣으면 오버플로우되어 0부터 다시 시작한다.

 

2. memset은 주어지는 포인터의 타입과는 상관없이 1byte씩 초기화 한다.

사실 1번과 일맥상통한 이야기인데,

dest는 선언 타입이 int* 이었더라도, unsigned char*으로 간주하므로 각 element의 크기가 1byte인 배열의 포인터로 해석된다. 따라서 int 배열을 memset을 사용하여 1로 초기화하면 각 element의 값이 1이 되는게 아니라, 각 element의 4개의 byte가 1로 초기화되므로 아래와 같이 초기화된다.

bits: 00000001 00000001 00000001 00000001
number: 16843009

 

C++에서 memset을 사용할 일이 생기면 대신 std::fill이나 std::fill_n을 사용할 것을 권장한다. 

std::fill_n은 memset이 가능하면 memset으로 초기화하고, 불가능하면 반복문으로 초기화하기 때문에

0으로 초기화할 경우 memset에 비해 성능 저하가 크지 않다.

 

memset의 원리를 알고 있다면 실수할 일이 없지만 사람은 기계가 아니다.

 

 

sourceware.org Git - glibc.git/blob - string/memset.c

1 /* Copyright (C) 1991, 1997, 2003 Free Software Foundation, Inc. 2 This file is part of the GNU C Library. 4 The GNU C Library is free software; you can redistribute it and/or 5 modify it under the terms of the GNU Lesser General Public 6 License as publ

sourceware.org

glibc의 memeset 구현체 소스코드이다.

'Programming Language' 카테고리의 다른 글

lvalue + xvalue = glvalue  (0) 2022.07.08
유니코드 한글 초성 중성 종성 분리하기  (0) 2022.06.26
가상함수, RTTI  (0) 2022.06.14
C++ 재활  (0) 2022.04.06
Virtual Function in C++  (0) 2022.03.04