指针_三种方式访问成员、动态内存分配【就当做笔记了】*

来源:互联网 发布:巨人网络回归a股涨多少 编辑:程序博客网 时间:2024/06/04 18:13

指针的三种访问成员的方式

参照自P304,谭浩强《C程序设计》第四版

#include<stdio.h>int main(){struct stu//自己定义的stu类型{int num1 = 1;int num2 = 2;int num3 = 3;}member;stu *p = &member;//member 即 成员名,printf("%d\n",member.num1);printf("%d\n",(*p).num2);printf("%d\n",p->num3);return 0;}//参照自P304,谭浩强《C程序设计》第四版

C++中“->”和“.”在使用中有什么区别呢(出自https://zhidao.baidu.com/question/415177703.html)

->是指针指向其成员的运算符 .是结构体的成员运算符。

最大的区别是

【->】前面放的是【指针】,而【.】前面跟的是【结构体变量】。

struct A{   int a;   int b;};A *point = malloc(sizeof(struct A));point->a = 1;//指针A object;object.a = 1;//结构体变量


动态内存分配

参照自P286,谭浩强《C程序设计》第四版
==============(除了sizeof函数,都要用上<stdlib.h>库)============

malloc和free函数简介 

malloc函数 
原型:void *malloc(unsigned int size); 
简介:该函数在内存的动态存储区中分配一块长度为size字节的连续区域;如果分配成功,则函数的返回值为该区域的首地址;如果分配失败,则返回空指针值NULL。

malloc(100);//开辟100字节的临时分配域,返回值为其第一个字节的地址


free函数 
原型:void free(void *p); 
简介:该函数将最近一次用malloc或calloc开辟的动态内存空间释放掉(p是最近一次调用malloc或calloc函数时得到的返回值),free函数无返回值。

free(p);//释放p所指向的已分配动态空间

calloc和realloc函数

calloc函数
原型:void *calloc(unsigned n,unsigned size);
简介:"数组似的"开辟空间
p=calloc(50,4);//开辟50*4个字节的临时分配域,把起始地址赋给指针变量p


realloc函数
原型: void *realloc(void *p, unsigned int size);
简介:“改变”已分配的“空间大小”
realloc(p,50);//将p所指向的已分配的动态存储空间改为50字节

注:unsigned int 无符号整数类型,(说白了就是不让你取负数= =)

sizeof函数

原型:sizeof有三种语法形式,如下:

1
2
3
sizeof(object);//sizeof(对象);
sizeof(type_name);//sizeof(类型);
sizeof object;//sizeof对象;

简介:sizeof是计算对象所占的字节个数,通常用来查看变量或结构体等所占的字节个数。

比如:

1
2
3
4
5
6
7
8
9
int a;
sizeof(a);   // 计算变量a所占的字节数,等价于sizeof(int)  
struct
{
    int num;
    char name[];
    int age;
}person;
sizeof(person);  // 计算整个结构所占的字节总数

又如:
#include<stdio.h>void main(){int a=sizeof(int);printf("%d", a);}
输出是4,因为 int 类型占4个字节。


一般用法:
#include<stdio.h>#include<stdlib.h>void main(){float z = 1;int * b= (int*)malloc(sizeof(z));//b初始化时给它分配内存【整形指针型,z的大小(此处为float大小)的内存】}


野指针

野指针指向一个已删除的对象或未申请访问受限内存区域的指针
比如定义一个指针后没给他赋值或者malloc一个空间,就使用之。
#include<stdio.h>#include<stdlib.h>void main(){int z = 1;int x = 2;//int * a ;//printf("%d", a);//整形指针a什么都没有就使用,出错//int * b ;//b初始化时没给它内存,出错//*b = z;//printf("%d", *b);int * b= (int*)malloc(sizeof(z));//b初始化时给它分配内存【整形指针型,z的大小的内存】*b = z;printf("%d\n", *b);//成功int * c = &z;//最常用方法,分配内存;直接指向了zprintf("%d\n", *c);c = &x;printf("%d\n", *c);printf("%d\n", z);}



例:建立动态链表

参考 书上P313
#include<stdio.h>#include<stdlib.h>#define LEN sizeof(struct Student)//这句话说以后的LEN都是Student类型 的长度struct Student//自己定义的stu类型{int num;struct Student *next;};int n;struct Student *creat()//此函数返回值为指向链表头的指针{struct Student *head;struct Student *p1,*p2;n = 0;p1 = p2 = (struct Student *)malloc(LEN);//(……)是强制转换类型运算符,就把malloc开辟出LEN长的地方变为struct Student *类型printf("请输入学号(以0结束) 如  10\n");scanf("%d", &p1->num);getchar();head = NULL;while (p1->num != 0)//只要学号输入不是0,可以无限延展{n = n + 1;if (n == 1) head = p1;//p1所记录的为链表头【仅第一次】else p2->next = p1;//p2的下一个指向【将要】新输入的p1的地址========p2 = p1;//p2指向【现在】p1的地址=================================p1 = (struct Student *)malloc(LEN);//p1搞了个【新】地址,p2记得就是刚才p1所在的地址了,p1“延展了”printf("请输入学号(以0结束) 如  10\n");scanf("%d", &p1->num);getchar();}p2->next = NULL;//链表结束了return head;//返回值为指向链表头的指针}int main(){struct Student *pt;pt = creat();//pt指向creat函数运行完后的“head”地址while (pt != NULL)//输出链表元素,直至尽头{printf("\n num:%d", pt->num);pt = pt->next;//当前“读指针”,指向下一个}return 0;}//参照自P313,谭浩强《C程序设计》第四版