为女朋友做网站,陈铭生我来找你了,霸州市网站建设,怎么把个人做的网站上传到网上函数原型及作用
memcpy 和 memmove 都是C语言中的库函数#xff0c;在头文件string.h中#xff0c;作用是拷贝一定长度的内存的内容#xff0c;原型分别如下#xff1a;
void* memcpy(void *dst, const void *src, size_t count);
void* memmove(void *dst, const void *…函数原型及作用
memcpy 和 memmove 都是C语言中的库函数在头文件string.h中作用是拷贝一定长度的内存的内容原型分别如下
void* memcpy(void *dst, const void *src, size_t count);
void* memmove(void *dst, const void *src, size_t count);
他们的作用是一样的唯一的区别是当内存发生局部重叠的时候memmove保证拷贝的结果是正确的memcpy不保证拷贝的结果的正确。 第一种情况下拷贝重叠的区域不会出现问题内容均可以正确的被拷贝。第二种情况下问题出现在右边的两个字节这两个字节的原来的内容首先就被覆盖了而且没有保存。所以接下来拷贝的时候拷贝的是已经被覆盖的内容显然这是有问题的。
实际上memcpy只是memmove的一个子集。
二者的c语言实现很简单有兴趣的朋友可以去看看。在实际情况下这两个函数都是用汇编实现的。
memmove在copy两个有重叠区域的内存时可以保证copy的正确而memcpy就不行了但memcpy比memmove的速度要快一些如 char s[] “1234567890”; char* p1 s; char* p2 s2; memcpy(p2, p1, 5) 与 memmove(p2, p1, 5) 的结果就可能是不同的memmove()可以将p1的头5个字符12345正确拷贝至p2而memcpy()的结果就不一定正确了
变态的命名
我们在写程序时一般讲究见到变量的命名就能让别人基本知道该变量的含义。memcpy内存拷贝没有问题;memmove内存移动错如果这样理解的话那么这篇文章你就必须要好好看看了memmove还是内存拷贝。那么既然memcpy和memmove二者都是内存拷贝那二者究竟有什么区别呢
memcpy
你有没有好好的参加过一场C笔试。让你写出memcpy的实现这是多么常见的笔试题啊。现在拿起你的演算纸和笔;是的是笔和纸不是让你在你的IDE上写。写不出来看下面吧
void *memcpy(void *dest, const void *src, size_t count)
{assert(dest ! NULL src ! NULL);char *p (char *)dest;char *q (char *)src;if (p q)return p;while (count--){*p *q;}return des;
}
memcpy的实现很简单一般在笔试时出现写源码的题目无非就是需要注意以下几点
确定函数原型;判断参数合法性;逻辑实现考虑各种情况统称逻辑实现;错误处理。
当然了我的这个没有错误处理也不需要错误处理。上面我写出了memcpy的实现源码实现原理如下图所示 这样下去上面的代码会运行的很好如果出现下面的情况呢 i、n、k的内存和J、e、l的内存地址重合了现在再使用上面的代码进行copy时会出现什么问题呢你有没有想过这个问题。如果没有那就现在想想不急着阅读下面的内容。
然后我再留一个问题上面的代码中为什么都需要将void *转换成char *呢
memmove
memmove也是用来实现内存的直接拷贝的。说起这个命名我个人觉的多少还是有点坑的。既然memmove也是用来内存数据移动的那就先来看看memmove的实现源码。
void *memmove(void *dest, const void *src, size_t count)
{assert(dest ! NULL || src ! NULL)if (dst src){char *p (char *)dest;char *q (char *)src;while (count--){*p *q;}}else{char *p (char *)dest count;char *q (char *)src count;while (count--){*--p *--q;}}return dest;
}从源码看memmove的确比memcpy复杂一些;再仔细一看多了些什么哦多了一个else分支而正是这个else分支就处理了当src和dest的内存重合的问题。
memcpy和memmove的比较
从实现源码中的确能看出一些猫腻当出现了src和dest的内存有重合的时机时memmove的处理规则是从后往前进行copy。当然了重合的问题需要考虑的以下两种场合。
如图所示当出现(1)对应的情况时就需要先从src的头部开始复制;也就是memmove源码中的if分支这部分源码和memcpy的实现是一致的;当出现(2)对应的情况时就需要先从src的尾部开始复制防止出现了覆盖现象。这就是memmove比memcpy多的一个考虑点所以说在实际使用时使用memmove是比memcpy更安全的。