1. 程式人生 > >C++函式學習

C++函式學習

1. 行內函數 inline和define

行內函數比常規函式執行速度更快,比define更安全。

常規函式呼叫記憶體中是跳來跳去的,行內函數是直接建立副本,順序執行,代價是記憶體浪費更多,define是巨集替換。

在不支援inline特性的環境下,經常使用define來達到類似的效果,如微控制器。

2.引用變數&、const、&&

常規函式是按值傳遞的,如在C語言中要修改引數的值只能通過指標來修改,在C++中新增加了&引用,直接訪問原值,而不是拷貝。

引用在效率上更高,用的記憶體更少(因為不用拷貝一次原來的值)。

當想使用引用又不希望引數值被改變時,可以使用const int&。

當引用的只希望是右值則可以使用&&

3.左值與右值

左值指的是可以通過地址修改的。

右值指的是不可以通過記憶體地址修改的。

int a=1+2;

a是左值,1+2是右值

int a=0,b=2;

a是左值,b+2是右值,因為b+2是產生一個臨時變數

4.return 和 return&

return 返回一個臨時複製的值

return & 返回引用值,即可以當左值。只可以返回一個存在的記憶體,而不能返回一個已經被銷燬的記憶體。

在效率和記憶體上和引數的引用一個原理。

5.引用主要原因有兩個

1.是可以修改原值

2.提高執行效率。

主要是用在佔據記憶體較大(和基本的資料型別比較的話)的類和資料結構。

6.函式過載

名稱相同,功能類似,引數列表不同的時候使用。

7.函式模板

演算法一樣,型別不一樣的時候使用。

模板的原理:

編譯器在編譯的時候會檢查模板的使用情況,建立不同的例項,程式執行過程中是沒有模板的。

當使用模板的時候不知道計算結果的型別時,可以使用decltype。會遍歷一個核對錶,選擇最適合的型別。

8.遞迴

函式本身呼叫自己來工作,直到遇到停止條件時停止工作。

9.函式指標

接下來是程式碼例項

#include<iostream>
using namespace std;
#define Squart(X) (X)*(X)
inline double squart(double a) { return a*a; }
struct person
{
	char name[20];
	int age;
	void setName(const char *);
	person();
	person(const char *n, int a);
	void show()
	{
		std::cout << "my name is " << name << " and i am " << age << (age == 1 ? " year" : " years") << " old" << endl;
	}
};
void person::setName(const char * n)
{
	int index = 0;
	do
	{
		name[index] = *(n + index);
	} while (n[index++]);
}
person::person()
{
	setName("Big ben");
	age = 20;
}
person::person(const char*n, int a)
{
	setName(n);
	age = a;
}
template<typename T>
void swap_(T &a, T& b)
{
	T temp = a;
	a = b;b = temp;
}
template<class T1,class T2>
void add(T1 A, T2 B)
{
	decltype(A+B) k = A + B;
	cout << k << endl;
}
int & inadd(int &result, const int &a, const int &b)
{
	result = a + b;
	return result;
}
int main() {
	double a = 0;
	cin >> a;
	cout << "define "<< Squart(a)<<endl;
	cout << "inline " << squart(a) << endl;
	person *p = new person("bai",30);
	p->show();
	p->setName("a little girl");
	p->show();
	int inta = 0,intb = 2;
	char cha = 'a', chb = 'b';
	cout << "int" << endl << inta << " " << intb << endl;
	swap_(inta, intb);
	cout << "int" << endl << inta << " " << intb << endl;

	cout << "char" << endl << cha << " " << chb << endl;
	swap_(cha, chb);
	cout << "char" << endl << cha << " " << chb << endl;

	add(1, 2);
	add(1.30, 5);
	add(1.000021, 1);
	int r = 0, m = 2, n = 1;
	inadd(r, m, n);
	cout << r << endl;
	inadd(r, m, n) += 2;
	cout << r << endl;
	return 0;
}

	

函式指標程式碼

#include<iostream>
using namespace std;
double add(double a, double b) { return a + b; }
double sub(double a, double b) { return a - b; }
double mul(double a, double b) { return a*b; }
double calculate(double a, double b, double(*p)(double c, double d)){	return (*p)(a, b);}
int main()
{
	double(*p[3])(double, double) = { add,sub,mul };
	double a, b;
	cout << "----------------------------------------- " << endl;
	cout << "a\tb\ta+b\ta-b\ta*b\t" << '|'<<endl;
	cout <<  "---------------------------------------" << endl;
	while (cin>>a>>b)
	{
		//system("cls");
		cout << a << '\t' << b ;
		for (int i = 0;i < 3;i++)
			cout << "\t" << calculate(a, b, p[i]);
		cout <<endl<<"---------------------------------------"<<endl;
	}
	return 0;
}

遞迴程式碼

#include<iostream>
using namespace std;
#define W 10
#define H 11
//int T = 0;
int mode[][2] = { {-1,1},{1,-1} };//0坐下1右上
int jz[H][W] = { {0} };
int out[H*W] = {};
int jz2[H][W] = { {0} };
int index = 0;
void Zcout(int m, int nx, int ny, int f, int &p)
{
	if (nx == 0 && ny == 0) p = 0;
	if (nx >= W || ny >= H) return;
	else jz[ny][nx] = p++;
	if (ny == 0 && nx % 2 != f && nx!=W-1){
		nx++;Zcout(!m, nx, ny,f,p);
	}
	else if (nx == 0 && ny % 2==f && ny !=H - 1){
		ny++;Zcout(!m, nx, ny, f,p);
	}
	else if (nx == W - 1 && ny%2==W%2+f){
		ny++;Zcout(!m, nx, ny, f, p);
	}
	else if (ny == H - 1 && nx % 2 != H % 2+f) {
		nx++;Zcout(!m, nx, ny, f, p);
	}
	else
	{	
		nx += mode[m][0];
		ny += mode[m][1];
		Zcout(m, nx, ny,f, p);
	}
}
void Zcin(int m, int nx, int ny, int f)
{
	if (index==W*H) return;
	else out[index++] = jz[ny][nx];
	if (ny == 0 && nx % 2 != f && nx != W - 1) {
		nx++;Zcin(!m, nx, ny, f);
	}
	else if (nx == 0 && ny % 2 == f && ny != H - 1) {
		ny++;Zcin(!m, nx, ny, f);
	}
	else if (nx == W - 1 && ny % 2 == W % 2 + f) {
		ny++;Zcin(!m, nx, ny, f);
	}
	else if (ny == H - 1 && nx % 2 != H % 2 + f) {
		nx++;Zcin(!m, nx, ny, f);
	}
	else
	{
		nx += mode[m][0];
		ny += mode[m][1];
		Zcin(m, nx, ny, f);
	}
}
int main()
{
	int k = 0;
	Zcout(0,0,0,0,k);//mode==f 1向上 0向下 
	for (int i = 0;i < H;i++)
	{
		for (int j = 0;j < W;j++)
			cout << jz[i][j] << "\t";
		cout << endl;
	}
	Zcin(0, 0, 0, 0);
	for (int i = 0;i < H*W;i++)
		cout << out[i] << " ";
	return 0;
}