stl-string

简介: stl-string
#include<iostream>
using namespace std;
#include<cstdio>
//string就是管理字符串的类
#include<string>
//库里面定义
template<class T>
class basic_string
{
private:
  T* _str;
  //...
};
//编码 --值--符号建立映射关系--编码表(用值和符号建立对应关系) 
// ASCILL编码表---表示英文编码
// unicode ---(包含ascill)表示全世界文字编码
//又包含utf -8,utf-16 
//gbk        --     中国自己量身定做的编码表
// 汉字可以用2个字节,
// 
//typrdef basic_string<char> string,我们用的是typedef后出来的,模板的
//int main()
//{
//  string s1("hello");
//  char str2[] = "吃饭";
//  cout << sizeof(char) << endl;
//  cout << sizeof(wchar_t) << endl;//2个字节,wstring
//
//  return 0;
//}
//初始化
void init()
{
  string s1;//无调用构造函数
  string s2("hello world");//构造函数
  string s3(s2);//拷贝构造
  //cin >> s1;
  cout << s1 << endl;
  cout << s2 << endl;
  cout << s3 << endl;
  //substring (3) 
  //string(const string & str, size_t pos, size_t len = npos);
  //利用字串进行初始化,pos是从0开始,从string里面先后数len个长度进行拷贝
  string s4(s2, 2, 6);
  cout << s4 << endl;//llo wo
  string s5(s2, 2);//默认从坐标为2的地方往后截取所有的s2
  cout << s5 << endl;//ello world
  //string (const char* s, size_t n);
  string s7("hello world", 3);//取前3个字符
  cout << s7 << endl;
  //string(size_t n, char c);连续弄n个c
  string s8(3, '!');//!!!
}
void func()
{
  string s1("hello");
  //不计算‘\0’,这两个对于string没什么区别,size是后出现为了保证容器的一致性
  cout << s1.size() << endl;//5
  cout << s1.length() << endl;//5
  cout << s1.max_size() << endl;//没什么意义
  cout << s1 << endl;
                  //计算容量
  cout << s1.capacity() << endl;//15
  s1.clear();//把有效数据都清理掉,空间保留,变成空字符串,0个字符
  cout << s1 << endl;
  cout << s1.capacity() << endl;
  if (s1.empty())//判断此字符串是否为空,即是否长度为0
  {
    cout << "not" << endl;
  }
}
//char& operator[] (size_t pos);这里的引用返回是因为这个数组是在堆上开辟的,出了作用域还在,并且可以对其中的字符进行修改,或者调用,还可以减少拷贝(不是主要目的)
void operatoracess()
{
  string s1("hello world");
  for (size_t i = 0; i < s1.length(); i++)
  {
    cout << s1[i];//[]是断言终止程序,检查错误
    s1[i] += 1;
  }
  cout << endl;
  for (size_t i = 0; i < s1.length(); i++)
  {
    s1.at(i) -= 1;//和上面是一样的
    cout << s1.at(i) << endl;//at是抛异常检查错误,建议还是使用[ ]
  }
  cout << endl;
}
//对字符串进行尾部添加字符或字符串
void add()
{
  string s;
  s.push_back('a');
  s.append("bcde");//尾插bcd
  cout << s << endl;//abcd
  s += '!';//也可以利用运算符重载进行实现尾插,推荐,abcd!
}
//只交换字符
//abc-bcd-qwlkj变成 jkl-wqd-cbcba  
//
class Solution {
public:
  //计算最后一个单词的长度如“hello world  ”g
  int lengthOfLastWord(string s) {
            int end=s.size()-1;
                    while(s[end]==' ')
                    {
                                  s.erase(end,1);//无法使用
                                              end--;
                    }
                    size_t pos=s.rfind(" ");
                    string sub=s.substr(pos+1);
                    return sub.size();
  }
};
//遍历,1.迭代器2.范围for
void test_string1()
{
string s1("hello");
string::iterator it=s1.begin();//s1.begin(),是第一个数据的地址,s1.end()是最后一个数据的后一个的地址
//这个iterator是定义在string里面,it现在指向了第一个数据的地址
//现在可以先想象成一个像指针一样的类型
//
while(it!=s1.end())//直到结尾就结束了,但是不建议用<
{
  cout<<*it<<" ";//*就是取他的数据
  ++it;//到下一个地址
}
cout<<endl;
//除了可以读还可以写
 it=s1.begin();//s1.begin(),是第一个数据的地址,s1.end()是最后一个数据的后一个的地址
//这个iterator是定义在string里面,it现在指向了第一个数据的地址
//现在可以先想象成一个像指针一样的类型
//
while(it!=s1.end())//直到结尾就结束了
{
  *it-=1;//*就是取他的数据
  ++it;//到下一个地址
}
cout<<endl;
//范围for,auto可以自动识别
//for(auto e:s1)//把s1里面每个字符取出来赋值给e,不需要自己++,自动判断结束
//{
//  cout<<e<<" ";
//}
cout<<endl;
//要修改就要用引用
//for(auto& e:s1)
//{
//  e-=1;
//}
cout<<endl;
//反向迭代器
//倒着遍历
string::reverse_iterator rit=s1.rbegin();//rbegin(),是最后一个数据的地址
//为了简化代码也可以直接auto推到
//
//auto  rit=s1.rbegin()
//
while(rit!=s1.rend())//rend()是第一个数据的前一个地址
{
  cout<<*rit<<" ";//olleh,反过来遍历
  ++rit;//反向迭代器的++,是往左走的
}
cout<<endl;
//迭代器遍历的意义是什么呢:所有的容器都可以用迭代器这种访问修改
//1.对于string类来说,利用[]都足够好用,确实可以不用迭代器
//2。对于其他容器(数据结构)也可以使用,如list,map,set,这些是不支持[],因为只有像数组一样的东西才支持[]遍历和下标,
//结论::对于string得会用迭代器,但是我们还是喜欢下标加[],
//还有const迭代器,普通迭代器是可读可写的
string cstr("hello world");
//funcion(cstr);
string::const_iterator re=s1.begin();//只读不写,同理还有反向迭代器
//cbegin()就是const迭代器,但是我们平时都不太用,
}
//对于容量的函数
void test_string3()
{
string s1;
s1.reserve(100);//可以设置容量的大小,容量就是100,加上原来的容量
string s2;
s2.resize(100,'x');//也是可以设置容量的大小,同时还可以对其进行初始化,如将s1有效数据的后面全部设置成x,如果没有第二个参数,则默认是‘\0’
}
//对于find,c_str ,rfind的认识与理解
void test_string2()
{
string s2="hello world";
cout<<s2.c_str()<<endl;//将string转变成c语言的形式字符串,char*,以\0截至
string file("test.txt");
//我们要以c语言的形式打开一个文件
//FILE* fout=fopen(s2.c_str(),"w"); //fopen第一个参数是char*,所以用这函数
//要求取出文件的后缀
  size_t pos=file.find('.');//在file里面查找‘x’的位置,find的返回值是size_t,下标从0开始,查找第一个符合的坐标,否则就返回-1
string s1(file,pos);
cout<<s1<<endl;
if(pos!=string::npos)
{
  string suffix=file.substr(pos);
cout<<suffix<<endl;
}
//rfind()//可以从后面完前找,找到第一个.,方便找后缀名
//https://blog.csdn.net/m0_61567378?spm=1000.2115.3001.5343
string url("http://blog.csdn.net/m0_61567378?spm=1000.2115.3001.5343");
//找协议头
size_t pos1=url.find(':');//:前面的就是协议头
string protocol=url.substr(0,pos1-0);//取得字串就是从0开始,到pos1位置,长度为pos1的字串,也就是http
cout<<protocol<<endl;
//找域名,
size_t pos2=url.find('/',pos1+3);//find默认从0开始找,现在我们给定他从pos1+3位置处开始找,也就是b开始,往后找,找到/的位置
string domain=url.substr(pos1+3,pos2-pos1-3);
cout<<domain<<endl;
//统一资源定位
string uri=url.substr(pos2+1);
cout<<uri<<endl;
}
//
void test_string4()
{
//insert不太推荐用,O(n),效率低
  string s="hell";
  s.insert(0,"owlod");//在头上插入一个owlod,是从第0个位置往后插入
  s.insert(0,1,'x');//在头上插入一个x,是
  s.insert(4,"xx");//从第4个位置往后插入xx
  cout<<s<<endl;
  //要挪动数据效率很低,
  s.erase(4,2);//从4位置,删除两个长度的字符
  cout<<s<<endl;
  s.erase(s.size()-1,1);//尾删
  s.erase(3);//第二个参数不给值就后面全部都删除了
  //尾删也可以
//s.pop_back();
//输入一整行的数据,包括‘ ’
getline(cin,s);//第一个参数是流 
}
void test_string5()
{
  string s1="hello";
  string s2="string";
  cout<<(s1<s2)<<endl;//h<s所以就是小于
  cout<<("hello"<s2)<<endl;//char*的也可以比较
  cout<<(string("hello")<s2)<<endl;//这样也是可以的
}
//字符串与整形的转化
void test_string6()
{
  int val=stoi("1234");//转变成int
  cout<<val<<endl;//1234
  double val1=stod("123");
  //转变成字符串
  string str=to_string(12.345);
string s=to_string(123456);
  string str = to_string(12.345);
}
//浅拷贝,完成值拷贝,将每个字节一起拷贝
//对于指针类型的就不可以靠浅拷贝
//浅拷贝抄作业连名字都没改,完完全全的抄
//深拷贝就是抄作业改了名字,不完全的抄
//
classm  my_string 
{
  private:
    char* _str;
  public:
    //构造函数
    my_string(const char* str)
    :_str(new char[strlen(str)+1])
    {
strcpy(_str,str);
    }
    //拷贝构造要用深拷贝
    my_string(const my_string& s)
      :_str(new char[strlen(str)+1])
    {
      strcpy(_str,s.str);
    }
}
void test_string7()
{
}
int main()
{
//  init();
//  func();
//  operatoracess();
//  add();
//  Solution sl;
//  sl.reverseOnlyLetters("Test1ng-Leet=code-Q!");
//test_string1();
//test_string3();
//test_string2();
//test_string4();
Solution ts;
string s="hello world  ";
//int k=ts.lengthOfLastWord(s);
//cout<<k<<endl;
//test_string6();
string s1 = "A man, a plan, a canal: Panama";
isPalindrome(s1);
return 0;
}
相关文章
|
11月前
|
算法 安全 C语言
【剖析STL】String(一)
1.什么是STL? 标准模板库(Standard Template Library,STL)是惠普实验室开发的一系列软件的统称。它是由Alexander Stepanov、Meng Lee和David R Musser在惠普实验室工作时所开发出来的。虽说它主要出现到C++中,但在被引入C++之前该技术就已经存在了很长时间。
38 0
|
28天前
|
存储 算法 程序员
【STL】string
【STL】string
|
4月前
|
C++ 容器
STL—vector、string
STL—vector、string
|
11月前
|
编译器 C语言 C++
【C++】STL---string
【C++】STL---string
30 0
|
4月前
|
存储 编译器 C++
C++:STL - string
C++:STL - string
72 1
|
11月前
|
算法 Linux C语言
【C++】从string开始了解STL(上)
【C++】从string开始了解STL(上)
|
10月前
|
编译器 C++ 容器
STL - string
STL - string
40 0
|
11月前
|
存储 C++ 容器
【剖析STL】String(二)
2.3.2string类对象的容量操作 本部分会介绍以下几个容器操作:
42 0
|
11月前
|
Linux C语言 C++
【C++】从string开始了解STL(下)
【C++】从string开始了解STL(下)
|
存储 算法 编译器
C++【STL】之string的使用
C++ STL string类常用接口详细讲解,干货满满!
70 0
C++【STL】之string的使用