zl程序教程

您现在的位置是:首页 >  后端

当前栏目

C++系列笔记(八)

C++笔记 系列
2023-06-13 09:11:25 时间

导读】《21天学通C++》这本书通过大量精小短悍的程序详细而全面的阐述了C++的基本概念和技术,包括管理输入/输出、循环和数组、面向对象编程、模板、使用标准模板库以及创建C++应用程序等。这些内容被组织成结构合理、联系紧密的章节,每章都可在1小时内阅读完毕,都提供了示例程序清单,并辅以示例输出和代码分析,以阐述该章介绍的主题。本文是系列笔记的第八篇,欢迎各位阅读指正!

模板简介

模板声明以关键字template打头,接下来是类型参数列表。这种声明的格式template <parameter list>示例代码如下:

#include<iostream>
#include<string>
using namespace std;
template <typename Type>
const Type& GetMax(const Type& value1, const Type& value2)
{
        if (value1 > value2)
               return value1;
        else
               return value2;
}
template <typename Type>
void Displaycomparison(const Type& value1, const Type& value2)
{
        cout << "GetMax(" << value1 << "," << value2 << ")=";
        cout << GetMax(value1, value2) << endl;
}
int main()
{
        int a1 = -101, int a2 = 2011;
        Displaycomparison(a1, a2);
        double d1 = 3.14, double d2 = 3.1415926;
        Displaycomparison(d1, d2);
        string Name1("Jack"), Name2("john");
        Displaycomparison(Name1, Name2);
        return 0;
}

模板函数不仅可以重用(就像宏函数一样),而且更容易编写和维护,还是类型安全的。请注意,调用Displaycomparison时,也可显式地指定类型,如下所示: Displaycomparison<int>(Int1,Int2); 然而,调用模板函数时没有必要这样做。您无需指定模板参数的类型,因为编译器能够自动推断出类型;但使用模板类时,需要这样做。

模板类

模板类是模板化的 C++类,是蓝图的蓝图。使用模板类时,可指定要为哪种类型具体化类。这让您能够创建不同的Human对象,即有的年龄存储在 long long成员中,有的存储在 int成员中,还有的存储在short成员中。对于模板,术语实例化的含义稍有不同。用于类时,实例化通常指的是根据类创建对象。但用于模板时,实例化指的是根据模板声明以及一个或多个参数创建特定的类型。对于下面的模板声明:

template <typename T>
class TemplateClass
{
    T m_member;
};

使用模板是将这样编写代码

TemplateClass <int> IntTemplate;

这种实例化创建的特定类型称为具体化。

声明包含多个参数的模板

如下面代码所示:

template <typename T1, typename T2>
class HoldsPair
{
private:
    T1 Value1;
    T2 Value2;
public:
    HoldsPair(const T1& value1,const T2& value2)
    {
        Value1=value1;
        Value2=value2;
    }
    //other function declarations
};

实例化如下:

HoldsPair<int,double> pairIntDouble(6,1.99);
HoldsPair<int,int> pairIntDouble(6,500);

包含默认参数的模板

template <typename T1=int,typename T2=int>
class HoldsPair
{
    //……method declare
};

实例化可简写为:

HoldsPair <> PairIntDouble(6,500);

实例代码如下:

#include<iostream>
using namespace std;
template <typename T1=int,typename T2=double>
class HoldsPair
{
private:
        T1 Value1;
        T2 Value2;
public:
        HoldsPair(const T1& value1, const T2& value2)
        {
               Value1 = value1;
               Value2 = value2;
        };
        const T1 & GetFirstvalue() const
        {
               return Value1;
        };
        const T2& GetSecondvalue() const
        {
               return Value2;
        };
};
int main()
{
        HoldsPair<> mIntFloatPair(300, 10.09);
        HoldsPair<short,const char*> mshortstringPair(25, "learn template,love c++");
        cout << "the first object conntains-" << endl;
        cout << "Value 1:" << mIntFloatPair.GetFirstvalue() << endl;
       cout << "Value 2:" << mIntFloatPair.GetSecondvalue() << endl;
        cout << "the second object contains-:" << endl;
       cout << "Value 1:" << mshortstringPair.GetFirstvalue() << endl;
       cout << "Value 2:" << mshortstringPair.GetSecondvalue() << endl;
        return 0;
}

输出为:

the first object conntains-
Value 1:300
Value 2:10.09
the second object contains-:
Value 1:25
Value 2:learn template,love c++

模板类和静态成员

实例代码如下:

#include<iostream>
using namespace std;
template <typename T>
class TestStatic
{
public:
        static int StaticValue;
};
template<typename T> int TestStatic<T>::StaticValue;
int main()
{
        TestStatic<int> Int_Year;
        cout << "setting staticvalue for Int_Year to 2011" << endl;
        Int_Year.StaticValue = 2011;
        TestStatic<int> Int_2;
        TestStatic<double> Double_1;
        TestStatic<double> Double_2;
        cout << "setting staticvalue for Double_2 to 1011" << endl;
        Double_2.StaticValue = 1011;
        cout << "Int_2.StaticValue= " << Int_2.StaticValue << endl;
        cout << "Double_1.StaticValue= " << Double_1.StaticValue << endl;
        return 0;
}

输出为:

setting staticvalue for Int_Year to 2011
setting staticvalue for Double_2 to 1011
Int_2.StaticValue= 2011
Double_1.StaticValue= 1011

上述有一条程序初始化模板类的静态成员:template<typename T> int TestStatic<T>::StaticValue*对于模板类的静态成员,通用的初始化语法如下:

template<typename parameters> staticType ClassName<Template Arugments>::StaticVarName;

使用static_assert执行编译阶段检查

tatic_assert是C++11新增的一项功能,让您能够在不满足指定条件时禁止编译。语法如下: static_assert(expression being validated, "error message when check fails" 要禁止针对类型int实例化模板类,可使用static_assert(),并将sizeof(T)与sizeof(int)进行比较,如果它们相等,就显示一条错误消息:

static_assert(sizeof(T)!=sizeof(int), "No int please!");

示例代码如下

#include<iostream>
using namespace std;
template <typename T>
class everythingbutInt
{
public:
        everythingbutInt()
        {
               static_assert(sizeof(T) != sizeof(int), "Not int please!");
        }
};
int main()
{
        everythingbutInt<int> test;
        return 0;
}