C++string中有关大小和容量的函数浅析
1.length()与size()
length是因为沿用C语言的习惯而保留下来的,string类最初只有length,引入STL之后,为了兼容又加入了size,它是作为STL容器的属性存在的,便于符合STL的接口规则,以便用于STL的算法。 string类的size()/length()方法返回的是字节数,不管是否有汉字。
两者原型如下:
size_type __CLR_OR_THIS_CALL length() const
{ // return length of sequence
return (_Mysize);
}
size_type __CLR_OR_THIS_CALL size() const
{ // return length of sequence
return (_Mysize);
}
可见两者没有区别。
2.capacity()
对这个函数的理解为: 当我们定义了一个string变量,如string str("abcdefg");或string str1="abcdefg";那么编译器就会为它分配空间,而capacity()返回的就是这个空间的大小(按字节算)。通常实际分配的空间比字符串的实际长度要大。这是一种优化,因为当我们再向原串加入一些字符(不超过原来的capacity()值)的话,就不用再次分配空间了。从下面的例子可以看出,当string变得比较大时,空间分配并不再遵循n*16-1这样的规律,空间分配变得不是那么大方了。另外,并不是所有的编译器都会为string多分配空间,比如CodeBlocks12.11上(GCC编译器),string str1 = "ab";cout << str1.capacity() << endl;的结果就是2.
以下结果来自VS2013
#include<iostream>
#include<string>
#include<fstream>
using namespace std;
int main()
{
string str1 = "ab";
cout << str1.capacity() << endl;//15
str1 += "c";
cout << str1.capacity() << endl; //15
str1 += "defghi";
cout << str1.capacity() << endl;//15
str1 += "haohao";//等于15个
cout << str1.capacity() << endl;//15
str1 += "x";//超过15个
cout << str1.capacity() << endl;//31
ifstream readfile("zpc2.txt", ios::in);
if (!readfile){ cout << "程序出现异常,自动退出!" << endl; return 0; }
string str, str2;
while (!readfile.eof())
{
getline(readfile, str2);
str += str2; str += ' ';
}
readfile.close();
cout << str.length() << endl;//913
cout << str.capacity() << endl;//1126
return 0;
}
3.reserve()
原型: void reserve( size_type _Count = 0 );
功能:函数reserve()将字符串的容量设置为至少size. 如果size指定的数值要小于当前字符串中的字符数(亦即size < this→size()), 容量将被设置为可以恰好容纳字符的数值。它最大的 用处是为了避免反复重新分配缓冲区内存而导致效率降低,或者在使用某些STL操作(例如std::copy)之前保证缓冲区够大。但在有些编译器上,reserve()并不怎么起作用。
#include<iostream>
#include<string>
using namespace std;
struct Mystr
{
string str;
Mystr()
{
str = "abcdefiunyhiluyntv5eco8unmomusb nbjhg bj kkiubhno";
str.reserve(20);
}
};
int main()
{
string str1 = "abcd";
str1.reserve(6);
cout << str1.length() << endl;//4 4
cout << str1.capacity() << endl;//15 8
string str2 = "abcd";
str1.reserve(50);
cout << str2.length() << endl;//4 4
cout << str2.capacity() << endl;//15 4
string str3;
str3.reserve(6);
cout << str3.length() << endl;//0 0
cout << str3.capacity() << endl;//15 6
Mystr mystr;
cout << sizeof(mystr) << endl;//28 4
return 0;
}
上面的输出结果中,前一个来自于VS2013,后一个来自于CodeBlocks12.11。
从输出结果来看,reserve()的结果毫无规律可循,并且似乎并没有起到它应有的效果。
所以,根据以上情况,对于capacity()和reserve(),我们的态度是:能不用就不用。即使要用,也要实现确定它们在当前环境下的表现。
4.resize()
原型:
void resize( size_type size, char val = char() );
功能: 改变原有字符串的长度,size指定新长度,当size大于原长度时,多出的部分用val来填充,如果为指定val,则val默认为空格;当size小于原长度时,从开
始起截取size个字符,即相当于把后面的部分删除。
#include<iostream>
#include<string>
using namespace std;
struct Mystr
{
string str;
Mystr()
{
str = "abc";
str.resize(9);
}
};
int main()
{
string str1 = "ab";
str1.resize(6);
cout << str1 << endl;//ab+4个空格 ab+4个空格
cout << str1.length() << endl;//6 6
cout << str1.capacity() << endl;//15 6
string str2 = "abcdefg";
str2.resize(5);
cout << str2 << endl;//abcde abcde
cout << str2.length() << endl;//5 5
cout << str2.capacity() << endl;//15 7
string str3 = "abc";
str3.resize(5, 'a');
cout << str3 << endl;//abcaa abcaa
cout << str3.length() << endl;//5 5
cout << str3.capacity() << endl;//15 6
string str4 = "abcdefg";
str4.resize(5, 'a');//此时'a'将不起作用
cout << str4 << endl;//abcde abcde
cout << str4.length() << endl;//5 5
cout << str4.capacity() << endl;//15 7
Mystr mystr;
cout << sizeof(mystr) << endl;//28 4
return 0;
}
以上两个输出对应的环境同上。
5.max_size()
返回string对象最多可包含的字符数。当程序执行了长度超过max_size()的string操作,编译器会抛出length_error异常。max_size()的值与编译器有关,对于不同的编译器,max_size()的值不一定相同。
#include<iostream>
#include<string>
using namespace std;
int main()
{
string str1 = "abcdefg";
cout << str1.max_size() << endl;//4294967294 1073741820
str1.resize(4294967300);//出现警告 无警告无错误
return 0;
}
以上两个输出对应的环境同上。
C++string中有关大小和容量的函数浅析的更多相关文章
- C++string中用于查找的find系列函数浅析
总述: 以下所讲的所有的string查找函数,都有唯一的返回类型,那就是size_type,即一个无符号整数(按打印出来的算).若查找成功,返回按查找规则找到的第一个字符或子串的位置:若查找 ...
- php中urlencode()和urldecode()URL编码函数浅析[转]
URLEncode:是指针对网页url中的中文字符的一种编码转化方式,最常见的就是Baidu.Google等搜索引擎中输入中文查询时候,生成经过Encode过的网页URL.URLEncode的方式一般 ...
- 从源代码的角度聊聊java中StringBuffer、StringBuilder、String中的字符串拼接
长久以来,我们被教导字符串的连接最好用StringBuffer.StringBuilder,但是我们却不知道这两者之间的区别.跟字符串相关的一些方法中总是有CharSequence.StringBuf ...
- 关于Android中图片大小、内存占用与drawable文件夹关系的研究与分析
原文:关于Android中图片大小.内存占用与drawable文件夹关系的研究与分析 相关: Android drawable微技巧,你所不知道的drawable的那些细节 经常会有朋友问我这个问题: ...
- String中的“equal方法”和“==”
二话不说,先来说下重写的事情: 在Java中,String .Math.还有Integer.Double....等这些封装类重写了Object中的equals()方法,让它不再比较其对象在内存中的地址 ...
- Java的String中的subString()方法
方法如下: public String substring(int beginIndex, int endIndex) 第一个int为开始的索引,对应String数字中的开始位置, 第二个是截止的索引 ...
- Here String 中不该进行分词
我们知道,在 Shell 中,一个变量在被展开后,如果它没有被双引号包围起来,那么它展开后的值还会进行一次分词(word splitting,或者叫拆词,分词这个术语已经被搜索引擎相关技术占用了)操作 ...
- css中的大小、定位、轮廓相关属性
css中的大小.定位.轮廓相关属性 1.通过height.width属性控制组件大小 height:高度,可以设置任何有效的距离值: width:宽度,可以设置任何有效的属性值: max-height ...
- MFC 编辑框中字体大小改变,行高不能改变,只能显示一半的问题,已解决。
CKagulaCEdit是CEdit的一个继承类,m_edit的CKagulaCEdit类型的一个变量 调用的时候,是这样的: 编辑框中字体大小改变,行高不能改变,只能显示一半的问题,问题如下: 这时 ...
随机推荐
- POM.xml的配置实例
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/20 ...
- 关于static 的研究 与递归调用的输出
static的作用 :1.保存上次执行的结果 2.static int m; 这里默认m的初始值为0,即默认 值是0 #include "stdio.h" int fun(int ...
- 给RecyclerView实现的GridView加上HeaderView和FooterView
给RecyclerView设置布局管理器 GridLayoutManager gridLayoutManager = new GridLayoutManager(this, 3); 写适配器,添加子项 ...
- 请求量限制方法-使用本地Cache记录当前请求量[坑]
有个需求:需要限制每个账户请求服务器的次数(该次数可以配置在DB,xml文件或其他).单位:X次/分钟.若1分钟内次数<=X 则允许访问,1分钟内次数>X则不再允许访问. 这类需求很常 ...
- C#使用ajaxForm进行上传图片
<div class='imgOuter addImgBtn l_canshu' id='ImagePath1' value=''> <img src="../Images ...
- Nginx配置(日志服务器中关于日志的产生)
一:概括 1.需要配置的概括 定义日志格式 日志的分割字段:^A 日志格式:IP地址^A服务器时间^A请求参数 配置location,记录请求日志到本地磁盘 将数据按照给定的日志格式存储到本地磁盘 二 ...
- Java学习-048-插件应用之 Find Bugs
FindBugs 是一个静态分析工具,它可以检查类或者 JAR 文件,将字节码与一组缺陷模式进行对比以发现可能的问题,使用 FindBugs 可以在不实际运行程序的情况对软件进行分析.使用时最好将字节 ...
- Python开发【程序】:计算器
开发一个简单的python计算器 实现加减乘除及拓号优先级解析 用户输入 1 - 2 * ( (60-30 +(-40/5) * (9-2*5/3 + 7 /3*99/4*2998 +10 * 568 ...
- curl 查看一个web站点的响应时间(rt)
1. curl 查看web站点rt curl -o /dev/null -s -w %{time_namelookup}::%{time_connect}::%{time_starttransfer} ...
- 【转】Linux下怎样检查、如何查看某软件包是否已经安装?
因为linux安装软件的方式比较多,所以没有一个通用的办法能查到某些软件是否安装了.总结起来就是这样几类: 1.rpm包安装的,可以用rpm -qa看到,如果要查找某软件包是否安装,用 rpm -qa ...