复合数据类型
1.联合union
联合是一个能在同一个存储空间里(但不同时)存储不同类型数据的数据类型。
共享同一段内存空间
union u_data
{
unsinged char a;
unsigned int b;
} data;
sizeof(data) = 4
data.b = 0x12345678;
data.a = 78(小端字节序)
12(大端字节序)
data.a = 0xef;
data.b = 0x123456ef
2.枚举enum
可以使用枚举类型声明表示整数常量的符号名称。
enum
{
Gold,
Wood,
Water,
Fire = 8,
Earth,
};
switch(five_line)
{
case Gold:
do_something;
break;
default:
break;
}
#define LED1 1
#define LED2 2
#define LED3 3
#define LED_MAX 3
enum
{
LED1,
LED2,
LED3,
};
3.结构体Strut
char str[100];
str[9] == *(str+9)
str = "hello world" //编译器不会报错,运行出错
char str[100] = "hello world";//定义的同时进行初始化ok
char str[100];
strncopy ("hello world",sizeof(str));//运用strncopy可以
如果我们想保存学生的信息,这些信息包括学生的姓名,年龄,性别,成绩等。在我们已知的类型中是否有一种数据类型能够描述这所有信息?
结构体可以由基本数据类型构造出一种新的复合数据类型来。
enum { male, female };
struct _st_student
{
char name[32];
int gender;
int age;
float score;
} student;
struct _st_student student = {"zhangsan", male, 20, 90.0};
struct _st_student student = {.name="zhangsan", .gender=male, .age=20, .score=90.0};
printf("Name:%s Gender:%d Age:%d Score: %f\n", student.name, student.gender, student.age, student.score);
4.Typedef
Typedef 用来定义一种新的数据
t
ypedef unsigned char u8; u8 var1, var2;
typedef unsigned short uint_16; uint_16 var1, var2;
typedef char * pchar; pchar var1, var2;
typedef int * pint; pint var1, var2;
#define PCHAR char * PCHAR var1, var2;
typedef struct _st_student
{
char name[32];
int gender;
int age;
float score;
} st_student;
st_student student; == struct _st_student student;
_exit:
若一个函数前带_说明它是底层函数,不能随意调用
5.结构体对齐
typedef struct _st_struct1
{
char a;
short b;
int c;
} st_struct1;
sizeof(st_struct1) = 8
t
ypedef struct _st_struct2
{
short b;
int c;
char a;
} st_struct2;
sizeof(st_struct2) = 12
自身对齐值: 自身对齐值就是结构体变量里每个成员的自身大小;
指定对齐值: 指定对齐值是由宏#pragma pack (N)指定的值,里面的N必须是2的幂次方,如1,2,4,8,16等。如果没有通过#pragma pack宏那么在32位的Linux主机上默认指定对齐值为4,64位的Linux主机上默认指定对齐值为8,ARM CPU默认指定对齐值为8;
有效对齐值: 结构体成员自身对齐时有效对齐值为自身对齐值与指定对齐值中较小的一个,结构体圆整时,为所有成员中自身对齐值最大的与指定对齐值较小的一个;
步骤: 1, 结构体各成员对齐 2,整个结构体圆整
CPU从内存上取数据:data一次传32位(4个字节)address从2开始,1<<2 01->100 (4),2<<2 10->1000(8),4的整数倍
结构体指针
st_student student;
st_student *ptr = NULL;
ptr = &student;
strncpy(student.name, "zhangsan", 32);
student.gender = female;
student.age = 19;
student.score = 95.0;
strncpy(ptr->name, "zhangsan", 32);
ptr->gender = female;
ptr->age = 19;
ptr->score = 95.0;
(*ptr).gender = female;
(*ptr).age = 19;
(*ptr).score = 95.0;
指针访问它里面的成员用->
变量访问它里面的成员用.
结构体嵌套
typedef struct _st_score
{
float math;
int english;
int chinese;
} st_score
typedef struct _student
{
char name[32];
int gender;
int age;
st_score score;
st_score *pscore;
} st_student;
st_student student;
st_student *ptr = &student;
student.score.math = 90.0; student.pscore->math = 90.0
ptr->scrore.math = 90.0; ptr->pscore->math = 90.0
函数指针与回调函数
指针是用来存放地址的,而函数名就是函数的入口地址。那么我们是否可以定义一个指针来指向一个函数?
int func1(int arg1, int arg2); void func2(int arg1, int arg2)
int (*func_ptr)(int, int) ; int *func_ptr(int , int);
func_ptr = func1; func_ptr = func2;
func_ptr(1,2) == func1(1,2);
float calc_total_score(struct st_score score)
{
return score.math+score.english+score.chinese;
}
float print_student_score(struct st_score score, float (* func_ptr)(struct st_score))
{
printf("Math:%f English:%f Chinse:%f Total:%f\n",
score.math, score.english, score.chinese, func_ptr(score));
}
print_student_score(student.score, calc_total_score);
题目:
AVR32(Internal SRAM:0x0000) AVR32(SDRAM:0x30000000: )
kernel.bin 0x30008000 void entry(int zero,int arch,void*);
void(*ptr)(int,arch,void*) =(void (*)(int,arch,void*)0x30008000)
*ptr(); ptr();
bootloader.SRAM:->SDRAM //通过函数指针