Unix/Linux環境C程式設計入門教程(29) 記憶體操作那些事兒

尹成發表於2014-07-21
  1. 函式介紹

memccpy(拷貝記憶體內容)

相關函式

bcopy,memcpy,memmove,strcpy,strncpy

表標頭檔案

#include<string.h>

定義函式

void * memccpy(void *dest, const void * src, int c,size_t n);

函式說明

memccpy()用來拷貝src所指的記憶體內容前n個位元組到dest所指的地址上。與memcpy()不同的是,memccpy()會在複製時檢查引數c是否出現,若是則返回dest中值為c的下一個位元組地址。

返回值

返回指向dest中值為c的下一個位元組指標。返回值為0表示在src所指記憶體前n個位元組中沒有值為c的位元組。

範例

#include<string.h>
main()
{
char a[]="string[a]";
char b[]="string(b)";
memccpy(a,b,'B',sizeof(b));
printf("memccpy():%s\n",a);
}

執行

memccpy():string(b)

   




memchr(在某一記憶體範圍中查詢一特定字元)

相關函式

index,rindex,strchr,strpbrk,strrchr,strsep,strspn,strstr

表標頭檔案

#include<string.h>

定義函式

void * memchr(const void *s,int c,size_t n);

函式說明

memchr()從頭開始搜尋s所指的記憶體內容前n個位元組,直到發現第一個值為c的位元組,則返回指向該位元組的指標。

返回值

如果找到指定的位元組則返回該位元組的指標,否則返回0。

範例

#include <string.h>
main()
{
char *s="0123456789012345678901234567890";
char *p;
p=memchr(s,'5',10);
printf("%s\n",p);
}

執行

5.68E+25

   




memcmp(比較記憶體內容)

相關函式

bcmp,strcasecmp,strcmp,strcoll,strncmp,strncasecmp

表標頭檔案

#include<string.h>

定義函式

int memcmp (const void *s1,const void *s2,size_t n);

函式說明

memcmp()用來比較s1和s2所指的記憶體區間前n個字元。字串大小的比較是以ASCII碼錶上的順序來決定,次順序亦為字元的值。memcmp()首先將s1第一個字元值減去s2第一個字元的值,若差為0則再繼續比較下個字元,若差值不為0則將差值返回。例如,字串"Ac"和"ba"比較則會返回字元'A'(65)和'b'(98)的差值(-33)。

返回值

若引數s1和s2所指的記憶體內容都完全相同則返回0值。s1若大於s2則返回大於0的值。s1若小於s2則返回小於0的值。

範例

#include<string.h>
main()
{
char *a ="aBcDeF";
char *b="AbCdEf";
char *c="aacdef";
char *d="aBcDeF";
printf("memcmp(a,b):%d\n",memcmp((void*)a,(void*) b,6));
printf("memcmp(a,c):%d\n",memcmp((void*)a,(void*) c,6));
printf("memcmp(a,d):%d\n",memcmp((void*)a,(void*) d,6));

執行

memcmp(a,b):1 /*字串a>字串b,返回1*/
memcmp(a,c):-1 /* 字串a<字串c,返回-1*/
memcmp(a,d):0 /*字串a=字串d,返回0*/

   




memcpy(拷貝記憶體內容)

相關函式

bcopy,memccpy,memcpy,memmove,strcpy,strncpy

表標頭檔案

#include<string.h>

定義函式

void * memcpy (void * dest ,const void *src, size_t n);

函式說明

memcpy()用來拷貝src所指的記憶體內容前n個位元組到dest所指的記憶體地址上。與strcpy()不同的是,memcpy()會完整的複製n個位元組,不會因為遇到字串結束'\0'而結束。

返回值

返回指向dest的指標。

附加說明

指標src和dest所指的記憶體區域不可重疊。

範例

#include<string.h>
main()
{
char a[30]="string (a)";
char b[30]="string\0string";
int i;
strcpy(a,b);
printf("strcpy():");
for(i=0;i<30;i++)
printf("%c",a[i]);
memcpy(a,b,30);
printf("\nmemcpy() :");
for(i=0;i<30;i++)
printf("%c",a[i]);
}

執行

strcpy() : string a )
memcpy() : string string

   




memmove(拷貝記憶體內容)

相關函式

bcopy,memccpy,memcpy,strcpy,strncpy

表標頭檔案

#include<string.h>

定義函式

void * memmove(void *dest,const void *src,size_t n);

函式說明

memmove()與memcpy()一樣都是用來拷貝src所指的記憶體內容前n個位元組到dest所指的地址上。不同的是,當src和dest所指的記憶體區域重疊時,memmove()仍然可以正確的處理,不過執行效率上會比使用memcpy()略慢些。

返回值

返回指向dest的指標。

附加說明

指標src和dest所指的記憶體區域可以重疊。

範例

參考memcpy()。

   




memset(將一段記憶體空間填入某值)

相關函式

bzero,swab

表標頭檔案

#include<string.h>

定義函式

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

函式說明

memset()會將引數s所指的記憶體區域前n個位元組以引數c填入,然後返回指向s的指標。在編寫程式時,若需要將某一陣列作初始化,memset()會相當方便。

返回值

返回指向s的指標。

附加說明

引數c雖宣告為int, 但必須是unsigned char ,所以範圍在0到255之間。

範例

#include <string.h>
main()
{
char s[30];
memset (s,'A',sizeof(s));
s[30]='\0';
printf("%s\n",s);
}

執行

AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA

  1. 小試

    流程設定:

    原始碼實現:

    #include <stdio.h>
    #include <ctype.h>
    #include <string.h>
    #include <stdlib.h>
     
    int main(void)
    {    
    // //作為輸入緩衝區
    char buffer[32];
     
    long int res;
     
    //分配兩指標 後面利用這兩個指標進行遍歷操作
    char *q,*r;
    //malloc先分配一段記憶體p
    char *p = (char *)malloc(10*sizeof(char));
    printf("申請記憶體成功\n請輸入帶有數字的字串\n");
    scanf("%s",buffer);
     
    //memset清零
    memset(p,0,10);
    printf("memset清零\n");
     
    //memcpy 拷貝我們輸入緩衝區的數字字元進p
    q = p;
    r = buffer;
    while(r || q)
        {
    if(*r == '\0' )
    break;
    if(isdigit(*r)) //isdigit(測試字元是否為阿拉伯數字)
            {    
                //void * memmove(void *dest,const void *src,size_t n);
                memcpy(q,r,sizeof(char));
    printf("找到了一個字元並拷貝了\n");
    q++;
            }
    r++;
        }
    //atol轉化成一個長整形數 並輸出 long atol(const char *nptr);
        res = atol(p);
    printf("轉化後的數字是%ld \n",res);
     
    free(p);
    printf("釋放記憶體成功\n");
    return 0;
    }


查詢一下atol的標頭檔案

  1. 各平臺的執行情況

    在RHEL7上

    在RHEL6上

    在Solaris11上

    在mac上

相關文章