![](/img/trans.png)
[英]In what platform memmove and memcpy can have significant performance difference?
[英]Performance of memmove compared to memcpy twice?
我已经看到了接受的答案中指出的区别:memmove和memcpy有什么区别? 它说memmove might be very slightly slower than memcpy
。
我们可以通过以下方法实现memmove
的替代方案:分配一个临时缓冲区,然后两次memcpy
(src-> tmp,tmp-> dest)。 我的问题是:哪种方法更快,更memmove
或其他选择?
来自http://en.cppreference.com/w/cpp/string/byte/memmove
尽管已指定“好像”使用了临时缓冲区,但此功能的实际实现不会产生重复复制或额外内存的开销。 如果数量较少,则可能会加载并写出寄存器。 对于较大的块,一种通用的方法(glibc和bsd libc)是如果目标在源之前开始,则从缓冲区的开始向前复制字节,否则从末尾向后复制字节,然后在到达时复制回std :: memcpy完全没有重叠。
因此,开销很可能是几个条件分支。 大块几乎不值得担心。
但是,值得记住的是std::memcpy
是一个“魔术”函数,是在两种不同类型之间进行转换的唯一合法方法。
在c ++中,这是非法的(未定义的行为):
union {
float a;
int b;
} u;
u.a = 10.0;
int x = u.b;
这是合法的:
float a = 10.0;
int b;
std::memcpy(std::addressof(b), std::addressof(a), size(b));
如果您是C程序员,并会执行工会希望做的事情。
std::memmove
“可能比非常稍慢 std::memcpy
”(强调),因为它必须首先检查源和目标范围是否重叠。 在内部,这只是几个指针比较。 完成此操作后,如果没有重叠或目标在源下方开始,它将调用std::memcpy
; 否则,它将调用std::memcpy
的变体,该变体从末尾开始复制。
简而言之, 唯一的区别是初始比较。 一旦完成,就像std::memcpy
。 无需额外的缓冲区,无需复制所有内容两次。
Memcpy通常更快,因为它不假定目标和源可能重叠。
因此,如果尝试使用memcpy将字符串abcd
从位置X
复制到X+2
,则可能会得到类似的结果
X: A B C D
在memcpy之后
X+2 A B A A
而memmove可以确保您不会丢失任何内容,因为它使用中间缓冲区存储原始字符串。
另一方面,您可以对源和目标使用限定符restrict
,这样您可以告诉记忆源和目标不重叠,并且像记忆可以在使用该限定符的情况下选择其他更快的算法。
有关详细信息,请参见此处 。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.