[C++]テンプレート(下記)


1. typename の使用

テンプレート パラメーターを使用するときにクラスを使用することも、テンプレート パラメーターを定義するために typename を使用することもできます。typename に新しい役割が追加されました。

template<class container>
void Print(const container& v)
{
    
    
	//编译器不确定Container::const_iterator是类型还是对象
	//没有实例化的类模板,需要使用typename明确告诉编译器container是一个类型,否则编译器报错
	typename container::const_iterator it = v.begin();
	//也可使用auto  auto it=v.begin();
	while (it != v.end())
	{
    
    
		cout << *it << " ";
		it++;
	}
	cout << endl;
}

2. 非型テンプレートパラメータ

テンプレート パラメーターは、型パラメーターを非型パラメーターに分類します。

タイプ パラメータ: テンプレート パラメータ リストに表示され、その後にクラスやタイプ名などのパラメータ タイプ名が続きます。

非型パラメータ: クラス(関数)テンプレートのパラメータとして定数を使用することであり、そのパラメータはクラス(関数)テンプレート内で定数として使用できます。

例:

#define _CRT_SECURE_NO_WARNINGS 1
#include<iostream>
#include<vector>
#include<list>
#include<array>
using namespace std;

//静态栈
//非类型模板参数
//1.常量
//2.必须是整形,不可在类中修改
template<class T,size_t N=10>   
class Stack
{
    
    
public:
	void func()
	{
    
    
		//常量,不可修改
		//N = 10;
	}
private:
	T _a[N];
	int _top;
};

int main()
{
    
    
	Stack<int, 10> st1;
	Stack<int, 100> st2;

	//st1.func();

	//非类型模板参数使用   定长数组  C++11
	//array只有一个优势,越界检查严格
	array<int,10> a;
	for (auto e : a)
	{
    
    
		cout << e << " ";
	}
	cout << endl;

	return 0;
}

型以外のテンプレート パラメーター、配列 - 固定長配列を使用して新しいコンテナーを実装しました

3. テンプレートの特化

1.コンセプト

通常、テンプレートを使用して型に依存しないコードを実装できますが、一部の特殊な型では、誤った結果が得られる可能性があり、特別な処理が必要になります。たとえば、以下の比較に特別に使用される関数テンプレートを実装します。

namespace tzc
{
    
    
	template<class T>
	bool less(T a, T b)
	{
    
    
		return a < b;
	}
}
 
int main()
{
    
    
	int a = 10;
	int b = 20;
	int* c = &a;
	int* d = &b;
	cout << tzc::less(a, b) << endl;
	cout << tzc::less(c, d) << endl; // 传入指针 ,只会比较指针
	return 0;
}

ここに画像の説明を挿入

2つの変数の大小を比較する関数テンプレートを実装しましたが、比較の種類が限られており、ポインタ型の変数を渡した場合、大小比較の結果が意図したものにならないことがよくあります。関数テンプレートを実装する必要があります。特殊なケースを処理するための特殊化

2. テンプレートの機能特化

関数テンプレートの特殊化手順:
1. 最初に基本的な関数テンプレートが必要です
2. キーワード テンプレートの後には空の山かっこ <> が続きます
3. 関数名の後には山括弧のペアが続きます。特殊化の必要性を指定します。 4. 関数
パラメータ テーブル: テンプレート関数の基本パラメータ タイプとまったく同じである必要があります。異なる場合、コンパイラが奇妙なエラーを報告する可能性があります。

//函数模板
template<class T>
bool Less(T left, T right)
{
    
    
	return left < right;
}

//函数模板的特化    也可重载
//这种只能解决int类型的问题
template<>
bool Less<int*>(int* left, int* right)
{
    
    
	return *left < *right;
}
//解决各种指针类型的比较,
template<class T>
bool Less(T* left, T* right)
{
    
    
	return *left < *right;
}

int main()
{
    
    
	cout << Less(1, 2) << endl;

	int a = 1, b = 2;
	cout << Less(&a, &b) << endl;
	return 0;
}

3. クラスのテンプレートの特殊化

① 全特化

//类模板
template<class T1,class T2>
class Date
{
    
    
public:
	Date() {
    
     cout << "Date<T1 ,T2>" << endl; }
private:
	T1 _d1;
	T2 _d2;
};

//全特化
template<>
class Date<int ,double>
{
    
    
public:
	Date() {
    
     cout << "Date<int,double>" << endl; }
};

int main()
{
    
    
	Date<int, int> d1;
	Date<int, double>d2;
	return 0;
}

ここに画像の説明を挿入

②部分専門化

//类模板
template<class T1,class T2>
class Date
{
    
    
public:
	Date() {
    
     cout << "Date<T1 ,T2>" << endl; }
private:
	T1 _d1;
	T2 _d2;
};

//偏特化,特化部分参数
template<class T>
class Date<T,double>
{
    
    
public:
	Date() {
    
     cout << "Date<T,double>" << endl; }
};

//偏特化,对某些类型进行进一步特化
template<class T1,class T2>
class Date<T1*,T2*>
{
    
    
public:
	Date() {
    
     cout << "Date<T*,T*>" << endl; }
};

int main()
{
    
    
	Date<double, double>d3;
	Date<int*, int*>d4;
	Date<double*, double*>d5;
	return 0;
}

ここに画像の説明を挿入

おすすめ

転載: blog.csdn.net/Tianzhenchuan/article/details/131856029