1. 程式人生 > 其它 >2.c++_基礎_地址和引用

2.c++_基礎_地址和引用

技術標籤:初中物理c++

一、指標

  1. 指標的定義
    int a = 10;
	// 指標定義的語法;資料型別 * 指標變數
	int* p;

	// 讓指標記錄變數a的地址
	p = &a;
	cout << "a的地址為:" << &a << endl;
	cout << "指標p為:" << p << endl;
  1. 使用指標
	// 可以通過解引用的方式找到指標指向的記憶體
	// 指標前加 * 代表解引用,找到指標指向的記憶體中的資料
	*p = 1000;
	cout <<
"a = " << a << endl; cout << "*p = " << *p << endl;
  1. 指標佔用空間
cout << "sizeof (int *)" << sizeof(int*) << endl;
cout << "sizeof (float *)" << sizeof(float*) << endl;
cout << "sizeof (double *)"
<< sizeof(double*) << endl; cout << "sizeof (char *)" << sizeof(char*) << endl;
  1. 空指標 記憶體編號為0-255系統佔用記憶體
// 空指標
int * p3 = NULL;
// cout << *p3 << endl;  報錯,記憶體編號為0-255系統佔用記憶體,
// *p3 = 100; 報錯,不允許使用者訪問
  1. 野指標,指標指向非法的記憶體空間,沒有申請的記憶體空間是非法記憶體空間
	int * p4 = (int*)
0x1100; // 0x1100這個空間還沒有申請就訪問,會報錯 // cout << *p4 << endl;
  1. 結構體指標,結構體指標操作屬性寫法
stu->age
void printStudent(const Student* stu)
{
	// stu->age = 100; 操作失敗,因為加了const
	cout << "姓名:" << stu->name << "年齡:" << stu->age << "分數:" << stu->score << endl;
}
  1. const修飾地址或常量
int a = 10;
int b = 10;

指標指向的值不能改,指標的指向可以改。eg:

const int* p = &a;
// *p = 20;  錯誤,指標指向的值不能改
p = &b; // 正確

指標的指向不可以改,指標指向的值可以改。eg:

int* const p2 = &a;
// p2 = &b; // 錯誤
*p2 = 20;

指標的指向和指標指向的值 都不可以改

const int* const p3 = &a;
//*p3 = 100; 錯誤
//p3 = &b;   錯誤
  1. 指標運算元組
// 4. 指標和陣列
	int arr[] = { 1,2,3,4,5 };

	int* p4 = arr;

	cout << "第一個元素:" << arr[0] << endl;        
	cout << "指標訪問的第一個元素 " << *p << endl;   

	for (int i = 0; i < 5; i++)
	{
		// 利用指標遍歷陣列
		cout << *p4 << endl;
		p4++;
	}
int main() {
	int* arr = new int[10];

	for (int i = 0; i < 10; i++) {
		arr[i] = i + 100;
	}

	for (int i = 0; i < 10; i++)
	{
		cout << arr[i] << endl; 
	}

	delete[] arr;

	return 0;
}
  1. new生成的變數,其記憶體空間不會被釋放,直到視窗被關閉,即程式碼
int main() {

	int* p = func_2();

	cout << *p << endl; // 10 
	cout << *p << endl; // 10 
	cout << *p << endl; // 10 
	
	delete p;
	// cout << *p << endl; // 錯誤,delete p, p已經釋放了記憶體

	return 0;
}

二、引用

  1. 資料型別 &別名 = 原名
int a = 10;
int &b = a;
  1. 引用就是地址值不能修改的地址,必須初始化,初始化後不能更改,所以也是地址傳遞。

自動轉換為 int* const ref = &a;

void func(int& ref)
{
	ref = 100;
}
int main()
{
	int a = 10;

	// 自動轉換為 int* const ref = &a; 指標常量指標指向不可改,所以引用不能改
	int& ref = a;
	ref = 20; // 內部發現ref是引用,自動幫我們轉換 *ref = 20;

	cout << "a: " << a << endl;  // 20 
	cout << "ref: " << ref << endl;  // 20

	func(a);
	return 0;
}
void swap01(int a, int b)
{
	int temp = a;
	a = b;
	b = temp;
}

void swap02(int *a, int *b)
{
	int temp = *a;
	*a = *b;
	*b = temp;
}

void swap03(int &a, int &b)
{
	int temp = a;
	a = b;
	b = temp;
}
int main() {

	int a = 10;
	int &b = a;  // 資料型別 &別名 = 原名  

	cout << "a = " << a << endl;
	cout << "b = " << b << endl;

	b = 100;

	cout << "a = " << a << endl;
	cout << "b = " << b << endl;

	// 1.引用必須初始化
	// int& b; 錯誤,必須初始化
	// 2.引用在初始化後,不可以改變
	
	// 3. 通過引用引數產生的效果同地址傳遞是一樣的

	int c = 10;
	int d = 20;

	//swap01(c, d);
	//swap02(&c, &d);
	swap03(c, d);

	cout << "c = " << c << endl;
	cout << "d = " << d << endl;

	return 0;
}
  1. 區域性引用不能作為函式返回值,因為區域性引用在函式呼叫後,其指向的記憶體資料就會被刪除。若被static修飾,不會被刪除
int& test01()
{
	int a = 10;
	return a;
}
int& test02()
{
	static int a = 20;
	return a;
}

int main()
{
	int& ref = test01();
	// 1.區域性引用不能作為函式返回值,因為區域性引用在函式呼叫後,其指向的記憶體資料就會被刪除
	cout << "ref= " << ref << endl; // 10
	cout << "ref= " << ref << endl; // 2049755664

	int& ref2 = test02();
	cout << "ref2= " << ref2 << endl; // 20
	cout << "ref2= " << ref2 << endl; // 20
	
	return 0;
}
  1. 引用(別名)可以做左值
// 2.引用(別名)可以做左值
	test02() = 1000;

	cout << "ref2= " << ref2 << endl; // 1000
	cout << "ref2= " << ref2 << endl; // 1000
  1. 為防止傳到函式中的引用發生變化,有const修飾引用
void showValue(const int& val)
{
	// val = 1000; // 加上const 
	cout << "val = " << val << endl;
}