memset、memcpy 是內存操作雙雄,雖屬 <string.h>,但實為「字節級內存填充/複製」,適用於任意類型數據,遠不限字符串。本文深度解析參數語義、典型用法、易錯陷阱與最佳實踐。
void* memset(void* s, int c, size_t n);
c 取低 8 位(unsigned char),逐字節填充 n 個字節。s,支持鏈式調用。// 1. 清零結構體/數組(最常用)
struct Pos { int x, y; } pos;
memset(&pos, 0, sizeof(pos));
int arr[100]; memset(arr, 0, sizeof(arr));
// 2. 字符串初始化(注意:字符串字面量不可修改!)
char s[] = "Hello"; // 棧上數組,可修改
memset(s, 'X', 3); // "XXXlo"
char* p = "Hello"; // 指向只讀區,memset(p,...) → 崩潰!
int a[5]; memset(a, 1, sizeof(a)); // 結果:每字節 0x01 → 每 int 0x01010101 = 16843009,而非 1! // 正確做法:for 循環賦值,或用 memcpy 複製模板數組。
void* memcpy(void* dest, const void* src, size_t n);
n 字節,不檢查重疊(重疊用 memmove)。dest。陷阱:目標空間不足
特性 memset memcpy 操作 填充單一字節值 複製內存塊 適用類型 任意(字節視圖) 任意(字節視圖) 重疊安全 無重疊概念 不安全(用 memmove) 常見用途 清零結構體、初始化數組 結構體複製、數據序列化、緩衝區拷貝 性能 極快(編譯器常優化為向量指令) 極快(同前) 最佳實踐清單
- 清零結構體/數組首選
2. 非 0 值填充整型/浮點數組**禁用**memset(ptr, 0, size),比循環快且不易出錯。memset,改用循環或memcpy複製模板。 3. 複製結構體/數組用memcpy,注意目標空間足夠、源目不重疊(重疊用memmove)。 4. 字符串字面量const char***絕不** 作為memset/memcpy目標。 5. 內存操作函數不關心類型,**務必手動計算正確字節數**(sizeof、strlen+1等)。