结构体内存对齐、sizeof与strlen、数据名当作参数传递

来源:互联网 发布:手机跟踪定位器软件 编辑:程序博客网 时间:2024/06/07 07:22

1.结构体对齐(对于32位系统)

结构体中成员根据其被声明的顺序按照自然对齐原则来(alignment)来分配内存,对

1)基本数据类型自然对齐:

char 1字节对齐

short 2字节对齐

int, long, float 4字节对齐

double: 8字节对齐

 

2)使用#pragma pack(n)来对齐

原则,

a)结构体成员按自己的方式对齐,取自然对齐与指定对齐(n)的较小值。

b)结构体的默认对齐方式字节数取其所有成员对齐参数中最大的一个。

c)结构体的长度必须为所用过的所有对齐参数的整数倍,不够就补空字节

 

#pragma pack(8)

struct s1{
short a;  //2
字节对齐,占4字节大小,下面的b不对齐填充了2字节形如11**
long b;   //4
字节对齐,占4字节大小
};   //
结构体大小为8字节, 对齐数为4,即其成员中最大的对齐参数max(2,4)

struct s2{
char c;   //1byte alignment, 
4字节,1***
s1 d;   //4
字节对齐8字节,至此已存储12字节,下面的e不对齐,需填充4字节

double e;  //8对齐,8大小。
};

#pragma pack() 

sizeof(s2) = 24

 

2. sizeofstrlen

1) sizeof可以用类型(需要用括号括起来)或变量做操作数,而strlen接受char*型字符指针做参数,并且该指针所指向的字符串必须是以'/0'结尾的;

22) sizeof是操作符,对数组名使用sizeof时得到的是整个数组所占内存的大小,而把数组名作为参数传递给strlen后数组名会被转换为指向数组第一个元素的指针;

3. 3)sizeof的结果在编译期就确定了,而strlen是在运行时被调用。

 

       char *p = "abcde";

       char a[10] = "abcde";

       char b[10] = {"abcde"};

       char c[10] = {'a','b','c','d','e'};

       char d[10] = {'a','b','c','d','/0'};

       int x = sizeof(p);

       int y = sizeof(a);

       int z = sizeof(b);

       int u = sizeof(c);

       int v = sizeof(d);

x,y,z,u,v的值分别为: __4,10,10,10,10___

 

       char *p = "abcde";

       char a[10] = "abcde";

       char b[10] = {"abcde"};

       char c[10] = {'a','b','c','d','e'};

       char d[10] = {'a','b','c','d','/0'};

       int x = strlen(p);

       int y = strlen(a);

       int z = strlen(b);

       int u = strlen(c);

       int v = strlen(d);

x,y,z,u,v的值分别为:__5,5,5,不确定,4_____

3.数据名当作参数传递

(1)数组名的内涵在于其指代实体是一种数据结构,这种数据结构就是数组;  

(2)数组名的外延在于其可以转换为指向其指代实体的指针,而且是一个指针常量;  

(3)指向数组的指针则是另外一种变量类型(在WIN32平台下,长度为4 ,仅仅意味着数组的存放地址!

#include <stdio.h>

void arrayTest(char str[])

{

printf(“%d/n”,sizeof(str));

}

int main(int argc,char* argv[])

{

   char str1[10]=”I Love U”;

   arrayTest(str1);

   return 0;

}

 

输出结果为4

1)  数组作为函数形参时,在函数体内,其失去了本身的内涵,仅仅只是一个指针;

2)  在失去其内涵的同时,它还失去了其常量特性,可以做自增,自减等操作,可以被修改。

 

4. 指向数据的指针自增

#include <stdio.h>
void main(int argc, char *argv[])
{
    int a[][3] = { 1,2,3 ,4,5,6};
    int (*ptr1)[1]=a;
    int (*ptr2)[2]=a;
    int (*ptr3)[3]=a;
    printf("%d ", (*ptr1)[0]); //1
    printf("%d ", (*ptr2)[0]); //1
    printf("%d ", (*ptr3)[0]); //1
    ++ptr1; //自增1
    ++ptr2; //自增2
    ++ptr3; //自增3
    printf("%d " , (*ptr1)[0]);  //2
    printf("%d " , (*ptr2)[0]);  //3
    printf("%d " , (*ptr3)[0]);  //4
}