C++ 函数模板基础
文章目录
- 一、什么是函数模板
- 二、函数模板的优点
- 1、代码重用
- 2、类型安全
- 3、可读性
- 4、泛型编程
- 5、性能优化
- 6、库开发
- 三、函数模板的使用场景
- 1、通用操作
- 2、数据结构与容器操作
- 3、排序与查找算法
- 4、数学与统计函数
- 5、类型转换器
- 6、自定义函数对象
- 四、模板参数的声明(使用template关键字)
- 1、类型参数声明
- 1)示例1
- 2)示例2
- 2、非类型参数声明
一、什么是函数模板
C++中的函数模板是用于创建泛型和可重用代码的一种编程范式。通过为编译器提供一组用于生成特定类型函数的模板,可以让同一段代码为多种类型的操作提供支持。在编译时,编译器根据函数模板和提供的类型将创建具体函数(实例化)。
以下是一个C++函数模板的示例,表示计算两个数中的较大者的通用模板:
#include <iostream>
using namespace std;// 函数模板声明
template <typename T>
T maxNumber(T a, T b);int main() {int x = 3, y = 5;double u = 2.5, v = 1.8;// 使用模板函数,编译器自动推导类型int int_max = maxNumber(x, y);double double_max = maxNumber(u, v);cout << "Max of x and y = " << int_max << endl;cout << "Max of u and v = " << double_max << endl;return 0;
}// 函数模板定义
template <typename T>
T maxNumber(T a, T b) {return (a > b) ? a : b;
}
在上述代码中,我们定义了一个函数模板 maxNumber,它有一个类型参数 T,用于泛化不同数据类型。此示例展示了如何使用同一个函数模板来处理多种类型的数据(在本例中,我们处理了int和double数据类型)。编译器会根据提供的类型为该模板创建合适的函数实例。
通过使用函数模板,我们可以编写通用、易于维护且可重用的代码。这可以简化大型项目中的复杂性,避免因重复编写类似代码而引入的错误。
二、函数模板的优点
C++函数模板具有一些突出的优点,这使得它们在编写泛型和可重用代码时成为一个非常有用的工具:
1、代码重用
通过使用函数模板,您可以编写一段能及时适应不同数据类型的代码,避免为处理不同数据类型编写多个类似的函数实现。这降低了代码重复度,同时减少了维护成本。
2、类型安全
函数模板在编译时生成特定类型的函数实例,从而提供了额外的类型检查。这有助于捕获类型错误,确保程序的正确性,以及提高运行时性能。
3、可读性
使用函数模板可以提高代码的可读性和透明度,因为您不再需要在代码中明确处理每个特定数据类型的情况,从而使代码更简洁。
4、泛型编程
函数模板允许您实现泛型编程范式,这是一种设计和实现能够适应不同数据类型和情况的通用代码的方法。这可以提高代码的模块化和可扩展性。
5、性能优化
由于模板实例化为特定类型的函数发生在编译时,因此可以提供优化的机会,与非模板函数相比,运行时性能相同或更好。
6、库开发
在C++标准库和其他库中,函数模板被广泛用于实现通用算法、容器和其他实用程序,例如排序、查找、拷贝等操作。这提高了库的可重用性,并使库更易于集成。
虽然函数模板具有诸多优点,但需要在编写和使用时注意避免编译器误解、代码膨胀、难以调试的问题。总的来说,合理使用C++函数模板可以带来代码编写和维护的极大便利。
三、函数模板的使用场景
在C++中,函数模板用于编写通用的、能够适应多种数据类型的代码。以下是几个典型的函数模板使用场景:
1、通用操作
编写适用于不同数据类型的通用操作函数,例如比较大小、求和、交换两个变量的值等。
template <typename T>
T getMax(T a, T b) {return (a > b) ? a : b;
}
2、数据结构与容器操作
创建和操作通用数据结构,如链表、栈、队列、二叉树等。这种情况下,函数模板可用于实现类似查找、遍历、插入和删除等操作。
template <typename T>
bool findInVector(const std::vector<T>& vec, const T& value) {// ...
}
3、排序与查找算法
实现通用的排序和查找算法,例如冒泡排序、快速排序、二分查找等。这些算法可以适应于基本数据类型和用户自定义对象,只要定义了适当的比较操作。
template <typename T>
void quickSort(std::vector<T>& data, int left, int right) {// ...
}
4、数学与统计函数
实现泛型数学和统计函数,如最大公约数、最小公倍数、平均值计算等。
template <typename T>
T gcd(T a, T b) {// ...
}
5、类型转换器
编写通用的类型转换器函数,例如在编码/解码器、序列化/反序列化等场景中。
template <typename To, typename From>
To convertType(const From& source) {// ...
}
6、自定义函数对象
创建泛型的仿函数(函数对象),这些可用于执行操作(例如比较、转换等)并在传递给其他泛型函数时保持状态。
template <typename T>
class CustomComparator {// ...bool operator()(T a, T b) const {// ...}
};
在这些使用场景中,函数模板提供了灵活性和可重用性,使得你能够为不同数据类型编写一段代码。唯一的挑战是有效地管理类型参数,使其适应于所需的操作和逻辑。使用C++中的函数模板可以帮助你编写更加高效、可维护的代码。
四、模板参数的声明(使用template关键字)
在C++中,模板参数(可以是类型参数或非类型参数)在函数模板定义前使用template关键字进行声明。以下是模板参数声明的基本语法:
template <typename/type/class T, typename/type/class U, ... , typename/type/class N, NonTypeParameter1, NonTypeParameter2, ..., NonTypeParameterN>
这里,T、U和N表示类型参数,你可以使用typename或class关键字定义它们。NonTypeParameter1、NonTypeParameter2到NonTypeParameterN表示非类型参数(例如整数、字符或者指针等)。
1、类型参数声明
1)示例1
以下是一个使用单个类型参数的简单函数模板,实现任意类型变量的交换:
template <typename T> // 声明一个类型参数T
void swap(T& a, T& b) {T temp = a;a = b;b = temp;
}
2)示例2
以下是一个使用两个类型参数的函数模板,用于计算一对具有不同类型的值之和:
template <typename T, typename U> // 声明两个类型参数T和U
auto sum(T a, U b) -> decltype(a + b) {return a + b;
}
2、非类型参数声明
非类型参数表示一个编译时常量,如整数、枚举值、指针等。
以下是一个使用非类型整数参数N的数组求和函数模板:
template <typename T, int N> // 声明一个类型参数T和一个非类型整数参数N
T arraySum(const T (&arr)[N]) {T sum = T();for (int i = 0; i < N; ++i) {sum += arr[i];}return sum;
}
现在你已经了解了如何在C++中声明模板参数。使用模板参数可以帮助你编写更通用的代码,减少代码重复,并提高代码的可维护性。在C++编程中,模板参数是一个非常重要且强大的工具。
太多内容记不住?前往👉🏻 英雄算法联盟 和博主一起刷题,巩固知识点 和 加深印象。
相关文章:
C++ 函数模板基础
文章目录 一、什么是函数模板二、函数模板的优点1、代码重用2、类型安全3、可读性4、泛型编程5、性能优化6、库开发 三、函数模板的使用场景1、通用操作2、数据结构与容器操作3、排序与查找算法4、数学与统计函数5、类型转换器6、自定义函数对象 四、模板参数的声明(…...
CUDA torch reinstall 与杂谈
一 实用技巧 1 从cuda11升级到12 apt-get --purge remove "cuda*" wget https://developer.download.nvidia.com/compute/cuda/12.1.1/local_installers/cuda_12.1.1_530.30.02_linux.run sh cuda_12.1.1_530.30.02_linux.run vim ~/.bashrc export PATH/usr/local…...
[230530] 托福TPO口语真题| TPO66~TPO72|XPO|Task1|20:30~21:00
目录 真题 预测题 真题 66. Do you agree or disagree with the following statement? Some people believe that a person needs a college education in order to have a successful career. Others believe that a college education is not necessary for…...
【FMC201】基于FMC标准的1路CameraLink Full 输入 子卡模块
产品概述 FMC201是一款CameraLink信号输入(采集)FMC子卡模块,该模块支持2路CameraLink Base模式或者1路CameraLink Full模式的图像信号输入。板卡具有2个CameraLink端口(SDR26),可以作为采集卡使用。 技术指…...
C语言_VS系列编译器写C语言或C++代码产生的一些错误与警告的解决方法(VS2010/VS2019)
本次来分享在用VS系列编译(VS2010/VS2019)写C语言或C代码时会遇到的一些警告和错误,提供博主的一些解决方法,若有更好的解决方法,大家也可以在评论区发表自己的意见噢,话不多说,开始上菜: 此博主在CSDN发布…...
从零实现一个数据库(DataBase) Go语言实现版 0.介绍
英文源地址 数据库实现步骤细分 1.持久化(Persistence) 我们为什么需要数据库?为什么不是直接把数据dump进文件中. 第一个话题就是持久化. 我们将讨论如果写入文件的过程中程序崩溃了, 或者电源断电了, 文件的状态会是什么样的呢? 文件是否只是丢失了最后一次写操作?或者…...
操作系统-X18 linux日志审计
Linux日志审计 在unix/类unix(Linux)系统中,日志是内核(内存)的一部分。 用于记录系统、程序运行中发生的各种事件 通过阅读日志,有助于诊断和解决系统故障 日志文件的分类 ①内核及系统日志 由系统sysl…...
【Vue工程】011-Axios
【Vue工程】011-Axios 文章目录 【Vue工程】011-Axios一、概述1、简介2、官网3、訾博其他相关博客【axios】001-axios概述、特点、文档说明【axios】002-axios发起请求axios封装 二、基本使用1、安装2、创建一个 token 状态3、axios 封装4、使用示例设置 baseURL请求调用拦截器…...
Cy7 NHS ester水溶性七甲川花菁染料标记活性脂477908-53-5
Sulfo-CY7 NHS ester是一种荧光标记试剂,可用于生物分子的荧光标记。它是一种水溶性的N-羟基琥珀酰亚胺酯化合物,具有强烈的荧光信号和高度稳定性。Sulfo-CY7 NHS ester的化学结构为C43H48N3NaO16S2,分子量约为968.98 g/mol。Sulfo-CY7 NHS e…...
利用CX-ONE搭建omron PLC仿真环境
目录 1 安装参考 2 CX-Simulator 2.1 打开软件 2.2 选择PLC配置文件存放位置 2.3 选择PLC类型 2.4 PLC Unit全部选择 2.5 设置FINS通讯 2.6 设置串口通讯 2.7 建立连接 3 CX-Programmer 3.1 新建工程 3.2 设置PLC型号 3.3 设置网络类型 3.4 设置串口通讯 3.5 设…...
webpack Plugin Loader
本文作者为 360 奇舞团前端开发工程师 webpack是Javascript工具链的关键部分。webpack是个用于现代JavaScript应用程序的静态模块打包工具。它不仅可以支持ESM和CommonJS模块化编程,而且还可以支持或扩展支持许多不同的静态资源,例如:Files,I…...
关闭eslint - vue篇
文章目录 一、问题描述二、问题解决1、首先是比较旧的vue项目2、创建项目的时候,不要选eslint3、如果你使用的编辑软件是webstorm4、创建的项目没有webpack.base.conf.js文件,但是有 .eslintrc.js5、比较新的vue项目,目录没有(直接…...
XXL-SSO简要说明
一、介绍 XXL-SSO 是一个分布式单点登录框架。只需要登录一次就可以访问所有相互信任的应用系统。 拥有”轻量级、分布式、跨域、CookieToken均支持、WebAPP均支持”等特性。现已开放源代码,开箱即用。 官方文档 二、集成 2.1、源码下载 下载地址 2.2、代码结构…...
HC-05蓝牙模块的使用
我最近刚刚开始学习嵌入式,在第一次使用蓝牙模块HC-05的时候遇到了很多问题, 甚至连接线都不会,因此下面我会十分详细地介绍我一步一步探索的步骤,直到完成使用手机APP和51单片机收发数据。 调试步骤 首先,我们需要明…...
初始python
初始python 缘由 对于python,相比大家并不陌生,Python是一种高级的、解释性编程语言,它具有简洁的语法和强大的内置函数,适用于广泛的应用领域,例如运维,Web开发,数据科学,人工智能等。Pyt…...
C++入门预备语法
C入门预备语法 C关键字命名空间C输入&输出初步缺省参数函数重载引用内联函数auto和范围for(C11)指针空值nullptr C关键字 命名空间 命名空间是一种将变量名、函数名、类名和库名称等封装到一个命名空间域中,与其他域的同名量相隔离&…...
python发送email
通过第三方SMTP发送纯文本邮件 #!/usr/bin/python -- coding: UTF-8 -- import smtplib from email.mime.text import MIMEText from email.header import Header 第三方 SMTP 服务 mail_host“smtp.XXX.com” #设置服务器 mail_user“XXXX” #用户名 mail_pass“XXXXXX” …...
软件测试面试题自动化面经分享——这才是高薪的秘诀!
Hello,你们的好朋友来了!今天猜猜我给大家带来点啥干货呢?最近很多小伙伴出去面试的时候经常会被问到跟自动化测试相关的面试题。所以,今天特意给大家整理了一些经常被公司问到的自动化测试相关的面试题。停,咱先收藏起…...
Ceph入门到精通-Centos8安装prometheus
普罗米修斯是一个开源的监控、查询和警报工具。最初由Soundcloud于2012年构建,功能丰富的工具已被多家公司采用,用于监控其IT基础架构并确保所有系统平稳运行。Prometheus 允许您通过 HTTP 协议查询和提取时间序列指标,例如 CPU 和内存利用率,并在实时图表上可视化它们。您…...
把树莓派改造成无线网卡(3)-----共享无线网络,无线网络转换成有线网络,让有线网络设备连上无线网络
本文目录 1、准备工作2、安装DNS和配置管理软件3、设置网络路由功能3.1、树莓派的有线网络接口IP配置3.2、启用路由和IP伪装3.3、为有线网络配置DHCP和DNS服务 4、运行5、进阶--将二个以太网口加入到同一个网桥 现在的无线路由器非常便宜,所以实际上除了有特殊的要求…...
蓝牙抓包不求人:从HCI日志里‘挖’出Link Key的两种实用方法(附安卓路径)
蓝牙安全逆向实战:从HCI日志中提取Link Key的深度解析在蓝牙协议安全研究领域,Link Key作为设备配对认证的核心凭证,其获取方式一直是逆向工程师关注的焦点。许多安全审计场景下,我们往往只能获得加密后的HCI通信日志,…...
软阴影:那个让虚拟世界“温柔起来“的光影小秘密
一、从一只小猫的影子说起 前几天我在朋友家做客,他家养了一只胖乎乎的橘猫,正趴在阳台的窗边晒太阳。我无意间瞥了一眼那只猫脚边的影子,突然被一个细节震撼了—— 那只猫的影子——并不是一片均匀的黑。 仔细看——猫肚子紧贴地板的地方——…...
6款高效降AI率工具 改写实力出众
写论文时反复检测出的AI痕迹总让你提心吊胆?别担心,这里整理了6款真正好用的论文降AI率工具,堪称应对AI生成特征的“得力助手”。它们能有效识别并消除AI生成的痕迹,改写能力出众,帮你快速降低查重率,顺利通…...
ROS Noetic实战:从bag包里‘抠’出雷达点云和IMU数据的保姆级教程(Ubuntu 20.04)
ROS Noetic实战:从bag包里提取雷达点云和IMU数据的完整指南(Ubuntu 20.04)在机器人开发中,ROS bag文件就像是一个装满珍贵数据的宝箱,而雷达点云和IMU数据则是其中最闪亮的宝石。作为一名长期与ROS打交道的开发者&…...
Burp Suite深度解析:从流量抓包到业务逻辑漏洞挖掘
1. 这不是“学个插件”——Burp Suite 是渗透测试的呼吸系统 很多人第一次听说 Burp Suite,是在某篇“三步拿下登录框”的速成教程里:装好Java、拖进浏览器代理、点几下Repeater就弹出密码明文。结果真去测一个中型SaaS后台,不到十分钟就卡在…...
关于psthon问题
我想问问各位 我python可以查到 但是我的bit文件查不到python怎么回事...
随机森林算法在儿童出行方式预测中的实战应用与优化
1. 项目概述:用随机森林预测孩子怎么上学做城市交通规划或者做家长接送方案的时候,你肯定想过一个问题:孩子们到底是怎么上学的?是走路、骑车、坐公交还是家长开车送?这个问题看似简单,背后却牵扯到城市规划…...
为什么你的DeepSeek微调loss震荡不止?(Meta/DeepSeek联合团队未公开的梯度裁剪+LoRA初始化双校准协议)
更多请点击: https://codechina.net 第一章:DeepSeek微调loss震荡的根本归因剖析 DeepSeek系列模型在微调过程中频繁出现loss剧烈震荡现象,其本质并非单一因素所致,而是数据、优化器、梯度动态与模型结构四者耦合失稳的系统性表现…...
抖音内容批量下载实战:从零开始构建个人视频资料库
抖音内容批量下载实战:从零开始构建个人视频资料库 【免费下载链接】douyin-downloader A practical Douyin downloader for both single-item and profile batch downloads, with progress display, retries, SQLite deduplication, and browser fallback support.…...
基于Arduino与蓝牙模块的六路无线开关控制系统设计与实现
1. 项目概述:用手机蓝牙控制六路LED想不想把手机变成一个无线遥控器,随手一点就能开关家里的灯带、氛围灯,甚至是其他电器?这个项目就是为你准备的。它基于一块功能增强的Arduino兼容板——GlowDuino Uno,配合一个极其…...
