C语言~指针进阶(1)
一维数组指针:
数组名:可以代表首地址,那么咱们就可以用指针指向数组。
虽然数组名可以代表一个元素首地址,但是它是个常量,不能自增或者自减!但是可以创建一个指针指向数组,然后++。
int arr[10];
arr++; // error E0137 表达式必须是可修改的左值 // error C2105 “++”需要左值printf("%p \n", arr); //1 004FF810,代表第一个元素地址
printf("%p \n", &arr);//2 004FF810,代表整个数组 1,2的值一样但是意义完全不同
printf("%p \n", arr + 1); //3 004FF814 跳过一个元素
printf("%p \n", &arr + 1);//4 004FF9A0 跳过了一个数组
int arr[6] = {0,1,2,3,4,5};
//p是个指针变量,可以任意操作 &arr[0]==arr
int* p = &arr[0];
p++;
printf("%d", *(p++));//输出结果:1
//&arr的类型是:int (*)[6]指向整个一维数组的类型
int a = &arr;//error:C2440 “初始化” : 无法从“int(*)[6]”转换为“int”
int(*pp)[6] = &arr; //正确的做法
二维数组指针:
//定义一个二维数组int map[5][2] = { 1,2,3,4,5,6,7,8,9,10 };//定义指针指向二维数组//int a = ↦ //error: C2440 “初始化” : 无法从“int(*)[5][2]”转换为“int”int(*p)[2] = ↦//(*p)为了让p先于*结合,成为一个指针,[2]是二维数组列数
p+1得到的是map[1]地址,因为map[1]里包含map[1][0],map[1][1] 所以不能直接*(p+1)来获取数值,
只能**(p+1)来获取
//p+1==map[1] map[1][0]==**(p+1)
printf("\n%d", *(p + 1));//输出结果:4585576 /*警告 C6273 传递了一个非整数作为_Param_(2),而对“printf”的调用需要一个整数,实际类型: “int[2]” : 如果当前传递的是一个指针值,则应使用 % p */
printf("\n%d", **(p + 1));//输出结果:3 等价于(*(p+1))[0]
printf("\n%d", map[1][1]);//4
printf("\n%d", (*(map + 1))[1]);//4 map+1==&map[1] *(p+1)==map[1]第一个元素首地址 (*(p+1))[1]==(*(map+1))[1]
printf("\n%d", (**(map + 1))+1);//4
内存四区:
1.栈区:放在栈区的变量,生命周期结束自动释放内存 例如:int age=3;
2.堆区:需要手动申请,需要手动释放,如果忘记释放就会导致内存泄漏
3.全局区:静态变量 全局变量 常量(不是const定义的)
4.代码区:代码,二进制代码
int num = 0;//栈区const double p = 3.14;//栈区static aa = 0;//全局区char arr[] = "hello";//栈区"hello";//全局区(常量区)printf("%p %p", arr, "helllo");//输出结果:007FFB9C 00F67BCC
动态内存分配:
malloc:
//动态内存分配,在堆区int* pa = (int*)malloc(sizeof(int));//防御性编程if(pa == NULL){return -1;//如果申请失败返回-1}//使用*pa = 18;printf("%d", *pa);//输出结果:18//不要改变pa指向,如果改变了,释放就会出错,内存会泄露,后果很严重(*pa)++;printf("\n%d", *pa);//输出结果:19//如果实在改变了要在释放内存前恢复原样再释放(*pa)--;//释放内存free(pa);pa = NULL;//释放后再置空,后面再使用这个内存就会报错危险:使用了释放了的内存//*pa = 6666;//printf("\n%d", *pa);
realloc:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define BABY_NUM 61
int main()
{//定义一个数组存储所有同学年龄//int ages[61];//虽然这样也可以,但是不够灵活,要是同学少于61则浪费内存,多余61数组又不够大int* ages = (int*)malloc(sizeof(int)* BABY_NUM);if (!ages){return -1;}for (int i = 0; i < BABY_NUM; i++){*(ages + i) = 19;printf("%d\n", ages[i]);}printf("\n");//怎么调整大小?realloc传进去的内存已经释放掉了,返回的是新的内存地址int* Newages = (int*)realloc(ages, sizeof(int) * 59);if (!Newages){Newages = ages;//free(ages);return -2;}for (int j = 0; j < 59; j++){printf("%d", Newages[j]);}free(Newages);return 0;
}
calloc:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
int main()
{int capacity = 10;//容量int* pa = (int*)malloc(sizeof(int) * capacity);//malloc不会自动初始化memset(pa, 0, sizeof(int) * capacity);//清空数组内存for (int i = 0; i < capacity; i++){printf("%d", pa[i]);//如果不用memset输出结果:-842150451-842150451...垃圾值}printf("\n");int* pa2 = (int*)calloc(capacity, sizeof(int));//calloc自动初始化为0for (int i = 0; i < capacity; i++){printf("%d ", pa2[i]);//输出结果:0 0 0 0 0 0 0 0 0 0}//别忘了释放置空free(pa);pa = NULL;free(pa2);pa2 = NULL;return 0;
}
指针数组:
//指针数组//数组里的元素都是int型指针int* arr[5] = { NULL };for (int i = 0; i < 5; i++){arr[i] = (int*)calloc(5, sizeof(int));for (int j = 0; j < 5; j++){arr[i][j] = j;}}for (int i = 0; i < 5; i++){for (int j = 0; j < 5; j++){printf("%d ", **(arr+1)+j);}printf("\n");}for (int i = 0; i < 5; i++){free(arr[i]);}
C语言~指针进阶(1)相关推荐
- C语言指针进阶(2)
上一篇一起探讨了指针进阶的字符指针.指针数组和数组指针.这一篇我们继续来学习C语言指针进阶的第二部分,主要内容包括数组传参和指针传参.函数指针和函数指针数组. 目录 数组传参.指针传参 一维数组传参 ...
- 解密英文藏头诗C语言,《C语言指针进阶》PPT课件.ppt
2020年3月26日 第1页 第11章指针进阶 2020年3月26日 第2页 本章要点 指针数组和指向指针的指针是如何被定义和使用的 指针如何作为函数的返回值 指向函数的指针的意义是什么 什么是结构的 ...
- C进阶_C语言_函数与指针_C语言指针进阶
上一篇博客http://t.csdn.cn/GYCiM 我们了解了指针相关知识,今天来了解函数和指针的关系. 目录 函数指针 函数指针数组 指向函数指针数组的指针 回调函数 qsort 冒泡排序模拟实 ...
- 带你刷笔试关的小怪|详解指针习题和面试题【C语言/指针/进阶】
文章目录 前言 9. 指针和数组笔试题解析 复习回顾 一维数组 字符数组 二维数组 10. 指针笔试题 笔试题1: 笔试题2 笔试题3 笔试题4 笔试题5 笔试题6 笔试题7 (#)笔试题8 结语 前 ...
- C语言指针进阶(1.一阶与二阶指针)
目录 一.一阶指针与二阶指针 一.一阶指针 二.二阶指针以及高阶指针 一.一阶指针与二阶指针 一.一阶指针 字符指针char*,浮点指针double* 等等类比 整数指针 int* 1.指针是用来存取 ...
- C语言———指针进阶3
目录 6.函数指针数组: 7.指向函数指针数组的指针: 8..回调函数 : 6.函数指针数组: 函数指针数组是存放函数指针的数组,数组中每个元素的类型都是函数指针类型. 因为,Add是加法函数,,Su ...
- 字符指针?指针数组?数组指针?《C语言指针进阶第一重奏》
目录 一.字符指针 1.1字符指针的认识 1.2字符指针存放字符串 1.3字符指针的使用 二.指针数组 2.1指针数组的认识 三.数组指针 3.1数组指针的认识 3.2数组名和&数组名的区别 ...
- C语言指针进阶(中)
提示: 上集内容小复习
- C语言——指针(进阶版)
目录 指针的进阶 1.字符指针 2.指针数组 3.数组指针 3.1 数组指针的定义 3.2数组指针的使用 4.动态内存分配与指向它的指针变量 4.1 什 ...
最新文章
- JavaScript创建对象的方法
- matlan数据分析库函数
- js操作DOM对象(节点的增删改)
- python观察日志(part21)--ord,chr,unichr方法的联系与区别
- CF198D Cube Snake(三维空间/增量构造)
- 数据库连接池的作用及c3p0的详解(转载他人的--合理掌握学习方式)
- Support Web Application Projects
- Java经典设计模式(1):五大创建型模式(附实例和详解)
- java企业绩效_员工绩效管理系统,基于SSM框架下的JAVA系统
- CSRF和SSRF漏洞
- 【京东】scrapy爬虫抓取京东图书详情、评论
- java gmail邮箱_Java - 谷歌邮箱发送邮件详解
- 让吹牛都能全世界最棒
- 计算机网络技术个人简历范文,计算机网络技术专业个人简历自我评价范文
- 太极图形课-01-Taichi编程
- 英语六级(包含作文)
- 很不错的免费电影网站中国影视库mdbchina.com
- 《程序员的修炼——从优秀到卓越》读书笔记
- Linux云计算网络服务CentOS7.5
- 【U8+】用友U8试算UFO报表后,显示#公式错误;并且函数向导中没有用友账务函数。