c++中傳遞字符指針容易犯的錯誤

先看一段容易犯錯的代碼段:

#include<iostream>
using namespace std;
char* GetMe()
{
	char st[]="hello word!";
	return st;
	
}
int main()
{
	char *str;
	str=GetMe();
	cout<<str<<endl;
	return 0;
}

該段代碼可能輸出正確結果,也可能輸出錯誤結果。原因是:GetMe函數中的str是局部變量,分配的是局部數組,他是在內存中的棧中申請的空間,超出該函數作用域之後st的內存空間就會被收回,雖然返回的指針仍然指向該內存空間,但是空間中的值隨時有可能會被改變,所以輸出的有可能是錯誤結果。修改的方法一種是在全局區域申請內存空間,一種是在堆中申請內存空間。先看在內存的全局區域申請內存空間的代碼,至於在堆區分配內存有關文章已經講了,不再贅述:

#include<iostream>
using namespace std;
const char* GetMe()
{
	char *st="hello word!";
	//*st='t';
	return st;
	
}
int main()
{
	const char *str;
	str=GetMe();
	cout<<str<<endl;
	return 0;
}


char *st=“hello word!”與上一段代碼中的char st[]="hello word!"的區別是char *st=“hello word!”是在內存的全局區域申請的內存空間,全局區域的值是不能進行修改的。如代碼中被註釋起來的那一行,如果去掉註釋,雖然編譯時沒錯誤,但是運行時程序就會崩潰,因爲修改了全局區域的值。所以在全局區域定義了變量之後,該值在程序結束之前是不會被改變的。另外需要普及的常識就是:

程序用來存放數據 的內存分爲四塊:

1、全局區(靜態區):全局變量和靜態變量存儲的地方,它與其他變量的不同之處就是生命週期的不同,全局區的變量只有在程序結束時系統纔會釋放該塊資源。

2、文字常量區:常量字符串存放的地方。它也是在程序結束時釋放。

3、棧區:存放函數的參數值,局部變量值等,進入區域分配內存,超出區域收回內存。

4、堆區:程序員分配程序員釋放。

當然了該題目也可以通過開闢一段靜態內存區來實現,它與全局區是同一塊內存,只是代碼表示方式不同:

#include<iostream>
using namespace std;
const char* GetMe()
{
	static char st[]="hello word!";
	//*st='t';
	return st;
	
}
int main()
{
	const char *str;
	str=GetMe();
	cout<<str<<endl;
	return 0;
}


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章