当前位置: 首页 > wzjs >正文

惠州住房和城乡建设局网站品牌策划公司怎么找客户

惠州住房和城乡建设局网站,品牌策划公司怎么找客户,设计社交网站,手机网站设计企业写在前面 在阅读本篇笔记前,请各位看官先有泛型编程的基础,具体可以看不才前面写的博客:【C】模板上(泛型编程) —— 函数模板与类模板 文章目录 写在前面一、非类型模板参数二、模板的特化2.1、函数模板特化2.2、类模板特化2.2.1、全特化2.…

写在前面

在阅读本篇笔记前,请各位看官先有泛型编程的基础,具体可以看不才前面写的博客:【C++】模板上(泛型编程) —— 函数模板与类模板


文章目录

  • 写在前面
  • 一、非类型模板参数
  • 二、模板的特化
    • 2.1、函数模板特化
    • 2.2、类模板特化
        • 2.2.1、全特化
        • 2.2.2、偏特化
  • 三、模板的分离编译
  • 模板优缺点


一、非类型模板参数

模板参数可分为类型形参和非类型形参。

  • 类型形参: 出现在模板参数列表中,跟在 classtypename关键字之后的参数类型名称
  • 非类型形参用一个常量作为类(函数)模板的一个参数,在类(函数)模板中可将该参数当成常量来使用。

其作用与宏相似,不过的作用域加粗样式是整个程序的生命周期,而非类型模板参数的只作用在模板的生命周期

非类型模板参数的定义类型形参一样在模板的<>中,但是其类型就是需要程序猿显示的写内置类型
在这里插入图片描述

template<class T, size_t N> //N:非类型模板参数
class StaticArray
{
public:size_t arraysize(){return N;}
private:T _array[N]; //利用非类型模板参数指定静态数组的大小
};
  • 其中class T:是类型模板参数,其类型是由编译器自动推导
  • size_t N:是非类型模板参数,其类型为size_t

非类型模板参数可以直接在类中做为常数使用,所以可以用来定义数组。

使用非类型模板参数后,我们就可以在实例化对象的时指定所要创建的静态数组的大小了。

int main()
{StaticArray<int, 10> a1; //定义一个大小为10的静态数组cout << a1.arraysize() << endl; //10StaticArray<int, 100> a2; //定义一个大小为100的静态数组cout << a2.arraysize() << endl; //100return 0;
}
  • 这时候需要程序猿显示实例化类,才是正确的使用非类型模板参数的泛型编程

注意

  • 非类型模板参数只允许使用整型家族浮点数、类对象、字符串是不允许 作为非类型模板参数的。
  • 非类型的模板参数在编译期就需要确认结果,因为编译器在编译阶段就需要根据传入的非类型模板参数生成对应的类或函数。

二、模板的特化

这里举一个简单的例子来说明什么是特化,下面是用于比较两个任意相同类型的数据是否相等的函数模板。
在这里插入图片描述

template<class T>
bool IsEqual(T x, T y)
{return x == y;
}

我们大概会这样使用该函数模板:

cout << IsEqual(1, 1) << endl; //1
cout << IsEqual(1.1, 2.2) << endl; //0

这样使用是没有问题的,它的判断结果也是我们所预期的,但是我们也可能会这样去使用该函数模板

char a1[] = "你干嘛~~哎哟";
char a2[] = "你干嘛~~哎哟";
cout << IsEqual(a1, a2) << endl; //0

判断结果是这两个字符串不相等,这很好理解,因为我们希望的是该函数能够判断两个字符串的内容是否相等而该函数实际上判断是确实这两个字符串所存储的地址是否相同,这是两个字符串数组在栈区定义的,那其地址显然是不同的

类似于上述实例,使用模板可以实现一些与类型无关的代码,但对于一些特殊的类型可能会得到一些错误的结果,此时就需要对模板进行特化即在原模板的基础上,针对特殊类型进行特殊化的实现方式

模板的特化其核心的思想其实和函数的重载是一样的


2.1、函数模板特化

函数模板的特化步骤:

  1. 首先必须要有一个基础的函数模板
  2. 关键字template后面接一对空的尖括号<>
  3. 函数名后跟一对尖括号尖括号中指定需要特化的类型
  4. 函数形参表必须要和模板函数的基础参数类型完全相同,否则不同的编译器可能会报一些奇怪的错误。

在这里插入图片描述

对于上述实例,我们知道当传入的类型是char*时,应该依次比较各个字符的ASCII码进而判断两个字符串是否相等,或是直接调用strcmp函数进行字符串比较,那么此时我们就可以对char*类型进行特殊化的实现。

//基础的函数模板
template<class T>
bool IsEqual(T x, T y)
{return x == y;
}//对于char*类型的特化
template<>
bool IsEqual<char*>(char* x, char* y)
{return strcmp(x, y) == 0;
}

注意: 一般情况下,如果函数模板遇到不能处理或者处理有误的类型,为了实现简单通常都是将该函数直接给出(即函数重载)。例如,上述实例char*类型的特化还可以这样给出:

//基础的函数模板
template<class T>
bool IsEqual(T x, T y)
{return x == y;
}//对于char*类型的特化
bool IsEqual(char* x, char* y)
{return strcmp(x, y) == 0;
}

2.2、类模板特化

不仅函数模板可以进行特化,类模板也可以针对特殊类型进行特殊化实现,并且类模板的特化又可分为全特化偏特化(半特化)

类模板的特化步骤

  1. 首先必须要有一个基础的类模板
  2. 关键字template后面接一对空的尖括号<>
  3. 类名后跟一对尖括号尖括号中指定需要特化的类型
2.2.1、全特化

全特化即是将模板参数列表中所有的参数都确定化。

在这里插入图片描述

template<class T1, class T2> //正常的类模板
class Dragon
{
public://构造函数Dragon(){cout << "Dragon<T1, T2>" << endl;}
private:T1 _D1;T2 _D2;
};

假设T1T2分别是doubleint时,我们若是想对实例化的类进行特殊化处理,那么我们就可以对T1T2分别是doubleint时的模板进行全特化

//对于T1是double,T2是int时进行的全特化
template<>
class Dragon<double, int>
{
public://构造函数Dragon(){cout << "Dragon<double, int>" << endl;}
private:double _D1;int _D2;
};

我们程序运行结果:
在这里插入图片描述

2.2.2、偏特化

偏特化是指任何针对模板参数进一步进行条件限制设计的特化版本。

我们还是使用上面的类做为例子

1、部分特化
我们可以仅对模板参数列表中的部分参数进行确定化。
在这里插入图片描述
例如,我们可以对T1int类型的类进行特殊化处理。

//对T1为int的类进行特化
template<class T2>
class Dragon<int, T2>
{
public://构造函数Dragon(){cout << "Dragon<int, T2>" << endl;}
private:int _D1;T2 _D2;
};

程序运行结果:
在这里插入图片描述

2、参数更进一步的限制
偏特化并不仅仅是指特化部分参数,而是针对模板参数进一步的条件限制所设计出来的一个特化版本。
在这里插入图片描述
我们还是以上面的例子做为主类。例如,我们还可以指定当T1T2某种类型时,使用我们特殊化的类模板。

template<class T1, class T2>//主类
class Dragon
{
public://构造函数Dragon(){cout << "Dragon<T1, T2>" << endl;}
private:T1 _D1;T2 _D2;
};//两个参数偏特化为指针类型
template<class T1, class T2>
class Dragon<T1*, T2*>
{
public://构造函数Dragon(){cout << "Dragon<T1*, T2*>" << endl;}
private:T1 _D1;T2 _D2;
};//两个参数偏特化为引用类型
template<class T1, class T2>
class Dragon<T1&, T2&>
{
public://构造函数Dragon(){cout << "Dragon<T1&, T2&>" << endl;}
private:T1 _D1;T2 _D2;
};

程序运行结果:

在这里插入图片描述


三、模板的分离编译

一个程序(项目)由若干个源文件共同实现,而每个源文件单独编译生成目标文件,最后将所有目标文件链接起来形成单一的可执行文件的过程称为分离编译模式。

在分离编译模式下,我们一般创建三个文件,一个头文件用于进行函数声明,一个源文件用于对头文件中声明的函数进行定义,最后一个源文件用于调用头文件当中的函数
在这里插入图片描述
按照此方法,我们若是对一个加法函数模板进行分离编译,其三个文件当中的内容大致如下:
在这里插入图片描述
但是使用这三个文件生成可执行文件时,却会在链接阶段产生报错。

下面我们对其进行分析:
我们都知道,程序要运行起来一般要经历以下四个步骤:

  1. 预处理: 头文件展开、去注释、宏替换、条件编译等。
  2. 编译: 检查代码的规范性、是否有语法错误等,确定代码实际要做的工作,在检查无误后,将代码翻译成汇编语言。
  3. 汇编: 把编译阶段生成的文件转成目标文件。
  4. 链接: 将生成的各个目标文件进行链接,生成可执行文件

详细内容可以查看不才之前写的笔记:C/C++程序的编译+链接

以上代码在预处理阶段需要进行头文件的包含以及去注释操作。如下图:
在这里插入图片描述
这三个文件经过预处理后实际上就只有两个文件了,若是对应到Linux操作系统当中,此时就生成了 Add.imain.i 文件了。如下图:
在这里插入图片描述
预处理后就需要进行编译,虽然在 main.i 当中有调用Add函数的代码,但是在 main.i 里面也有Add函数模板的声明,因此在编译阶段并不会发现任何语法错误。之后便顺利将 Add.imain.i 翻译成了汇编语言,对应到Linux操作系统当中就生成了 Add.smain.s 文件。

之后就到达了汇编阶段,此阶段利用 Add.smain.s 这两个文件分别生成了两个目标文件,对应到Linux操作系统当中就是生成了 Add.omain.o 两个目标文件。

在链接阶段发现,在main函数当中调用的两个Add函数实际上并没有被真正定义,主要原因是函数模板并没有生成对应的函数,因为在全过程中都没有实例化过函数模板的模板参数T,所以函数模板根本就不知道该实例化T为何类型的函数

模板分离编译失败的原因
函数模板定义的地方Add.cpp没有进行实例化,那编译器不会为模板推导任何类型的函数实体,而在需要函数调用的地方main.cpp)就会因为没有模板函数没有对应的定义,无法进行实例化。

在了解其特性后,我们就可以根据特性来进行编程,但是不才这里建议**模板来说最好不要进行分离编译,不论是函数模板还是类模板,将模板的声明和定义都放到一个文件当中就行了。**这样就不会出现乌龙事件


模板优缺点

优点:

  • 模板复用了代码,节省资源,更快的迭代开发,C++的标准模板库(STL)因此而产生。
  • 增强了代码的灵活性。

缺陷:

  • 模板会导致代码膨胀问题,也会导致编译时间变长。
  • 出现模板编译错误时,错误信息非常凌乱,不易定位错误。

以上就是本章所有内容。若有勘误请私信不才。万分感激💖💖 如果对大家有用的话,就请多多为我点赞收藏吧,您的每一个点赞都是不才最大的鼓励~~~💖💖
请添加图片描述

ps:表情包来自网络,侵删🌹


文章转载自:

http://Coy2fnv3.qqnxh.cn
http://iJb0hNoZ.qqnxh.cn
http://533JYXHN.qqnxh.cn
http://KTJY2UJy.qqnxh.cn
http://ie2QEIRL.qqnxh.cn
http://TgkITfTk.qqnxh.cn
http://4OfYv99C.qqnxh.cn
http://1sngYTIC.qqnxh.cn
http://DwQREI9U.qqnxh.cn
http://wtILhoIl.qqnxh.cn
http://rflPsAVt.qqnxh.cn
http://stNPJFSZ.qqnxh.cn
http://dVnmCUEw.qqnxh.cn
http://iquuwylm.qqnxh.cn
http://cbX1JRdY.qqnxh.cn
http://P0DOwFwo.qqnxh.cn
http://lRwN3hKQ.qqnxh.cn
http://cPy8qjZW.qqnxh.cn
http://dPJTRgcs.qqnxh.cn
http://AQXdM86B.qqnxh.cn
http://qb1rsr15.qqnxh.cn
http://BPIlQMcf.qqnxh.cn
http://ZctjjAKS.qqnxh.cn
http://DUJK4wSd.qqnxh.cn
http://xpeEPxoA.qqnxh.cn
http://nixnHHsn.qqnxh.cn
http://fLT9hZoQ.qqnxh.cn
http://fH7rMTXp.qqnxh.cn
http://vxSVC0tO.qqnxh.cn
http://S7sdmWML.qqnxh.cn
http://www.dtcms.com/wzjs/720014.html

相关文章:

  • 平湖新埭哪里有做网站的青岛关键词优化报价
  • 北京网站开发周期wordpress 运行好慢
  • 用asp做的网站有哪些关键词网络推广企业
  • 做网站需要准备哪些专业做汽配的网站
  • 最早做美食团购的网站平昌移动网站建设
  • 商务网站设计制作好的工具和方法wordpress自定义面板
  • 网上做头像用什么网站恩施seo搜索引擎优化
  • wordpress站点logo设置做视频网站玩什么配置
  • 电商网站需要多少钱中国网站备案
  • 本子网站建设浏览器打不开wordpress
  • 一个网站如何产生流量国外图片网站源码
  • 网站上线前要做哪些准备建立网站的服务器
  • 织梦系统网站打开速度慢管理咨询公司属于什么行业
  • 机械建设网站房地产市场现状
  • 小说网站 做百度联盟成都创新互联做的网站怎么样
  • 最好的dm单网站建设贴图库外链图床wordpress插件
  • 工程网站模板免费下载手机app
  • 网站移动端怎么做的王占山人物简介
  • 阳江网站设计公司小程序商城开发公司哪个好
  • 求生之路2怎么做非官方网站如何做网站的后台管理
  • 地方门户网站推广方案建网站的公司
  • 福州房地产网站建设WordPress全站跳转
  • 模板建站流程网站域名备案多长时间
  • 西安做网站建设的公司网页传奇游戏排行榜比亚迪
  • 网站建设价格一览表设计怎么学
  • 湖滨网站建设基本的网站建设步骤
  • 网站由什么构成网站链接查询
  • 网站服务器机房网站搭建是什么专业学的
  • 科技建站网站源码商丘做网站哪个好
  • 网站备案与icp备案如何自建网站做淘客