目录
在学习使用string库函数的使用技巧里,我记录了字符串函数的一些使用技巧(求字符串长度、字符串拷贝、字符串比较、字符串连接)。这篇文章,将继续为大家梳理一下其他库函数的使用方法。
一、memcpy函数
1、定义与功能:
memcpy函数是string库里一个很重要的函数,它的功能与strcpy有些类似(这一点我们从名字上也可以看得出)。
memcpy的功能是从源内存地址的起始位置开始拷贝若干个字节到目标内存地址中,即从源src中拷贝n个字节到目标dest中。(字节!字节!字节!重要的事情说三遍!strcpy拷贝的是字符!)要注意:memcpy不适用于重叠内存拷贝,这一点要和memmove函数区分开来。
2、具体细节:
int arr1[10] = { 1,2,3,4,5,6,7,8,9,10 };
int arr2[5] = { 0 };
//将arr1内存里初始的20个字节复制到arr2里。
memcpy(arr2, arr1, 20);
由于传输的是void*类型,所以理论上来说,我们内存当中所有类型的数据都可以被拷贝(因为是按字节拷贝,所以只要规定好复制的字节数,两块地址所存放的数据是一模一样的)。这里我们传输的是20个字节,对于int型来说,就是20/4 = 5,所以拷贝的是前五个数字。
验证通过,确实是拷贝了前五个数字(而不是20个,切记memcpy函数是按字符拷贝,接下来mem系列函数都是按照字符数来操作的)。
二、memmove函数
1、定义与功能:
memmove函数其实是功能更加强大的memcpy函数,因为它可以实现重叠地址的移动。
我们可以看到,memmove函数的形参部分都和memcpy函数完全一致,所以memmove函数可以看作是memcpy函数的上位替代函数。(但是在新版本的库当中,memcpy函数也已经可以实现重叠内存拷贝)
2、具体细节:
既然我们已经知道memmove的功能和memcpy函数差不多,那我们就来看一看memmove函数和cpy函数的差异点,即——重叠内存拷贝。
int arr[] = { 1,2,3,4,5,6,7,8,9,10 };
int arr2[] = { 10,9,8,7,6,5,4,3,2,1 };
//将arr2的前20个字节拷贝到 arr+2的偏移位置。
memmove(arr + 2, arr2, 20);
我们来看这段代码,已知memmove函数的作用就是,按字节将源地址的内容,移动到目的地址。我们首先知道移动了20个字节,也就是5个int类型大小的数据。其次,我们是从arr2数组首地址字节开始移动。最后,我们移动的目的地是arr+2即:arr首地址 + 2*sizeof(int) = 8,也就是从第arr[2]开始覆盖。
观察结果,和我们所想的一模一样。
三、strstr函数
1、定义与功能:
strstr函数是用来检查子串的,例如:字符串abcdef中有没有子字符串cde。它也是一个实用性很强的函数。
通过查询MSDN,我们可以得知strstr函数传入的是两个字符串,这个不难理解。传入的是要判断的字符串,和判据子串。而返回值则是一个char* 类型的数据,根据MSDN的举例,我们可知如果含有子串,则返回母串中包含子串的起始位置。如果不含有子串,则返回母串;
2、具体细节:
char arr1[] = "abbbcdef";
char arr2[] = "bbc";
char* ret = strstr(arr1, arr2);
运行上述代码,我们可以猜测结果应该为bbcdef,因为bbc在母串abbbcdef中是存在的,而子串存在时,返回的就应该是子串在母串中的位置。
我们可以看到结果确实为bbcdef,证明我们使用的方法没错。
四、小结
本次介绍的三个函数,是对上次介绍的补充。
在使用memcpy和memmove函数的时候,要时刻记住,mem系列函数,传入的是字节!字节!字节!很多人都因为忽略了传入值为字节的这个细节,导致程序有时候会发生一些意想不到的错误,从而使程序崩溃。