關於memset賦值問題


學習借鑒自:https://blog.csdn.net/yexiaohhjk/article/details/52717934

 

memset是C語言頭文件<string.h>中的一個函數,作用是在一段內存塊中填充某個給定的值,它是對較大的結構體數組進行清零操作的一種最快方法

memset(數組名,賦值變量,數組長度);

void *memset(void *s, int ch, size_t n);

初始化清零是   memset(a,0,sizeof(a));
初始化無窮大是   memset(a,0x3f,sizeof(0x3f));

memset的賦值規則:

逐一對數組范圍內的每個字節進行賦值(一字節 = 8_bit,1_bit = 一位二進制數)也就是也就賦值有效數值在8_bit(兩位16進制);

假設我們對一個長度為2的int型數組進行賦值 0x3f4f5f6f(0x表示16進制,該數表示6進制數3F4F5F6F)memset(a,0x3f4f5f6f,sizeof(a))

在存儲單元中就將得到 6F 6F 6F 6F    6F 6F 6F 6F 

那么坑人的問題就出來了 a[0]=6F 6F 6F 6F ,而我們原來要的結果是把0x3f4f5f6f賦值給a數組;

當我們要用0x3f4f5f6f與a數組中的值對比時你就會發現不等於,那么我們的賦值就失去意義

現在我們用0x6f 賦值:

在存儲單元中就將得到 6F 6F 6F 6F    6F 6F 6F 6F 

#include<cstring>//C語言頭文件在C++中的用法
#include<cstdio>
using namespace std;
int main(){
    int a[2];
    printf("a數組字節數:\n%d\n",sizeof(a));

    memset(a,0x6f,sizeof(a));
    printf("給a數組賦值為0x6f:\n");
    for(int i=0;i<2;i++)
        printf("%d ",a[i]);
    printf("\n");

    memset(a,0x3f4f5f6f,sizeof(a));
    printf("給a數組賦值為0x3f4f5f6f:\n");
    for(int i=0;i<2;i++)
        printf("%d ",a[i]);
    printf("\n");

    printf("賦值0x3f4f5f6f后的數組是否於0x3f4f5f6f相等:");
    if(a[0]==0x3f4f5f6f)
        printf("yes");
    else
        printf("no");
    return 0;
}

 

當memset(,1,sizeof()); 1轉為二進制0000 0001,當做一字節,一字節8位,int為4字節,所以初始化完每個數為0000 0001 0000 0001 0000 0001 0000 0001 = 16843009;

賦值無窮大問題:

這個問題是在我做最短路問題時,遇到的明明代碼對了,卻一直得不到想要的答案,最后對比別人的代碼發現問題原來我的預設的無窮大值是0x3f3f3f;

那么就會出現上述的問題,數組值不等於我們賦的值。

賦值int型時,int型的位數根據編譯器而定,現在一般主流的編輯器都是4字節,賦無窮大值時我們一般賦值所有 bit 位全 1 ,留一位當符號位,其余全1剛好是0x7fffffff

為什么無窮大值不取0x7fffffff,這個數是32_bit中最大的值,而取0x3f3f3f3f或0x3f(取0x3f時比較相等要和0x3f3f3f3f比),在編程過程中我們給一個數組賦值后是需要使用的,

如果你設置一個這么大的數的話,當進行加和操作的時候很容易數據溢出,而得到一個負數。所以這個數還需要能做的“無窮大加無窮大等於無窮大”,所以我們取0x3f3f3f3f或0x3f。

數值上0x3f3f3f3f是10^9,一般當無窮大已經夠了,又滿足“無窮大加無窮大等於無窮大”

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM