【库函数】在什么时候使用 string_view 代替 string

前言
C++17增加了std::string_view,它在很多情况会优于使用std::string 。
尤其是用做函数形参的时候,使用std::string_view基本一定优于老式的const std::string&这种写法。
了解std::string_view
在讲述它的优越性之前,我们应该先介绍一下它。
首先,它顾名思义,就是一个字符串视图,它和std::string不一样,不是一个可变的字符串类型。
它只是用来指代“字符串”(这个字符串可以指代的东西很多)的,并不拥有所有权,自然也不可变。
通常实现只保有两个数据成员:一个指向字符串的指针,一个表示字符串的的size(通常是size_t类型)。
通常64位系统下大小为16个字节。
了解std::string
class string {//简单示例,实际不可能如此
public:
// all 83 member functions
private:
char* m_data;
size_type m_size;
size_type m_capacity;
std::array<char, 16> m_sso;
};
对于 64 位系统,每个字符串std::string有 24 个字节的“开销”(size,capacity,data),另外还有 16 个字节用于 SSO 缓冲区。
加起来也就是40。
实际使用
老式写法
void func(const std::string&s){
std::cout << s << '\n';
}
看起来没有任何问题,但其实在很多传参调用的情况下,开销是很大的。
std::string s{"乐呵"};
func("乐呵");
func(s);
你觉得上面哪个调用,谁的开销更大?
是 func("乐呵");,这里我们传入的是字符串字面量,它和std::string不是一个类型,这里实际上需要调用std::string的转换构造函数,在当前构造出一个临时的std::string对象,也就是一个纯右值表达式。
const std::string&可以接纯右值表达式,没问题,并且延长临时对象的生存期,可以在函数局部使用。
const char* p = "乐呵";
func(p);//传指针也和上面说的差不多。
另外,使用const std::string&还更容易造成一些bug,比如:
const std::string& f(const std::string& str) {
return str;
}
int main() {
auto& ret = f("哈哈");
std::cout << ret << '\n';
}
const std::string& str接纯右值表达式是没问题。但是它最后还想返回这个对象的引用,就不对了。
在函数调用中绑定到函数形参的临时量,存在到含这次函数调用的全表达式结尾为止:如果函数返回一个生命长于全表达式的引用,那么它会成为悬垂引用。
使用std::string_view
void func(std::string_view s){
std::cout << s << '\n';
}
int main(){
std::string s{"乐呵"};
const char* p = "乐呵";
func("乐呵");
func(s);
func(p);
}
std::string有一个到std::string_view的转换函数,其他的都是正常走std::string_view的构造函数。
std::string_view 只是一个视图,用来指代原字符串的,保有一个size和一个指针即可。
新增加的库基本上不会再以const std::string&这种作为形参,比如std::format,std::vformat。
总结
如果你能用std::string_view,那么请使用。至少在用作接口的时候,一定是。
【库函数】在什么时候使用 string_view 代替 string的更多相关文章
- 【C语言】模拟实现库函数strcat函数
//模拟实现库函数strcat函数 #include <stdio.h> #include <string.h> #include <assert.h> char ...
- C++中把string转成char
c_str函数的返回值是const char*的,不能直接赋值给char*, c++语言提供了两种字符串实现,其中较原始的一种只是字符串的c语言实现. 与C语言的其他部分一样,它在c+的所有实现中可用 ...
- C++17剖析:string_view的实现,以及性能
主要内容 C++17标准发布,string_view是标准新增的内容.这篇文章主要分析string_view的适用范围.注意事项,并分析string_view带来的性能提升,最后从gcc 8.2的li ...
- C++数值类型与string的相互转换
转自:https://www.cnblogs.com/johngu/p/7878029.html 1.数值类型转换为string 1.1使用函数模板+ostringstream 使用函数模板将基本数据 ...
- C++.【转】C++数值类型与string的相互转换
1.C++数值类型与string的相互转换 - JohnGu - 博客园.html(https://www.cnblogs.com/johngu/p/7878029.html) 2. 1.数值类型转换 ...
- string与char*的转换方法
c_str函数的返回值是const char*的,不能直接赋值给char*,所以就需要我们进行相应的操作转化,下面就是这一转化过程. c++语言提供了两种字符串实现,其中较原始的一种只是字符串的c语言 ...
- 5. 常见C语言字符串库函数的使用及实现
1. strncat 函数: [函数原型]#include <string.h> char *strncat( char *str1, const char *str2, size_t c ...
- Python网络编程(2)——socket模块(2)
目录: 1. 异常 2. 地址族 3. 套接字类型 4. 模块方法 5. Socket对象与实例方法 socket模块提供了Python中的低层网络连接接口,用于操作套接字操作. 异常 socket模 ...
- memcpy、memmove、memset及strcpy函数实现和理解
memcpy.memmove.memset及strcpy函数实现和理解 关于memcpy memcpy是C和C++ 中的内存拷贝函数,在C中所需的头文件是#include<string.h> ...
- Linux 内核开发—内核简单介绍
内核简单介绍 Linux 构成 Linux 为什么被划分为系统空间和内核空间 隔离核心程序和应用程序,实现对核心程序和数据的保护. 什么内核空间,用户空间 内核空间和用户空间是程序执行的两种不同的状态 ...
随机推荐
- 循环返回结果结果集(connect 函数使用)
--示例: SELECT 0 + ROWNUM sonID FROM DUAL /*区间范围*/ CONNECT BY ROWNUM <= 20;
- [P7880][Ynoi2006] rldcot
[Ynoi2006] rldcot 题目描述 给定一棵 \(n\) 个节点的树,树根为 \(1\),每个点有一个编号,每条边有一个边权. 定义 \(dep(x)\) 表示一个点到根简单路径上边权的和, ...
- Vue2.0 学习 第二组 语法模板
本笔记主要参考菜鸟教程和官方文档编写. 1.文本绑定 一般在dom中用{{}}标时,并且在vue构造体内的data中定义文本内容 <div id="app"> & ...
- 在 Sealos 中使用区块链技术实现统一支付系统
拿着区块链技术不一定是去发币,很多业务系统也适合用这些技术,比如做个统一支付系统,积分系统等,可以做为一家公司的金融基础设施,或支付中台.拿链的技术去做有很多好处: 高可用,自带多区域高一致性的能力, ...
- 使用动画曲线编辑器打造炫酷的3D可视化ACE
前言 在制作3D可视化看板时,除了精细的模型结构外,炫酷的动画效果也是必不可少的.无论是复杂的还是简单的动画效果,要实现100%的自然平滑都是具有挑战性的工作.这涉及到物理引擎的计算和对动画效果的数学 ...
- Illegal overloaded getter method with ambiguous type for property......
问题原因 建议 1.boolean类型的属性值不建议设置为is开头,否则会引起rpc框架的序列化异常. 2.如果强行将IDE自动生成的isSuccess()方法修改成getSuccess(),也能获取 ...
- 将Abp默认事件总线改造为分布式事件总线
@ 目录 原理 创建分布式事件总线 实现自动订阅和事件转发 使用 启动Redis服务 配置 传递Abp默认事件 传递自定义事件 项目地址 原理 本地事件总线是通过Ioc容器来实现的. IEventBu ...
- C++ Qt开发:StatusBar底部状态栏组件
Qt 是一个跨平台C++图形界面开发库,利用Qt可以快速开发跨平台窗体应用程序,在Qt中我们可以通过拖拽的方式将不同组件放到指定的位置,实现图形化开发极大的方便了开发效率,本章将重点介绍QStatus ...
- 字节国际化TnS算法实习的碎碎念
Motivation 在保研之后,我和南大的导师投了一篇个性化联邦学习的CVPR作为毕设.之后感觉就没什么事了,于是想着找个实习吧,第一个想法就是去字节实习,也只投了字节(别学我,还是多投一些哈哈,找 ...
- Sequelize的简单连接和使用
Sequelize是一个基于Node.js的ORM框架 特点: 1.支持多种数据库:Sequelize支持多种关系型数据库,包括MySQL.PostgreSQL.SQLite和MSSQL等,适用于需要 ...