内存函数memcpy和memmove的实现

相对strcpy函数,memcpy等内存函数能够通过指针直接操作传入的目标参数,实现对目标的修改,今天就来讲一下其中memcpy和memmove函数的实现

首先了解函数功能及函数参数

功能:从源内存地址的起始位置开始拷贝若干个字节到目标内存地址中

函数原型:void *memcpy(void *destin, void *source, unsigned n);     即从源地址source拷贝n个字节到目标地址destin中,因此相比strcpy拷贝字符串遇到'\0'就停止,memcpy内存拷贝有更广的应用

函数功能应用:

可以看到arr2中的前四个字节内容fedc被拷贝到了arr1中

接下来考虑memcpy函数实现,首先考虑入参的指针不为空:

assert(destin != NULL && source != NULL);

简写:assert(destin && source);

然后定义一个char类型指针ret接收目标地址用于最后返回(这里注意,考虑到其他int,double等类型的指针操作后解引用,影响内容大于1个字节,内存函数参数都统一强转为char*,方便后续对单字节内存循环拷贝)

char* ret = (char*)destin

最后就是循环每个字节拷贝的过程了,拷贝完后返回

简写:    

while (n--) {
        *((char*)destin)++ = *((char*)source)++;
    }

return ret

最后来个稍微复杂的应用,结构体内存拷贝。字符串整体拷贝,unsigned n参数需要+1拷贝'\0'。

接下来是稍微复杂的memmove实现

功能:memmove函数功能分两种情况,1、当目标空间和源空间没有重叠时,功能与memcpy相同

2、当目标空间和源空间产生重叠时,能在源空间被覆盖前,把要拷贝的字节拷贝到目标空间

简单点说,当目标空间和源空间指向同一块内存区时,比如"ABCDEFG"这个字符串,C为目标空间,A为源空间,拷贝到C之后的内存区域,会改变源空间的存储数据,但memmvoe函数不会受这种影响

函数原型:void *memmove( void* dest, const void* src, size_t count );

函数功能应用:

函数实现:

先断言:assert(dest && src);

接收目标空间地址:char* ret = (char*)dest;

目标空间和源空间没有重叠,即dest<src时,与memcpy一致:

    if (dest < src) {
        while (count--) {
            *(char*)dest = *(char*)src;
            dest=(char*)dest+1;
            src=(char*)src+1;
        }
    }

目标空间与源空间有重叠时:这里需要转变下思维,我们平常拷贝"ABCDEFG"时都是从头开始拷贝,这样会导致源空间在拷贝前被改变,所以我们可以从尾部开始拷贝,因为有count参数,因此我们可以定位到目标空间和源空间的尾部坐标,从后往前拷贝,就能避免上述问题,即:dest+count,src+count

else {
        while (count--) {
            *((char*)dest + count) = *((char*)src + count);
        }
    }
return ret;

函数应用:

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值