云计算百科
云计算领域专业知识百科平台

day 15 指针+函数

一、malloc 的基本概念与使用

malloc 是 C 语言中用于在堆上动态分配内存的函数,属于 <stdlib.h> 标准库。它根据指定的大小分配一块连续的内存空间,并返回指向该空间首地址的指针。若分配失败,返回 NULL。

malloc:数据可以开在堆上。手动申请,手动释放。

void* malloc(size_t size);  

功能:申请堆区空间 ;             参数:size:表示申请的空间大小,单位字节;

返回值:void*  表示空类型指针。

void*    万能指针:可以接受任意类型的指针。

int a = 10;
void *p = &a;
printf("&d\\n",*p); void表示空类型则最终不知道偏移多大一块空间

printf("&d\\n",*(int *)p);
如果想通过void * 类型的指针引引用到数据必须,强转为,你希望访问的指针类型

void *calloc(size_t nmemb,size_t size);   //calloc(10,sizeof(int));

void *realloc(void *ptr,size_t size);

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
void getmemory(char** p, int num) {
*p = (char*)malloc(num);
}
int main() {
char* str = NULL;

#str本身是一个指针,其值为NULL,表示它当前不指向任何有效的内存地址。str 存储的是内存地址。
#*str 是对指针 str 的解引用(dereference),即访问 str 所指向的内存位置的值。
#但由于str被初始化为 NULL,解引用 *str 会导致未定义行为(通常是程序崩溃,如段错误)。
#str 是指针变量,存储地址。
#*str 是解引用操作,访问指针指向的值(但需指针有效)。
#&str 是取指针变量 str 本身的地址,而不是指针指向的内容。即使str是NULL,&str仍然是合法的#操作,因为它返回的是指针变量 str 在内存中的地址。

getmemory(&str, 100);

#getmemory(str, 100); 和 getmemory(&str, 100); 的主要区别在于参数传递方式:
#前者传递指针的值(传值),后者传递指针的地址(传址)。

strcpy(str, "hello");
printf("%s", str);
free(str);
return 0;
}

注意:1.指针类型可以作为国数的返回值类型2.不能返回一个局部变量(栈上)的地址—已经是一个被销毁了的空间。

二、指针函数及函数指针

指针函数(返回值为指针的函数)及函数指针(指向函数的指针变量,如回调函数)。

#指针函数: 返回类型* 函数名(参数列表);
#函数指针:返回类型 (*指针变量名)(参数列表);

可以获得函数所在空间的地址函——函数名就是函数的入口地址

int add(int a,int b)

{           }//add函数名—就是函数的入口地址

定义个什么类型的指针来存放这种地址

函数也是有类型——函数类型

int add (int a,int b);add名字去掉 剩下就是函数类型

int(int a,int b)//—表示这么一类函数,返回值为int型,同时带有两个int型形参

int sum(int a,int b);

float sub(float b,float b);

#include <stdio.h>
int add(int a,int b)
{
return a+b;
}
int main(void)
{
int (*p)(int,int) = add; //函数指针
int(*pf[4])(int,int)= {add,sub,mul,div}: //指针函数数组
int i =0;
for(i = 0; i < 4; ++i)
{
processData(10,3,pf[i]);
}
int ret = p(1,2);
printf("ret = %d\\n",ret);
return 0;
}

地址:指针变量

int (int a,int b)    *p;//这种函数类型的指针–理解可以,但是不能这么写

int  (*p)(int a,int b);//c语言标准写法

回调函数:通过函数指针进行函数调用这种就叫回调函数,

C语言是通过函数指针实现回调。

#include <stdlib.h>
void qsort( void *base, 指向要带序的数组起始地址
size_t nmemb, 要排序元素个数
size_t size, 单个元素大小
int(*compar)(const void *,const void *) 比较规则一个函数,函数指针;

intcompar(constvoid*a,const void *b) a和b实际上是数组中某两个元素的地址
{
return *(int *)a – *(int *)b;
}
#include <stdio.h>
//const char * *
int main(int argc, const char *argv[])
{
printf("argc = %d\\n",argc);

int i = 0;
while(argv[i] != NULL)
{
printf("argv[%d] = %s\\n",i,argv[i]);
i++;
}
return 0;
}

三、结构体

结构体(struct)是一种用户自定义的数据类型,用于将多个不同类型的变量组合成一个逻辑单元。适用于需要将相关联的数据聚合管理的场景(如学生信息、坐标点等)。

struct Student {
char name[50];
int age;
float height;
};

告诉编译器,我定义了一个亲新的数据类型 —— 代表学生数据的-数据类型

自定义数据类型:

类型名:struct  student     //等价int ,short,float等。

结构体的大小:

内存对齐:为了提高效率32位将数据尽可能放到能被4字节整除的地址编号上。

结构体对齐的规则:1.结构体成员的对齐;要在自然边界对齐

                                 2.整个结构体最大的成员对齐

结构体的声明与初始化:声明结构体变量时可直接初始化

结构体初始化:

structstu s ={按照成员变量的的顺序,依次初始化};

方式:按照成员变量本身方式初始化,初始化值之间以逗号分隔

结构体变量的引用:访问数据不能访问整个结构体,必须访问到具体成员。

结构体变量名.成员变量名——-访问到了具体成员

赞(0)
未经允许不得转载:网硕互联帮助中心 » day 15 指针+函数
分享到: 更多 (0)

评论 抢沙发

评论前必须登录!