2011-09-16 17 views
9

El segundo arg en los prototipos para memmove/memcpy/strcpy son similares: Por ejemplo:¿Qué significa "const void *" en memmove?

void *memmove(void *dest, const void *src, size_t n); //const void* 
char *strcpy(char *dest, const char *src); //const char* 

Pero, al parecer, si dest y la superposición src, entonces el contenido de src serán alteradas, violar la const vacío/char *?

Respuesta

20

const void* significa que la referencia no se modificará a través de ese puntero.

Si hay otros punteros que no son const para el mismo objeto (también conocido como "aliasing"), entonces, por supuesto, aún se puede modificar a través de ellos. En el escenario que describe, ese otro puntero es dest.

Por cierto, en el caso de strcpy, el comportamiento no está definido si las regiones se superponen, y en C99 la firma es char *strcpy(char * restrict s1, const char * restrict s2);. Pero para memmove, aliasing está bien. Al otorgarle regiones superpuestas, le ha otorgado "permiso" para modificar la región dest y lo hará.

+0

estoy de acuerdo, eso es correcto. – Alcott

+0

¿quieres decir, si no puedo asegurarme de si el destino y el src se superponen o no, será mejor que no use strcpy, ¿verdad? – Alcott

+1

@Alcott: eso es correcto. Lo que probablemente verás en la práctica es que si tus regiones se superponen con 'dest

4

Significa memmove garantiza que no directamente modifica la memoria apuntada por src.

Por supuesto, si los dos bloques se superponen memmove se cambiará la memoria llamada "const". const es un contrato adjunto a un nombre. No hay forma de hacer que la memoria real sea de solo lectura.

+0

@downvoter ¿Nos importa? – cnicutar

+0

Se ha eliminado el voto a la baja según sus ediciones. –

+0

@Praetorian A menudo no sé de lo que estoy hablando pero me gustan los comentarios, así que puedo aprender :-) – cnicutar

7

El argumento está marcado const void * para indicar memmove nunca modificará la memoria apuntada por src usando ese puntero. Si se produce superposición, la memoria se modifica utilizando el puntero dest, no el puntero src, por lo que no se infringe la garantía.

3

Como el memove anterior no modificará el contenido de la memoria a través del puntero "src" sino que lo hará a través del puntero "dest".

La const se refiere a cómo se usan los punteros, no agrega ninguna protección de memoria.

Si ambos punteros apuntan a una región de memoria superpuesta, puede pasar cualquier cosa, ya que no está definida si la copia comenzará desde "src" e incrementará o comenzará desde "src + n" y disminuirá.

+0

disculpa por parecer una respuesta repetida por He publicado al mismo tiempo que el anterior fue editado –

+0

ese tipo de cosas suceden todo el tiempo, no es un problema. Generalmente hay diferencias sutiles en las respuestas, incluso cuando son sustancialmente iguales, y a menudo es bastante útil tener varias explicaciones de lo mismo: un lector entenderá mejor a uno de ellos, alguien más entenderá otro. –

Cuestiones relacionadas