日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

C语言再学习 -- 关键字sizeof与strlen

發布時間:2025/3/15 编程问答 23 豆豆
生活随笔 收集整理的這篇文章主要介紹了 C语言再学习 -- 关键字sizeof与strlen 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

sizeof?

一、簡單介紹

sizeof 是 C 語言的一種單目操作符,如 C 語言的其他操作符++、--等。它并不是函數C 規定 sizeof 返回 sieze_t 類型的值。這是一個無符號整數類型。C99更進一步,把%zd 作為用來顯示 size_t 類型值的 printf() 說明符。如果你的系統沒有實現 %zd,你可以試著使用 %u 或者 %lu 代替它。

sizeof 操作符以字節形式給出了其操作數的存儲大小。操作數可以是一個表達式或括在括號內的類型名。操作數的存儲大小由操作數的類型決定。


二、使用方法

1、用于數據類型

sizeof 使用形式: sizeof (type)

數據類型必須用圓括號括住。如:sizeof (int)


2、用于變量

sizeof 使用形式:sizeof (var_name) 或 sizeof var_name

變量名可以不用圓括號括住。如:sizeof (6.08) 或 sizeof 6.08 等都是正確的形式。帶括號的用法更普遍,大多數程序員采用這種形式。

注意:sizeof 操作符不能用于函數類型,不完全類型和位字段。不完全類型指具有未知存儲大小的數據類型,如未知存儲大小的數組類型未知內容的結構或聯合類型void類型等。如:


sizeof (max) 若此時變量 max 定義為 int max ( ),

sizeof (char_v) 若此時 char_v 定義為 char char_v [MAX] 且 MAX 未知

sizeof (void)

上述例子,都是不正確的形式。


3、sizeof 的結果

sizeof 操作符的結果類型是 size_t,它在頭文件中 typedef 為 unsigned int 類型。該類型保證能容納實現所建立的最大對象的字節大小。

1)在windows,32位系統中
char ? ? ? ? 1個字節
short ? ? ? ?2個字節
int ? ? ? ? ? ?4個字節
long ? ? ? ? 4個字節
double ? ?8個字節
float ? ? ? ? 4個字節


看看這三個分別是什么?
1,‘ 1‘,“ 1”。

第一個是整形常數, 32 位系統下占 4 個 byte;
第二個是字符常量,占 1 個 byte;
第三個是字符串常量,占 2 個 byte。

三者表示的意義完全不一樣,所占的內存大小也不一樣,初學者往往弄錯。


2)當操作數為指針時,sizeof 依賴于編譯器。一般unix的指針為 4個字節

#include <stdio.h>int main (void) {char ptr[] = "hello";char *str = ptr;printf ("sizeof (str) = %d\n", sizeof (str));return 0; } 輸出結果: sizeof (str) = 4

在 32 位系統下,不管什么樣的指針類型,其大小都為 4 byte。可以測試一下 sizeof( void *)。


3)當操作數具有數組類型時,其結果是數組的總字節數

#include <stdio.h>int main (void) {int ptr[20] = {1,2,3,4,5};printf ("sizeof (ptr) = %d\n", sizeof (ptr));return 0; } 輸出結果: sizeof (ptr) = 80

4)聯合類型操作數的 sizeof 是其最大字節成員的字節數,結構體類型操作數的sizeof,需要考慮內存對齊補齊。

參看:C語言再學習 -- 結構和其他數據形式

[cpp]?view plaincopy
  • #include?<stdio.h>??
  • ??
  • typedef?union?{??
  • ????char?ch;??
  • ????int?num;??
  • }UN;??
  • ??
  • int?main?(void)??
  • {??
  • ????printf?("sizeof?(UN)?is?%d\n",?sizeof?(UN));??
  • ????return?0;??
  • }??
  • 輸出結果:??
  • sizeof?(UN)?is?4??
  • 結構體內存對齊與補齊

    一個存儲區的地址一定是它自身大小的整數倍(雙精度浮點類型的地址只需要4的整數倍就行了),這個規則也叫數據對齊,結構體內部的每個存儲區通常也需要遵守這個規則。數據對齊可能造成結構體內部存儲區之間有浪費的字節。
    結構體的大小一定是內部最大基本類型存儲區大小的整數倍,這個規則叫數據補齊
    [cpp]?view plaincopy
  • #include?<stdio.h>??
  • typedef?struct??
  • {??
  • ????char?ch;??
  • ????int?num;??
  • ????char?ch1;??
  • }str;??
  • ??
  • int?main?(void)??
  • {??
  • ????printf?("sizeof?(str)?is?%d\n",?sizeof?(str));??
  • ????return?0;??
  • }??
  • 輸出結果:??
  • sizeof?(str)?is?12??


  • 5)如果操作數是函數中的數組形參或函數類型的形參,sizeof給出其指針的大小

    #include <stdio.h>char ca[10];void foo (char ca[100]) {printf ("sizeof (ca) = %d\n", sizeof (ca)); } int main (void) {char ca [25];foo (ca);return 0; } 輸出結果: sizeof (ca) = 4

    三、主要用途

    1、sizeof操作符的一個主要用途是與存儲分配和I/O系統那樣的例程進行通信。例如:void *malloc(size_t size), size_t fread(void *ptr, size_t size, size_t nmemb, FILE *stream) ?

    2、sizeof的另一個的主要用途是計算數組中元素的個數。例如:void *memset(void *s,int c,sizeof(s))

    3.在動態分配一對象時,可以讓系統知道要分配多少內存。如:int *p=(int *)malloc(sizeof(int)*10);

    4.由于操作數的字節數在實現時可能出現變化,建議在涉及到操作數字節大小時用sizeof來代替常量計算。

    5.如果操作數是函數中的數組形參或函數類型的形參,sizeof給出其指針的大小。


    四、注意的地方

    1、在混合類型的算術運算的情況下,較小的類型被轉換成較大的類型。反之,可能會丟失數據。

    #include <stdio.h> #include <string.h> #include <stdlib.h>int main (void) {int a = 10;printf ("sizeof ((a > 5) ? 4 : 8.0) = %d\n", sizeof ((a > 5) ? 4 : 8.0));return 0; } 輸出結果: sizeof ((a > 5) ? 4 : 8.0) = 8

    2、判斷表達式的長度并不需要對表達式進行求值

    #include <stdio.h> int main (void) {int a = 10;int b = 0;int c = sizeof (b = a + 12);printf ("a = %d, b = %d, c = %d\n", a, b, c);return 0; } 輸出結果: a = 10, b = 0, c = 4

    所以sizeof (b = a + 12)并沒有向 a 賦任何值。


    strlen

    strlen首先是一個函數,只能以char * 做參數返回的是字符的實際長度,不是類型占內存的大小。其結果是運行的時候才計算出來的。

    #include <string.h>
    size_t strlen(const char *s);

    函數功能:用來統計字符串中有效字符的個數

    功能實現函數:

    [cpp]?view plaincopy
  • size_t?strlen?(const?char?*s)??
  • {??
  • ????const?char?*sc;??
  • ????for?(sc?=?s;?*sc?!=?'\0';?++sc)??
  • ????/"nothing"/??
  • ????return?sc?-?s;??
  • }??
  • strlen()函數被用作改變字符串長度,例如:

    [cpp]?view plaincopy
  • #include?<stdio.h>??
  • #include?<string.h>??
  • void?fit?(char?*,?unsigned?int);??
  • int?main?(void)??
  • {??
  • ????char?str[]?=?"hello?world";??
  • ????fit?(str,?7);??
  • ????puts?(str);??
  • ????puts?(str?+?8);??
  • ????return?0;??
  • }??
  • ??
  • void?fit?(char?*string,?unsigned?int?size)??
  • {??
  • ????if?(strlen?(string)?>?size)??
  • ????????*(string?+?size)?=?'\0';??
  • }??
  • 輸出結果:??
  • hello?w??
  • rld??
  • 可以看出:fit()函數在數組的第8個元素中放置了一個'\0'字符來代替原有的o字符。puts()函數輸出停在o字符處,忽略了數組的其他元素。然而,數組的其他元素仍然存在。

    puts (str + 8);

    表達式str + 8是str[8]即'r'字符的地址。因此puts()顯示這個字符并且繼續輸出知道遇到原字符串中的空字符。


    sizeof 與 strlen 的區別

    參看:C語言再學習 -- 字符串和字符串函數

    談兩者的區別之前,先要講一下什么是字符串,字符串就是一串零個或多個字符,并且以一個位模式為全 0 的 '\0' 字節結尾。如在代碼中寫 "abc",那么編譯器幫你存儲的是 "abc\0"。

    siezeof運算符提供給你的數目比strlen大1,這是因為它把用來標志字符串結束的不可見的空字符('\0')也計算在內。

    #include <stdio.h> #include <string.h> #include <stdlib.h>int main (void) {char *str1 = "abcde";char str2[] = "abcde";char str3[8] = "abcde";char str4[] = {'a', 'b', 'c', 'd', 'e'};char *p1 = malloc (20);printf ("sizeof (str1) = %d, strlen (str1) = %d\n", sizeof (str1), strlen (str1));printf ("sizeof (*str1) = %d, strlen (str1) = %d\n", sizeof (*str1), strlen (str1));printf ("sizeof (str2) = %d, strlen (str2) = %d\n", sizeof (str2), strlen (str2));printf ("sizeof (str3) = %d, strlen (str3) = %d\n", sizeof (str3), strlen (str3));printf ("sizeof (str4) = %d, strlen (str4) = %d\n", sizeof (str4), strlen (str4));printf ("sizeof (p1) = %d, sizeof (*p1) = %d\n", sizeof (p1), sizeof (*p1));printf ("sizeof (malloc(20)) = %d\n", sizeof (malloc (20)));return 0; } 輸出結果: sizeof (str1) = 4, strlen (str1) = 5 sizeof (*str1) = 1, strlen (str1) = 5 sizeof (str2) = 6, strlen (str2) = 5 sizeof (str3) = 8, strlen (str3) = 5 sizeof (str4) = 5, strlen (str4) = 5 sizeof (p1) = 4, sizeof (*p1) = 1 sizeof (malloc(20)) = 4


    總結:

    1. sizeof 操作符的結果類型是 size_t,它在頭文件中typedef為?unsigned int?類型。該類型保證能容納實現所建立的最大對象的字節大小。

    2. sizeof 是算符,strlen 是函數

    3.?sizeof可以用類型做參數strlen只能用char*做參數且必須是以''\0''結尾的。sizeof 還可以用函數做參數,比如:

    short f();
    printf("%d\n",sizeof(f()));
    輸出的結果是sizeof(short),即2。

    4.數組做 sizeof 的參數不退化,傳遞給 strlen 就退化為指針了。

    5.大部分編譯程序 在編譯的時候就把 sizeof 計算過了 是類型或是變量的長度這就是 sizeof(x) 可以用來定義數組維數的原因
    charstr[20]="0123456789";
    int a=strlen(str);//a=10;
    int b=sizeof(str);//而b=20;

    6. strlen 的結果要在運行的時候才能計算出來,是用來計算字符串的長度,不是類型占內存的大小

    7. sizeof 后如果是類型必須加括弧,如果是變量名可以不加括弧。這是因為sizeof是個操作符不是個函數。

    8. 當適用了于一個結構類型時或變量, sizeof 返回實際的大小,當適用一靜態地空間數組, sizeof 歸還全部數組的尺寸。sizeof 操作符不能返回動態地被分派了的數組或外部的數組的尺寸。

    9.?數組作為參數傳給函數時傳的是指針而不是數組,傳遞的是數組的首地址,如:
    fun(char [8])
    fun(char [])
    都等價于 fun(char *)
    在C++里參數傳遞數組永遠都是傳遞指向數組首元素的指針,編譯器不知道數組的大小如果想在函數內知道數組的大小, 需要這樣做:進入函數后用memcpy拷貝出來,長度由另一個形參傳進去
    fun(unsiged char*p1, int len)
    {
    ? ? unsigned char* buf= new unsigned char[len+1]
    ? ? memcpy(buf, p1,len);
    }

    我們能常在用到 sizeof 和 strlen 的時候,通常是計算字符串數組的長度看了上面的詳細解釋,發現兩者的使用還是有區別的,從這個例子可以看得很清楚:

    charstr[20]="0123456789";
    int a=strlen(str);//a=10; >>>> strlen 計算字符串的長度,以結束符 0x00 為字符串結束。
    int b=sizeof(str);//而b=20; >>>> sizeof 計算的則是分配的數組 str[20] 所占的內存空間的大小,不受里面存儲的內容改變。
    上面是對靜態數組處理的結果,如果是對指針,結果就不一樣了

    char* ss ="0123456789";
    sizeof(ss) 結果4 ===》ss是指向字符串常量的字符指針,sizeof 獲得的是一個指針的之所占的空間,應該是 長整型的,所以是4
    sizeof(*ss) 結果1 ===》*ss是第一個字符 其實就是獲得了字符串的第一位'0' 所占的內存空間,是char類 型的,占了 1 位
    strlen(ss)= 10 >>>>?strlen 計算字符串的長度,以結束符 0x00 為字符串結束


    面試題:

    1、sizeof( int) *p 表示什么意思?

    需要明白 sizeof 后跟數據類型,必須要用圓括號括住的,強制類型轉換也應該是 (int*) p,所以這句話所表達的意思是 sizeof (int) 乘以 p

    #include <stdio.h>int main (void) {int p = 1;printf ("%d\n", sizeof (int)*p); return 0; } 輸出結果: 4

    #include <stdio.h>int main (void) {int p = 1;printf ("%d\n", sizeof ((int *)p)); //強制類型轉換return 0; } 輸出結果: 4

    2、在 32 位系統下:
    int *p = NULL;
    sizeof(p)的值是多少?
    sizeof(*p)呢?

    sizeof (p) = 4; ?因為 p為指針,32位系統 指針所占字節為 4個字節

    sizeof (*p) = 4; ?因為 *p 為 指針所指向的變量為int類型,整型為 4個字節

    #include <stdio.h>int main (void) {short *p = NULL;int i = sizeof (p);int j = sizeof (*p);printf ("i = %d, j = %d\n", i, j);return 0; } 輸出結果: i = 4, j = 2

    3、int a[100];
    sizeof (a) 的值是多少?
    sizeof(a[100])呢? //請尤其注意本例。
    sizeof(&a)呢?
    sizeof(&a[0])呢?

    sizeof (a) = 400; ?因為 a是類型為整型、有100個元素的數組,所占內存為400個字節

    sizeof (a[100]) = 4; ?因為 a[100] 為數組的第100元素的值該值為 int 類型,所占內存為4個字節。

    sizeof (&a) = 4; ?因為 &a 為數組的地址即指針,32位系統 指針所占字節為 4個字節

    sizeof (&a[0]) = 4; 因為&a[0] 為數組的首元素的地址即指針,32位系統 指針所占字節為 4個字節

    #include <stdio.h>int main (void) {int a[100];printf ("sizeof (a) = %d\n", sizeof (a));printf ("sizeof (a[100] = %d\n", sizeof (a[100]));printf ("sizoef (&a) = %d\n", sizeof (&a));printf ("sizeof (&a[0] = %d\n)", sizeof (&a[0]));return 0; } 輸出結果: sizeof (a) = 400 sizeof (a[100] = 4 sizoef (&a) = 4 sizeof (&a[0] = 4

    4、int b[100];
    void fun(int b[100])
    {
    sizeof(b);// sizeof (b) 的值是多少?
    }

    sizeof (b) = 4; ?因為函數中的數組形參或函數類型的形參,sizeof給出其指針的大小。參數傳遞數組永遠都是傳遞指向數組首元素的指針。

    #include <stdio.h>void fun (int b[100]) //指針做形參 {printf ("sizeof (b) = %d\n", sizeof (b)); }int main (void) {int a[10];fun (a);return 0; } 輸出結果: sizeof (b) = 4

    #include <stdio.h> void foo (void) {printf ("111\n"); }void fun (foo) //函數做形參 {printf ("sizeof (foo) = %d\n", sizeof (foo)); } int main (void) {fun ();return 0; } 輸出結果: sizeof (foo) = 4



    總結

    以上是生活随笔為你收集整理的C语言再学习 -- 关键字sizeof与strlen的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。