C语言内存函数(memcpy、memmove、memcmp)详解

一、memcpy(string.h)

1.介绍

memcpy函数为内存拷贝函数,既可以拷贝字符串,也可以拷贝整形数组、浮点型数组等,具有明显的应用优势,

destination为目的地空间,source为不可修改(const)的来源空间,num表示无符号的字节数。其主要含义为将source内容拷贝到destination中,拷贝num个字节数。其返回类型、目的地、来源类型均为void* ,void*可以接收任意类型的参数。因为它可以拷贝多种不同类型的内容,运用单一的类型,就限制了其拷贝的内容了。size_t表示无符号数。

返回时会返回目的地的起始位置地址。

下面我们通过几个例子了解一下它的用途。

2.例子

2.1 例一

 通过例一我们发现,memcpy函数将arr1的前5个字节数拷贝进了arr2数组中因为char类型的变量所占的字节数为1,所以abcde都拷进了arr2中。返回值为arr2数组的起始位置的地址。

2.2 例二

例一和例二的不同点在于多拷贝了一个字节,将arr1中的字符''拷进了arr2中,因此在打印arr2数组时遇见了拷贝进去的字符'',因此它只会打印''之前的内容,所以打印出的结果为abcde。

这也就说明了内存拷贝函数memcpy不会去管拷贝内容究竟是什么,只要没到达我拷贝的字节数,那就嘎嘎拷贝就完了。

2.3 例三

例三不为字符的拷贝了,为整形数组的拷贝,与浮点数拷贝两者相同。 也是将arr1中的前20个字节数,也就是5个整形变量,拷贝进了arr2中,其主要关键的点在于20表示的意思为前20个字节数。当然,如果你拷贝前19个字节,就会出现一些问题,所以拷贝时尽量按照一个变量所占字节数的整数倍来进行拷贝。

2.4 例四

我们预期结果为1 2 1 2 3 4 5 8 9 10 但实际结果为1 2 1 2 1 2 1 8 9 10。因此达不到我们预期结果。

这是因为我们想将12345拷贝进34567之中,所以1拷贝代替了3,2拷贝代替了4,此时3和4被变成了1和2,那么再拷贝3和4进5和6时,就是1和2拷贝进5和6了,剩下的拷贝也是如此。

应注意,此时目的地空间和来源空间有重叠空间,因此memcpy函数不支持有重叠内存空间的拷贝的,此时我们就需要另一个函数memove来帮助我们处理有重叠空间的内存拷贝。

二、memove(string.h)

1.介绍

memove函数为内存移动函数,也就是将来源空间内容移动到目的地空间之中。相当于拷贝。

 其参数类型和返回值和memcpy完全相同,其含义为将source(来源)前num个字节数空间的内容移动到destination(目的地)空间之中,和拷贝含义几乎相同。这就过多介绍了。其用法也基本相同,只不过,memmove函数可以处理重叠内存空间的拷贝。

直接看实例

2.例子

只看一个例子即可,就是重叠内存空间的处理,其他处理和memcpy函数相同。

 

 可以看到,memmove函数可以处理重叠内存空间的拷贝(移动)。因此在使用memcpy和memmove两个函数时要注意其应用条件。

三、memcmp(string.h)

1.介绍

memcmp函数为内存比较函数,其与字符串比较函数strcmp函数相像,不同的是memcmp函数可以既可以比较整形、浮点型,也可以比较字符串。

因为是比较函数,所以原来的空间内容是不可被修改的,只能用于比较,因此前两个参数都用了const做修饰。其可以接收任意类型的参数。其基本含义为比较两个空间前num个字节数内容大小,返回值类型为整形,若ptr1 > ptr2,则返回大于0的数字,若等于,则返回0,若小于,则返回小于0的数字。

2.例子

 

 比较arr1和arr2前9个字节空间的内容,而arr1和arr2前九个字节相同,因此返回0。

而比较前10个字节的时候,arr2的第10个字节内容大于arr1第10个字节的内容的,因此返回-1,表示arr1小于arr2。

综上,三大内存函数就已完全结束。