C++基础——指针

C++基础——指针

  • 指针
    • 1 定义指针
    • 2 使用指针
    • 3 指针的内存空间
    • 4 空指针
    • 5 野指针
    • 6 常量指针
    • 7 指针常量
    • 8 指针访问数组
    • 9 指针数组
    • 10 数组指针
    • 11 指针作为函数形参
    • 12 双重指针用法

指针

通过指针可以间接地访问内存
int a = 2;
内存中地址0x006FFC4C存储了a变量的值2,我们通过a变量访问值2;也可以通过指针p存储a的地址0x006FFC4C,通过访问地址,再提取地址处的值。

1 定义指针

数据类型 *指针变量名
如:

int a = 2;
int *p;
p = &a; //取址
cout << "a地址为:" << &a << endl << p << endl; 

2 使用指针

解引用:使用*p读取p指向的地址处的数据

*p = 1000;
cout << a << endl << *p << endl;
--------------------
1000
1000
//使用指针p找到a的内存并修改了内容

3 指针的内存空间

指针存储的是某数据的地址,如0x006FFC4C,在32位OS中占4字节,64位中占8字节.x86即32位

sizeof(int*),sizeof(char*),sizeof(double*)…均为4字节即32位。

4 空指针

  1. 给指针变量进行初始化int *p = NULL;地址为0处。
  2. 空指针不能被访问*p = 100;会报错,p为空
  3. 0-255为系统分配地址,不可访问

5 野指针

指针指向非法内存空间
int *p = (int*)0x1100,访问权限受限,不能自己随意指定地址。

6 常量指针

被const修饰的指针变量,指针指向可以改变,但是指向的地址的数据不能改变。
int a = 11, b = 12; const int *p = &a;
const修饰的是*p
C++基础——指针_第1张图片*p = 13;错误!指向的地址0x1100处的数据11被const限制,不能改变。

p = &b;正确,p的指向由a地址变为b的地址。

7 指针常量

const修饰的是p
指针的指向不能改,但是指向的地址的数据可以改。
int* const p = &a;
*p = 13;正确
p = &b;错误

PS const int* const p = &a;
既修饰指针又修饰常量,指向和数据均不可改。

8 指针访问数组

	//x86中long long 是8字节
	long long a[6] = {1,2,3,4,5,6};
	long long* p = a;
	for (; p < a+6; p++) {
		cout << p << " " << *p << endl ;
	}
	--------------------------------------
	006FFAF8 1
	006FFB00 2
	006FFB08 3
	006FFB10 4
	006FFB18 5
	006FFB20 6

C++基础——指针_第2张图片
每一次p++,都会跳过8字节,*p即为下一个元素

9 指针数组

是一个数组,里面每一个元素是指针,保存着其他变量的地址。
int* a[6];
C++基础——指针_第3张图片


10 数组指针

也叫行指针,是一个指针,指向一个数组
int (*p)[10] p是一个指针,指向一个长度为10的整型的一维数组
ps: []优先级高于*,因此要加上()。

当用数组指针遍历二维数组时:

int arr[2][3] = {1,2,3,4,5,6};
int (*p)[3] = arr;
for (int i = 0; i < 2;i++, p++) {
		cout << p << endl;
}

p每次代表arr的一行,依次是arr[0],arr[1],每次p++都是跳过了arr的一行,即3个整型的空间。

11 指针作为函数形参

  • 值传递
void swap(int c, int d){
	int temp = c;
	c = d;
	d = temp;
}
int main(){
	int a = 1, b = 2;
	swap(a, b);
	cout << a << " " << b << endl;
}
-----------------------------------
1 2

此处将a,b的值传递给swap的形参,但是a,b实参的值不会随着c,d形参的值改变而改变
C++基础——指针_第4张图片

  • 地址传递
    地址传递可以修饰实参
void swap(int* c, int* d){
	int temp = *c;
	*c = *d;
	*d = temp;
}
int main(){
	int a = 1, b = 2;
	swap(&a, &b); //传递地址
	cout << a << " " << b << endl;
}
-----------------------------------
2 1

C++基础——指针_第5张图片

12 双重指针用法

双重指针指的是指向指针的指针。
首先预热一下

int a = 11;
int* p = &a;
int** p1 = &p;
cout << "p1 " << p1 << endl;
cout << "*p1 " << *p1 << endl;
cout << "p " << p << endl;
cout << "**p1 " << **p1 << endl;
cout << "*p " << *p << endl;
---------------------------
p1 0x2200
*p1 0x1100
p 0x1100
**p1 11
*p 11

C++基础——指针_第6张图片


双重指针与函数形参实参的例子:
函数modifyPointer实现将空指针num的指向一个新的分配空间(这可以直接进行指向但是为了练习双重指针,特意写了一个函数)

void modifyPointer(int* a){
	a = (int*)malloc(4);
}
int main(){
	int* num = NULL;
	modifyPointer(num);
	cout<<num<<" "<<*num;
}
----------------------------
报错,num 是 nullptr

C++基础——指针_第7张图片

分析:num空指针作为实参传递给形参指针a,这里是值传递,是将num的值0传递给a,然后a指向新分配的空间,即a的值为新地址,但是并没有改变num的指向。要通过形参改变实参num需要用双重指针:

void modifyPointer(int** a){
	*a = (int*)malloc(4);
}
int main(){
	int* num = NULL;
	modifyPointer(&num);
	cout<<num<<" "<<*num;
}
----------------------------
0x2200 -842150451
成功分配到地址

分析:双重指针a指向num指针,a赋值为新的分配空间地址,即num值为新的分配空间地址,所以num为新分配的int随机数。
C++基础——指针_第8张图片

你可能感兴趣的:(C++笔记,c++,指针)