Пожалуйста, посмотрите на это необъяснимое поведение и вывод memcpy () для перекрывающихся блоков памяти

Прочитав следующее оmemcpy()Я начал читать оmemmove():

To avoid overflows, the size of the arrays pointed by both the destination and source parameters, shall be at least num bytes, and should not overlap (for overlapping memory blocks, memmove is a safer approach).(ССЫЛКА)

И после проверки программа, используемая для иллюстрации работыmemmove() Я решил настроить его с помощьюmemcpy() вместо этого, чтобы увидеть, насколько отличается результат. К моему удивлению, они являютсятакой же даже если это случай перекрывающихся блоков памяти. Вот программа и вывод, и я приступил к описанию своей путаницы после этого:

#include <stdio.h>
#include <string.h>

int main ()
{
  char str[] = "memmove can be very useful......";
  //memmove (str+20,str+15,11);
  memcpy(str+20,str+15,11);  //Simply used memcpy instead of memmove
  puts (str);
  return 0;
}

Выход memmove can be very very useful.

Этот вывод такой же, как и дляmemmove(). И вот мои заблуждения:

1) Почему вывод одинаков для обоих? Поскольку промежуточный буфер не используется в случаеmemcpy()Я ожидаю, что копирование начнется с копирования символа вstr+15 положение кstr+20 позиция (перезаписывая что там), персонаж вstr+16 положение вstr+21 положение и так далее досимвол в позиции str + 20, который теперь заменен на символ в позиции str + 15, который будет скопирован в позицию str + 25.Но это не так, здесь нет перезаписи, и он действует так, как будто промежуточный буфер используется для записи точной исходной строки. Вот иллюстрация:

memmove can be very useful......  //Original positions before memcopy
               ^    ^
            str+15  str+20

memmove can be very vseful......
                    ^ copies str+15 to str+20

memmove can be very veeful......
                     ^ copies str+16 to str+21
memmove can be very verful......
                      ^ copies str+17 to str+22
memmove can be very veryul......
                       ^copies str+18 to str+23
memmove can be very very l......
                        ^ copies str+19 to str+24
memmove can be very very v......
                         ^ I expect 'v' to be copied from str+20 to str+25
                           as str+20  now has 'v',not 'u'
memmove can be very very ve.....
                          ^ I expect 'e' to be copied from str+21 to str+26 
                            as str+21 now has 'e' not 's'

Тогда почему memcpy () копирует его какmemmove может быть очень, очень полезным, вместоmemmove может быть очень очень очень V ?

2) Теперь второстепенный вопрос, вытекающий из этого.memmove() (ССЫЛКА)

Copying takes place as if an intermediate buffer were used, allowing the destination and source to overlap.

Что именноas if здесь? Не является ли промежуточный буфердействительно используется дляmemmove()?

Ответы на вопрос(1)

Ваш ответ на вопрос