[译]C++17,使用 string_view 来避免重复分配内存https://blog.csdn.net/tkokof1/article/details/82527370好!
附上评论里大佬@荆楚闲人的补充,把small字符串加长
#include <iostream>
#include <string>
/*
当字符串数据的所有权已经确定(譬如由某个string对象持有),并且你只想访问(而不修改)他们时,使用 std::string_view 可以避免字符串数据的复制,从而提高程序效率,这(指程序效率)也是这篇文章的主要内容.
我假设你已经了解了一些 std::string_view 的知识,如果没有,可以看看我之前的这篇文章.C++ 中的 string 类型在堆上存放自己的字符串数据,所以当你处理 string 类型的时候,很容易就会产生(堆)内存分配.
*/
void* operator new(std::size_t count)
{//我重载了全局的 new 操作符,这样我就能跟踪(堆)内存的分配了,而后,代码分别在第18行,第19行,第27行,第29行创建了string对象,所以这几处代码都会产生(堆)内存分配.
std::cout << " " << count << " bytes" << std::endl;
return malloc(count);
}
void getString(const std::string& str) {}
int main()
{
std::cout << std::endl;
std::cout << "std::string" << std::endl;
//std::string small = "0123456789";
std::string small = "01234567890123456789000666666";
std::string substr = small.substr(5);
std::cout << " " << substr << std::endl;
std::cout << std::endl;
std::cout << "getString" << std::endl;
/*getString(small);
getString("0123456789");
const char message[] = "0123456789";*/
getString(small);
getString("01234567890123456789000666666");
const char message[] = "01234567890123456789000666666";
getString(message);
std::cout << std::endl;
return 0;
}
长串的 输出:
改成短串的输出。
No memory allocation required
现在, std::string_view 无需复制字符串数据的优点就更加明显了
#include <cassert>
#include <iostream>
#include <string>
#include <string_view>
void* operator new(std::size_t count)
{
std::cout << " " << count << " bytes" << std::endl;
return malloc(count);
}
void getString(const std::string& str) {}
void getStringView(std::string_view strView) {}
int main()
{
std::cout << std::endl;
std::cout << "std::string" << std::endl;
std::string large = "0123456789-123456789-123456789-123456789";
std::string substr = large.substr(10);
std::cout << std::endl;
std::cout << "std::string_view" << std::endl;
std::string_view largeStringView{ large.c_str(), large.size() };
largeStringView.remove_prefix(10);
assert(substr == largeStringView);
std::cout << std::endl;
std::cout << "getString" << std::endl;
getString(large);
getString("0123456789-123456789-123456789-123456789");
const char message[] = "0123456789-123456789-123456789-123456789";
getString(message);
std::cout << std::endl;
std::cout << "getStringView" << std::endl;
getStringView(large);
getStringView("0123456789-123456789-123456789-123456789");
getStringView(message);
std::cout << std::endl;
return 0;
}
输出
代码22行,23行,39行,41行因为创建了 string 对象 所以会分配(堆)内存,但是代码29行,30行,47行,48行,49行也相应的创建了 string_view 对象,但是并没有发生(堆)内存分配!