#### 写在前面
c++中兼容了c中处理字符串的方法,使用相关函数时要调用库 string.h 或者 cstring 两者是等同的,c++自己的是库string。
字符数组类型 C-string方法
1.是什么
字符数组类型实际上是开辟一系列的连续储存单元,把字符连在一起储存。
2.定义,初始化
定义如下:
数组的大小必须为常量或者常变量或者常量表达式。
char str1[10];//10可以替换为需要的数组大小
const int a=10;
char str2[a];//a是常变量
#define b 10
char str3[b];//b是符号常量
#define c 5
const int d=5;
char str4[0+c+d];//常量表达式
int c=10;
char str5[c];//有的编译器能够通过的,但是不要这样做。
原理如下:因为定义数组的时候会给数组开辟指定的储存空间,下标要用来指定开辟空间的大小,如果是变量,那么开辟的空间是可能改变的,会容易使得数据存储出现问题。
初始化如下:
char str6[10]="0123456";//末尾有\0
char str7[10]={ '0','1','2','3','4','5','6'}//其实就是对每一个数组元素赋值
这种赋值方法末尾不会自动加\0,但是数组初始化时每个位置都是\0。所以结果还是\0结尾。但是要注意数组满时,末尾加一可能不是\0,这是可能出现输出错误,或者其他功能的错误。
3.连接,复制,比较,求长度
这些功能可以自己编写函数来实现功能,需要用到:
1.字符串末尾为\0
2.ASCLL码的比较大小
但是c++中有对c继承了实现这些功能的函数。
下面的功能需要包含库 string.h或者string
连接
1.str2连接到str1后面
strcat(str1,str2);//把str2接到str1后面
这种做法当str2接在str1后面越界时可能出现错误。
2.把str2的前n个字符连接在str1的后面
const int n=1;
strncat(str1,str2,n)//n必须为常量,常变量,常量表达式
复制
1.把str2复制到str1
strcpy(str1,str2);
2.把str2的前n个复制到str1
const int n=1;
strncpy(str1,str2,n);//n必须为常量,常变量,常量表达式
p.s.
注意:str1后面的未被str2覆盖的位置没有改变。
strcpy复制时末尾的\0是跟着复制的
strncpy复制时可以指定不复制\0,然后实现替换str1的前n个的操作
比较
1.str1和str2
int p1=strcmp(str1,str2);
2.str1和str2 两者的前n个
int p2=strncpm(str1,str2,n);
p.s.
注意:
strcmp和strncmp 是有返回值的。
返回值等于0,比较部分是相同的
返回值大于0,比较部分str1的ASCLL值大于str2
返回值小于0,比较部分str1的ASCLL值小于str2
比较原理如下:
从前往后依次比较,一位一位的比较,比较的是ASCLL值。如果相同则往后比较,直到两个都为\0时为止,否则在不相同的地方就返回。
求长度
int len=strlen(str);
注意:
长度并不包含\0。也就是说,如果在字符串中间插入了一个\0 就会使得计算长度时到这儿就停止了。
4.函数调用
1.多维数组做形参
一维:
char str[10];
void set(char a[])//此处传递的只是数组的首地址
{
//此处省略
}
int main()
{
set(str);//传入的是str的地址
}
p.s.
1.形参可以为 a[2] a[234] ,应为只取首地址,与后面的数无关
2.实参应传入str的首地址
3.字符数组的名字就是该字符串的首地址
二维:
char str[10][10];
void set(char a[][10])
{
//此处省略
}
int main()
{
set(a);
}
p.s.
1.形参同上得原理使用a[2][10],或者a[34][10];
2.除第一维之外,更高维的大小是不能够省略的,因为在内存里面开辟的空间是连续的,如果更高维的大小,那么就会无法正常读取数据;
3.同样的传入的只是数组的首地址
总结:其实函数传递的一个参数只能对应一个变量,而不是一次传递很多个。传递数组时,传递的实际上时数组的首地址,所以对于第一维的大小是不用指定的。同理也可以得到其他类型的数组的函数传递方法是类似的。
5.读入单个字符&读入一整行
读入单个字符
1.不读入空格,换行符,制表符。
#include<iostream>
using namespace std;
int main()
{
char a;
cin>>a;
return 0;
}
直接使用标准的输入输出流会自动过滤掉空格,换行符,制表符
2.读入空格,换行符,制表符。
#include<cstdio>
using namespace std;
int main()
{
char a;
a=getchar();
return 0;
}
getchar() 最开始是在c的标准输入输出的库里面的。c++为了兼容c就有了cstdio。
c++的标准库是iostream,c的标准库是stdio.h。iostream为了兼容是包含有getchar()函数的。
下面我们来看c++的操作
#include<iostream>
using namespace std;
{
char a;
cin.get(a);//或者
a=cin.get();
}
注意:getchar()和cin.get()函数的返回值都是字符的ASCLL码的值。
读入一整行
1.不读入空格,换行符,制表符。读入的字符串遇到以上三种字符就会终止
#include<iostream>
using namespace std;
int main()
{
char a[10];
cin>>a;
return 0;
}
直接使用标准的输入输出流会自动过滤掉空格,换行符,制表符
2.读入空格,换行符,制表符。
#include<cstdio>
using namespace std;
int main()
{
int a[10];
cin.get(a,10,'\n');//结束符可以为任意字符
cin.getline(a,10,'\n');//两个的写法相同
return 0;
}
注意:
当第一个输入的字符为结束符时,后面的cin输入会出错,这个时候可以用cin.get()来读入一个空字符来解决。
6.输出
单个字符
1.标准输入输出
char a='a';
cout<<a;
2.cout.put()和putchar()
char a='a';
cout.put(a);
putchar(a);
两个是相同的,cout.put()来自c++,putchar()来自c
字符串
1.标准输入输出
char a[10]="abcdefg";
cout<<a;
2.一个一个的输出
char a[10]="abcdefg";
for(int i=0;a[i]!='\0';++i)
cout<<a[i];
string类型 string方法
1.实现原理
string叫做字符串类型。string不是c++里面的有的基本类型(int ,char ,float,double),他是一个用类来定义的一个类型。(class)
2.定义,初始化
string str1;
str1="abcde";
str1("abcde");//也可以写成这个样子 像函数调用的感觉
和基本变量的定义初始化相似,不赘述。
3.连接,复制,比较,求长度
连接
string str1,str2;
str1="abcd";
str2="efg";
str1=str1+str2;//执行完这句后 str1="abcdefg" 像做加法
加号号可以实现两个字符串的连接。把加号后面的字符串连接到加号前面的字符串后面。
复制
string str1,str2;
str1="abcd";
str2="efg";
str1=str2;//执行完这句后 str1="efg" 像赋值
注意:这个复制之后是全覆盖,之前str1中的字符全部没了。和字符数组不一样,字符数组是会保留未被处理处的字符。
比较
可以直接使用关系运算符来比较,比较原理为依次比较,按ASCLL值比较。
求长度
string s;
int len;
len=s.length();
len=s.size();
要使用string库,处理string类型的函数在string库里面
4.函数调用
void a(string s)
{
//省略
}
void b(string s[][2])
{
//省略
}
int main()
{
string str1,str2[2][10];
a(str1);//str1不被改变
b(str2);//str2被改变
}
同字符数组的传入规则相同,如果不明白往上翻。
需要注意的是:
1.如果只是传递单个的string 字符串,那么在被调函数中改变string 字符串的值时,主调函数中的string 字符串的值是不变的;
2.如果传递的是string 的数组,那么同数组的调用原理一样,函数间传递的是string 字符串的首地址。
5.读入一整行
string 类型的变量支持两种输入方式
1.标准输入
使用cin像基本的变量一样输入,输入时是忽略空格,制表符,换行符的。
2.getline
使用这个函数需要用到 string 库
#include<string>
string s;
getline(cin,s,'\n');
getline(输入流,字符串地址,结束符)
- 输入流不一定是标准输入流cin,还有文件输入等
- 字符串地址为字符串的名字
- 结束符可以任意指定字符,结束后不会放到缓冲区里面,默认的结束符是’\n’
- 特别注意如果要用结束符’\n’ 时,直接用默认的即可,否则容易出错。
这儿我们不讨论读入单个字符,直接标准输入就可以 cin
6.输出
使用标准使出cout即可。
p.s. 总结
– 函数之间数组值的传递 (一维到n维)
- 两种字符串的基本操作 (定义,赋值,比较,连接,复制等)
- 读入错误的处理(cin.get()读入空字符)
- 输入输出 (一整行和单个字符)