網(wǎng)站首頁(yè) 編程語(yǔ)言 正文
memset簡(jiǎn)介
memset是一個(gè)初始化函數(shù),作用是將某一塊內(nèi)存中的全部設(shè)置為指定的值。
void *memset(void *s, int c, size_t n);
- s指向要填充的內(nèi)存塊。
- c是要被設(shè)置的值。
- n是要被設(shè)置該值的字符數(shù)。
- 返回類型是一個(gè)指向存儲(chǔ)區(qū)s的指針。
需要說(shuō)明的幾個(gè)地方
一、不能任意賦值
memset函數(shù)是按照字節(jié)對(duì)內(nèi)存塊進(jìn)行初始化,所以不能用它將int數(shù)組出初始化為0和-1之外的其他值(除非該值高字節(jié)和低字節(jié)相同)。
其實(shí)c的實(shí)際范圍應(yīng)該在0~255,因?yàn)閙emset函數(shù)只能取c的后八位給所輸入范圍的每個(gè)字節(jié)。也就是說(shuō)無(wú)論c多大只有后八位二進(jìn)制是有效的。
=================================================================================================
對(duì)于int a[4];
memset(a, -1, sizeof(a)) 與 memset(a, 511, sizeof(a)) 所賦值的結(jié)果一樣都為-1:
因?yàn)?-1 的二進(jìn)制碼為(11111111 11111111 11111111 11111111);511 的二進(jìn)制碼為(00000000 00000000 00000001 11111111);
后八位均為(11111111),所以數(shù)組中的每個(gè)字節(jié)都被賦值為(11111111)。
注意int占四個(gè)字節(jié),例如a[0]的四個(gè)字節(jié)都被賦值為(11111111),那么a[0](11111111 11111111 11111111 11111111),即a[0] = -1。
二、注意所要賦值的數(shù)組的元素類型
先來(lái)看兩個(gè)例子:
例一:對(duì)char類型的數(shù)組a初始化,設(shè)置元素全為’1’
int main(){
char a[4];
memset(a,'1',4);
for(int i=0; i<4; i++){
cout<<a[i]<<" ";
}
return 0;
}
例二:對(duì)int類型的數(shù)組a初始化,設(shè)置元素值全為1
int main(){
int a[4];
memset(a,1,sizeof(a));
for(int i=0; i<4; i++){
cout<<a[i]<<" ";
}
return 0;
}
1、首先要說(shuō)明的第一點(diǎn)
?對(duì)于第二個(gè)程序,數(shù)組a是整型的,一般int所占內(nèi)存空間為4個(gè)字節(jié),所以在使用memset賦值時(shí),下面的語(yǔ)句是錯(cuò)誤的:
int a[4];
memset(a,1,4);
由于memset函數(shù)是以字節(jié)為單位進(jìn)行賦值的,所以上述代碼是為數(shù)組a的前4個(gè)字節(jié)進(jìn)行賦值,那么所得到的執(zhí)行結(jié)果就只能是:
正確的memset語(yǔ)句應(yīng)為:
memset(a,1,16); //int所占內(nèi)存為4字節(jié)的情況
memset(a,1,sizeof(a));
至于為什么不是預(yù)期得到的1,將在下面的第二點(diǎn)進(jìn)行說(shuō)明。
當(dāng)然,不同的機(jī)器上int的大小可能不同,所以最好用sizeof()函數(shù)。
2、為什么第一個(gè)程序可以正確賦值1而第二個(gè)不可以?
這就又回到了剛剛說(shuō)的第一個(gè)問(wèn)題,memset函數(shù)中只能取c的后八位賦給每個(gè)字節(jié)。
- 第一個(gè)程序中,數(shù)組a是字符型的,字符型占據(jù)的內(nèi)存大小就是1Byte,而memset函數(shù)也是以字節(jié)為單位進(jìn)行賦值的,所以輸出正確。
- 第二個(gè)程序中,數(shù)組a是整型的,整型占據(jù)的內(nèi)存大小為4Byte,而memset函數(shù)還是按照字節(jié)為單位進(jìn)行賦值,將1(00000001)賦給每一個(gè)字節(jié)。那么對(duì)于a[0]來(lái)說(shuō),其值為(00000001 00000001 00000001 00000001),即十進(jìn)制的16843009。
關(guān)于所要賦值的字符數(shù)的寫(xiě)法
先來(lái)看一個(gè)示例:
#include<bits/stdc++.h>
using namespace std;
void fun1(int a[]){
memset(a,-1,sizeof(a));
}
int main(){
int a[6];
fun1(a);
for(int i=0; i<6; i++){
cout<<a[i]<<" ";
}
return 0;
}
當(dāng)數(shù)組作為參數(shù)傳遞時(shí),其傳遞的實(shí)際上是一個(gè)指針,這個(gè)指針指向數(shù)組的首地址,如果用sizeof(a)函數(shù)得到的只是指針的長(zhǎng)度,而不是數(shù)組的長(zhǎng)度。
解決方案:
在函數(shù)中加入數(shù)組長(zhǎng)度參數(shù),在傳遞前先獲取數(shù)組長(zhǎng)度,然后將數(shù)組長(zhǎng)度作為參數(shù)傳遞進(jìn)去。
#include<bits/stdc++.h>
using namespace std;
void fun1(int a[], int len){
memset(a,-1,len);
}
int main(){
int a[6];
int len = sizeof(a);
fun1(a,len);
for(int i=0; i<6; i++){
cout<<a[i]<<" ";
}
return 0;
}
具體用法實(shí)例
初始化數(shù)組
char str[100];
memset(str,0,100);
清空結(jié)構(gòu)體類型的變量
typedef struct Stu{
char name[20];
int cno;
}Stu;
Stu stu1;
memset(&stu1, 0 ,sizeof(Stu));
Stu stu2[10]; //數(shù)組
memset(stu2, 0, sizeof(Stu)*10);
此外,如果結(jié)構(gòu)體中有數(shù)組的話還是需要對(duì)數(shù)組單獨(dú)進(jìn)行初始化處理的。
總結(jié)
? memset函數(shù)在初始化處理時(shí)非常方便,但也有其局限性,比如要注意初始化數(shù)值,要注意字節(jié)數(shù)等等。當(dāng)然,直接選擇用for循環(huán)或while循環(huán)來(lái)進(jìn)行初始化也是可以的,只不過(guò)memset更快捷一些。
原文鏈接:https://blog.csdn.net/weixin_44162361/article/details/115790452
相關(guān)推薦
- 2022-10-03 Android使用AudioRecord實(shí)現(xiàn)錄音功能_Android
- 2022-04-17 前端傳數(shù)組,后端怎么接收的問(wèn)題
- 2022-07-13 IO流分類以及分別使用字節(jié)流、字符流復(fù)制文本文件、復(fù)制圖片
- 2022-08-10 Pandas?sample隨機(jī)抽樣的實(shí)現(xiàn)_python
- 2022-12-24 Android開(kāi)發(fā)中Signal背后的bug與解決_Android
- 2022-12-14 PostgreSql?JDBC事務(wù)操作方法詳解_PostgreSQL
- 2022-10-16 pytorch中.numpy()、.item()、.cpu()、.detach()以及.data的使
- 2022-03-28 關(guān)于Qt添加opencv和libtorch庫(kù)的問(wèn)題_C 語(yǔ)言
- 最近更新
-
- window11 系統(tǒng)安裝 yarn
- 超詳細(xì)win安裝深度學(xué)習(xí)環(huán)境2025年最新版(
- Linux 中運(yùn)行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲(chǔ)小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎(chǔ)操作-- 運(yùn)算符,流程控制 Flo
- 1. Int 和Integer 的區(qū)別,Jav
- spring @retryable不生效的一種
- Spring Security之認(rèn)證信息的處理
- Spring Security之認(rèn)證過(guò)濾器
- Spring Security概述快速入門
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權(quán)
- redisson分布式鎖中waittime的設(shè)
- maven:解決release錯(cuò)誤:Artif
- restTemplate使用總結(jié)
- Spring Security之安全異常處理
- MybatisPlus優(yōu)雅實(shí)現(xiàn)加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務(wù)發(fā)現(xiàn)-Nac
- Spring Security之基于HttpR
- Redis 底層數(shù)據(jù)結(jié)構(gòu)-簡(jiǎn)單動(dòng)態(tài)字符串(SD
- arthas操作spring被代理目標(biāo)對(duì)象命令
- Spring中的單例模式應(yīng)用詳解
- 聊聊消息隊(duì)列,發(fā)送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠(yuǎn)程分支