指针的自增操作
查看数组与指针的关系
#include <iostream>
using namespace std;
int main() {
int ages[] = { 18, 20, 22, 25, 28 };
int len = sizeof(ages) / sizeof(ages[0]);
cout << "使用数组的方式访问元素" << endl;
for (int i = 0; i < len; i++) {
cout << "第" << i + 1 << "个年龄是:" << ages[i] << endl;
}
cout << "使用指针的方式访问元素" << endl;
int* p = ages;
for (int i = 0; i < len; i++) {
cout << "第" << i + 1 << "个年龄是:" << *p << endl;
p++;
}
cout << "打印数组的地址 和 第一个成员的地址" << endl;
cout << &ages << " " << &ages[0] << endl;
return 0;
}
我们来探究下 指针自增操作
我们知道数组都是连续的内存组成的,如果说是int类型的话 ,第一块内存占四个字节 ,第二块占四个字节 ,所以说 我们地址访问的时候 是按照四个四个字节增加(int) , 但是为什么指针p是++就可以了呢,原因是 编译器做了优化 p++ 是 p = p + sizeof(int) * 1 也就是自动帮我们计算了int的字节,然后自增到p上面。
可以看到地址都是以4个字节递增的
练习一:让用户输入一个字符串,然后反向输出,注意:不能改变原来的字符串
第一种方法:
#include <iostream>
using namespace std;
#define MAX_SIZE 100
int main() {
char str[MAX_SIZE];
scanf_s("%s", str, MAX_SIZE);
int len = strlen(str);
for (int i = 0; i < len / 2; i++) {
char temp = str[i];
str[i] = str[len - i - 1];
str[len - i - 1] = temp;
}
printf("%s", str);
return 0;
}
第二种方法:
#include <iostream>
using namespace std;
#define MAX_SIZE 100
int main() {
char str[MAX_SIZE];
scanf_s("%s", str, MAX_SIZE);
int len = strlen(str);
for(int i = 0 ; i < len ; i ++ )
printf("%c", str[len - 1 - i]);
return 0;
}
第三种方法:
#include <iostream>
using namespace std;
#define MAX_SIZE 100
int main() {
char str[MAX_SIZE];
scanf_s("%s", str, MAX_SIZE);
int len = strlen(str);
char* p = &str[len - 1];
for(int i = 0 ; i < len ; i ++ )
printf("%c", *p--);
return 0;
}
指针与整数的加减
1)指针与整数的运算,指针加减数字表示的意义是指针在数组中位置的移动:对于整数部分而言,它代表的是一个元素,对于不同的数据类型,其数组的元素占用的字节是不一样的,
比如指针 +1,并不是在指针地址的基础之上加1个地址,而是在这个指针地址的基础上加1个元素占用的字节数:
如果指针的类型是char*,那么这个时候1代表1个字节地址;如果指针的类型是int*,那么这个时候1代表4个字节地址;如果指针的类型是 foat*,那么这个时候1代表4个字节地址;如果指针的类型是 double*,那么这个时候1代表8个字节地址。
const和指针
int a = 1;
const int * p = &a;
上面的 const int *p = &a; 代表了 常量指针, const关键字代表了告诉编译器,通过这个指针所访问的数据不能被修改。在这个例子中,int
前面的 const
表示这个指针指向的整数是只读的,不能通过该指针来改变它的值。
int numbers = 10 , numbers2 = 20;
const int *ptr = &numbers;
//修改指针指向的地址
ptr = &numbers2;
//修改执政指向的地址的值
*ptr = 30;
int a = 1;
int * const p = &a;
int numbers = 10 , numbers2 = 20;
int * const ptr = &numbers;
//修改指针指向的地址
ptr = &numbers2;
//修改执政指向的地址的值
*ptr = 30;
我们进行一下总结
const int * p = &a; 可以改变所指向的地址 但是不能改变所指向地址的值
int* const p = &a; 可以改变所指向地址的值 但是不能改变所指向的地址
看const 离类型(int)近,还是离指针变量名近,离谁近,就修饰谁,谁就不能变
二级指针
二级指针也是普通的指针变量,只不过二级指针能够访问的值*ptr 是一个地址。
#include <iostream>
using namespace std;
int main() {
//柜子2的值是100
int guizi2 = 100;
//柜子1的值存的是柜子2的地址
int *guizi1 = &guizi2;
//张三的值是柜子1的地址
int** zhangsan = &guizi1;
cout << "柜子2的值:" << guizi2 << " 柜子2本身的地址:" << &guizi2 << endl;
cout << "柜子1的值:" << guizi1 << " 柜子1本身的地址:" << &guizi1 << endl;
cout << "张三的值:" << zhangsan << " 张三本身的地址:" << &zhangsan << endl;
return 0;
}
我们把上面打印出来的值进行一个整理
二级指针的用途
一级指针和二级指针
一级指针:当你有一个指针指向一个变量的内存地址时,这被称为一级指针。当你把一个变量的地址(也就是指针)作为参数传递给一个函数时,你可以在该函数内部修改这个变量的值,并且这个改变会影响到原始数据,因为你是直接操作的内存地址。但是,当函数执行完毕后,你在函数内部创建的任何局部变量都无法通过这个指针带出函数外使用。
void updateNum(int *p) {
*p = 20; // 通过 p 修改了 p 指向的值,即 num
}
上面可以通过传入一个指针,修改指针指向的值。但是p指向一个局部变量的时候,当作用域结束后,localVal被清理掉 p指向了一个垃圾地址。
void badFunction(int *p) {
int localVar = 30; // 局部变量
p = &localVar; // 尝试修改 p 指向局部变量
}
调用 badFunction(&num);
这样做是无效的,因为 localVar 在函数结束时不再存在
我们再举一个例子,我们传入一个指针 让指针指向局部的静态变量,然后打印值,这种报错了,局部变量的地址一旦传递出其所在的作用域就变得无效。因此,当 boy_home
返回后,试图使用 p
是未定义的行为。
简化一下:因为p指针传入的是一个副本 也就是形参的p和实参的p是两个不同的变量 所以说 p=&count 是形参的变量的值赋值为count的地址 但是外面的还是NULL
#include <iostream>
using namespace std;
void boy_home(int* p) {
static int count = 23;
p = &count;
}
int main() {
int* p = NULL;
boy_home(p);
cout << "p = " << *p << endl;
}
所以我们必须使用二级指针 也就是说 int** p 接受的是形参一级指针p的地址 也就是说**p的指针可以访问到实参的一级指针,使用*p访问到实参的一级指针。
#include <iostream>
using namespace std;
void boy_home(int** p) {
static int count = 23;
*p = &count;
}
int main() {
int* p = NULL;
boy_home(&p);
cout << "p = " << *p << endl;
}
下面是二级指针的另外一个例子
#include <iostream>
#include <stdlib.h>
using namespace std;
void goodFunction(int **p) {
int* localPtr = (int*)malloc(sizeof(int));
if (localPtr == NULL) {
cout << "Memory allocation failed" << endl;
exit(1);
}
*localPtr = 100;
*p = localPtr;
}
int main() {
int* num = NULL;
goodFunction(&num);
if (num != NULL) {
cout << "The value of num is " << *num << endl;
free(num);
}
return 0;
}
标签:const,int,C++,路线,地址,len,str,十四,指针
From: https://blog.csdn.net/weixin_45169583/article/details/142915481