返回完整目录

2.2 使用Stack类模板 Use of Class Template Stack

在C++17以前,使用类模板必须显式指定模板实参[1]。以下例子展示如何使用类模板Stack<>

// basics/stack1test.cpp

#include "stack1.hpp"
#include <iostream>
#include <string> int main()
{
Stack<int> intStack; //int类型的栈
Stack<std::string> stringStack; //string类型的栈 //操作int类型的栈
intStack.push(7);
std::cout << intStack.top() << '\n'; //操作string类型的栈
stdString.push("hello");
std::cout << stringStack.top() << '\n';
stringStack.pop();
}

通过声明类型Stack,int作为类模板内T的类型。因此,intStack为一个使用vector为元素的对象,任何被调用的成员函数将相应地实例化。相似地,通过声明Stackstd::string,创建一个使用vectorstd::string为元素的对象,任何被调用的成员函数将相应地实例化。

注意,只有被调用的模板(成员)函数代码才能被实例化。对于类模板,成员函数只有被调用才会实例化。这节省了时间和空间,同时也使得类模板可以被部分使用,这将在第2.3节中讨论。

本例中,int类型和string类型的默认构造函数、push()函数、top()函数都将被实例化,然而pop()函数只有string类型的进行了实例化。如果类模板有静态成员,这些静态成员也只实例化一次,而且只有使用了类模板的那一种类型进行了实例化。

实例化后的类模板类型可以像其他类型一样使用,可以用const或者volatile进行限定,或者基于它衍生出数组和引用。也可以将其作为typedef或者using进行类型定义的一部分(更多类型定义的内容详见第2.8节),或者当构建其他模板类型时作为类型参数,比如:

void foo(Stack<int> const& s) //参数s是int的Stack
{
using IntStack = Stack<int>; //IntStack是Stack<int>的别名
Stack<int> istack[10]; //istack是长度为10的Stack<int>的数组
IntStack istack2[10]; //istack2也是长度为10的Stack<int>的数组
}

模板实参可以是任何类型,比如float类型的指针,甚至是int的Stack:

Stack<float*> floatPtrStack;      //float指针的Stack
Stack<Stack<int>> intStackStack; //int的Stack的Stack

唯一的要求便是任何被调用的操作对于该类型是可行的。

注意到,C++11之前必须在两个闭模板括号(closing template brackets)之间放置空格:

Stack<Stack<int> > intStackStack;      //任何C++版本都没问题

如果不这么做而使用符号 >>,这将导致语法错误:

Stack<Stack<int>> intStackStack;       //C++11之前将引发错误

旧版本的这种行为的原因是这可以帮助C++编译器在第一轮中将源代码分成独立语义的片段(tokenize the source code independent of the semantics of the code)。然而,由于缺失空格是个典型的bug,这需要对应的错误消息,该代码的语义将越来越难以考虑在内。因此C++11移除了“在两个闭合模板括号中间必须加入空格”的规则,史称“角括号hack”(详见13.3.1节)。

脚注


  1. C++17引入了类模板实参推断,这使得可以跳过指定模板实参,只要可以从构造函数推断出模板实参。这将在2.9节中详细讨论。

C++ Templates (2.2 使用Stack类模板 Use of Class Template Stack )的更多相关文章

  1. C++ Templates (2.1 类模板Stack的实现 Implementation of Class Template Stack)

    返回完整目录 目录 2.1 类模板Stack的实现 Implementation of Class Template Stack 2.1.1 声明类模板 Declaration of Class Te ...

  2. C++类模板

    在上篇文章(C++函数模板)中,主要介绍了C++中函数模板,与函数相似,类也可以被一种或多种类型参数化.容器类就是一个具有这种特性的典型的例子, 本文地址:http://www.cnblogs.com ...

  3. C++:类模板与模板类

    6.3 类模板和模板类 所谓类模板,实际上是建立一个通用类,其数据成员.成员函数的返回值类型和形参类型不具体指定,用一个虚拟的类型来代表.使用类模板定义对象时,系统会实参的类型来取代类模板中虚拟类型从 ...

  4. C++学习笔记36:类模板

    类模板的目的 设计通用的类型式,以适应广泛的成员数据型式 类模板的定义格式 template<模板形式参数列表>class 类名称{...}; 原型:template<typenam ...

  5. 初步C++类模板学习笔记

    类模板 实现:在上课时间的定义给它的一个或多个参数,这些参数代表了不同的数据类型.                              -->抽象的类. 在调用类模板时, 指定參数, 由编 ...

  6. C++_进阶之函数模板_类模板

     C++_进阶之函数模板_类模板 第一部分 前言 c++提供了函数模板(function template.)所谓函数模板,实际上是建立一个通用函数,其函数类型和形参类型不具体制定,用一个虚拟的类型来 ...

  7. C++17尝鲜:类模板中的模板参数自动推导

    模板参数自动推导 在C++17之前,类模板构造器的模板参数是不能像函数模板的模板参数那样被自动推导的,比如我们无法写 std::pair a{1, "a"s}; // C++17 ...

  8. 使用js栈stack类的实现

    使用js栈stack类的实现 /*使用栈stack类的实现*/ function stack() { this.dataStore = [];//保存栈内元素,初始化为一个空数组 this.top = ...

  9. Java的Stack类实现List接口真的是个笑话吗

        今天在网上闲逛时看到了这样一个言论,说“Java的Stack类实现List接口的设计是个笑话”.   当然作者这篇文章的重点不是这个,原本我也只是一笑置之,然而看评论里居然还有人附和,说“Ja ...

随机推荐

  1. 一本通 高手训练 1788 爬山 dp 斜率 凸包

    LINK:爬山 很早以前看的题目 发现自己想的完全不对 这道题还是比较有价值的. 先不考虑走的路线问题 考虑某个点能看到的最高的山. 分左边和右边来考虑 考虑左边 利用单调栈存长度单调递减的山 不能直 ...

  2. x86架构:保护模式下利用中断实现抢占式多任务运行

         站在用户角度考虑,一个合格的操作系统即使在单核下也能 "同时" 执行多个任务,这就要求CPU以非常快的频率在不同任务之间切换,让普通人根本感觉不到任务的切换.windwo ...

  3. 郭超:阿里云Cassandra背后的故事

    大家好,我是阿里云数据库产品事业部的玄陵,真名郭超. ​ 本次的分享大概分三个部分:Cassandra云数据库简介.Cassandra云数据库特性以及Q&A. ​ 我们先了解一下Cassand ...

  4. 当asp.net core偶遇docker一(模型验证和Rabbitmq 二)

    上一篇我们说到构建了一个Rabbitmq容器 现在我们说说如何在一个悄悄传输消息到队列 我们现在设计一个Rabbitmq发送消息部分的模块 先设计一个远程发送的接口 public interface ...

  5. Docker入坑指南之RUN

    总有一些场景,我们需要自己制作一个镜像,可以快速还原环境,又不想被其他因素干扰镜像的纯净,这个时候,就可以选择Docker了,启动便捷,镜像还原很快捷,除了上手不容易. 最近入坑研究了一番,小有心得, ...

  6. spring security 简介+实战

    过滤器链: 依赖: security 功能列表: 一.登录验证.权限验证 1.1 httpbasic验证 1.2form验证 建立数据需要遵循RBAC模型 用户表要参考UserDetail创建 实例类 ...

  7. 用Python一键生成炫酷九宫格图片,火了朋友圈

  8. 用Java制作斗地主

    首先,按照斗地主规则,完成洗牌发牌的动作.如图: 具体规则: 1. 组装54张扑克牌 2. 将54张牌顺序打乱 3. 三个玩家参与游戏,三人交替摸牌,每人17张牌,最后三张留作底牌. 4. 查看三人各 ...

  9. java 静态导入、可变参数、集合嵌套

    一 静态导入 在导包的过程中我们可以直接导入静态部分,这样某个类的静态成员就可以直接使用了. 在源码中经常会出现静态导入. 静态导入格式: import static XXX.YYY;   导入后YY ...

  10. homekit_四路继电器

    这款继电器使用苹果手机进行控制,有普通版本和点动版本可供选择,有兴趣的可以去以下链接购买: https://item.taobao.com/item.htm?spm=a1z10.1-c.w4004-1 ...