Entiendo cómo funciona malloc (). Mi pregunta es, veré cosas como esta:
#define A_MEGABYTE (1024 * 1024)
char *some_memory;
size_t size_to_allocate = A_MEGABYTE;
some_memory = (char *)malloc(size_to_allocate);
sprintf(some_memory, "Hello World");
printf("%s\n", some_memory);
free(some_memory);
Omití la comprobación de errores en aras de la brevedad. Mi pregunta es, ¿no puede hacer lo anterior inicializando un puntero a algún almacenamiento estático en la memoria? quizás:
char *some_memory = "Hello World";
¿En qué punto realmente necesita asignar la memoria usted mismo en lugar de declarar / inicializar los valores que necesita retener?
c
memory
memory-management
randombits
fuente
fuente
malloc()
puede fallar.Respuestas:
está creando un puntero a una constante de cadena. Eso significa que la cadena "Hello World" estará en algún lugar de la parte de solo lectura de la memoria y solo tiene un puntero hacia ella. Puede usar la cadena como de solo lectura. No puede hacerle cambios. Ejemplo:
Está buscando problemas.
Por otra parte
está asignando una matriz de caracteres (una variable) y algunos puntos de memoria a esa memoria asignada. Ahora, esta matriz es tanto de lectura como de escritura. Ahora puedes hacer:
y el contenido de la matriz cambia a "hola mundo"
fuente
const char *s = "hi";
¿No es esto realmente requerido por el estándar?const char const* s;
Para ese ejemplo exacto, malloc es de poca utilidad.
La razón principal por la que se necesita malloc es cuando tiene datos que deben tener una vida útil diferente del alcance del código. Su código llama a malloc en una rutina, almacena el puntero en algún lugar y finalmente llama a free en una rutina diferente.
Una razón secundaria es que C no tiene forma de saber si queda suficiente espacio en la pila para una asignación. Si su código necesita ser 100% robusto, es más seguro usar malloc porque entonces su código puede saber que la asignación falló y manejarla.
fuente
malloc es una herramienta maravillosa para asignar, reasignar y liberar memoria en tiempo de ejecución, en comparación con declaraciones estáticas como su ejemplo de Hola mundo, que se procesan en tiempo de compilación y, por lo tanto, no se pueden cambiar de tamaño.
Por lo tanto, Malloc siempre es útil cuando se trata de datos de tamaño arbitrario, como leer el contenido de un archivo o manejar sockets y no se sabe la longitud de los datos que se deben procesar.
Por supuesto, en un ejemplo trivial como el que proporcionó, malloc no es la "herramienta correcta para el trabajo correcto" mágica, pero para casos más complejos (crear una matriz de tamaño arbitrario en tiempo de ejecución, por ejemplo), es la única forma de Vamos.
fuente
Si no conoce el tamaño exacto de la memoria que necesita usar, necesita una asignación dinámica (
malloc
). Un ejemplo podría ser cuando un usuario abre un archivo en su aplicación. Deberá leer el contenido del archivo en la memoria, pero, por supuesto, no conoce el tamaño del archivo de antemano, ya que el usuario selecciona el archivo en el momento, en tiempo de ejecución. Entonces, básicamente, lo necesitamalloc
cuando no conoce el tamaño de los datos con los que está trabajando de antemano. Al menos esa es una de las principales razones para consumirmalloc
. En su ejemplo con una cadena simple cuyo tamaño ya conoce en el momento de la compilación (además de que no desea modificarlo), no tiene mucho sentido asignar eso dinámicamente.Un poco fuera de tema, pero ... debes tener mucho cuidado de no crear pérdidas de memoria al usar
malloc
. Considere este código:¿Ves lo que está mal con este código? Hay una declaración de retorno condicional entre
malloc
yfree
. Puede parecer bien al principio, pero piénselo. Si hay un error, volverá sin liberar la memoria que asignó. Esta es una fuente común de pérdidas de memoria.Por supuesto, este es un ejemplo muy simple, y es muy fácil ver el error aquí, pero imagina cientos de líneas de código llenas de punteros,
malloc
s,free
s, y todo tipo de manejo de errores. Las cosas pueden complicarse mucho muy rápido. Esta es una de las razones por las que prefiero C ++ moderno sobre C en los casos aplicables, pero ese es un tema completamente diferente.Por lo tanto, siempre que lo use
malloc
, asegúrese siempre de que su memoria tenga las mismasfree
posible.fuente
es ilegal, los literales de cadena son
const
.Esto asignará una matriz de caracteres de 12 bytes en la pila o globalmente (dependiendo de dónde se declare).
Si desea dejar espacio para una mayor manipulación, puede especificar que el tamaño de la matriz sea mayor. (Sin embargo, no ponga 1 MB en la pila).
fuente
Una razón por la que es necesario asignar la memoria es si desea modificarla en tiempo de ejecución. En ese caso, se puede utilizar un malloc o un búfer en la pila. El ejemplo simple de asignar "Hola mundo" a un puntero define la memoria que "normalmente" no se puede modificar en tiempo de ejecución.
fuente