AnswerBun.com

Cómo Deshacer un realloc exitoso. (Lenguaje C)

Stack Overflow en español Asked by Sarah_13 on January 1, 2022

Estoy intentando programar una estructura de datos que tiene dos campos implementados con un array dinámico. Al intentar programar la función que se encargará de aumentar la capacidad de la estructura, me encuentro con el siguiente problema.

Si hago dos realloc() secuenciales y compruebo tras el primero que se ha reasignado bien mi array:

  • ¿Qué pasa si el segundo realloc() me falla?
  • ¿Cómo puedo devolver el espacio reasignado a su tamaño original?
  • ¿Un realloc() con el tamaño anterior sería infalible? ¿O tendría que comprobar también si éste se pudo realizar?

Como estoy solicitando menos memoria, no debería generar ningún problema, ¿o sí? De no ser así, entraría en un problema recurrente. ¿Cómo puedo hacer un programa que gestione bien esta memoria?

Gracias de antemano. Adjunto el código incompleto y la EdD.

  struct _Graph {
    Node **nodes; /*!<Dynamic array with the graph nodes */
    List **plconnect; /*!<Adjacency dynamic array list */
    int num_nodes; /*!<Total number of nodes in the graph */
    int num_edges; /*!<Total number of connections in the graph */
    int capacity; /*!<Current size of the dynamically allocated array */
  } ;

  Status graph_increaseCapacity(Graph *g) {
    Node **n = NULL;
    List **l = NULL;
    int i;
    int new_capacity = g->capacity * INCR;
    
    n = realloc(g->nodes, new_capacity * sizeof(Node *));
    if (n == NULL) {
        return ERROR;
    }
    l = realloc(g->plconnect, new_capacity * sizeof(List *));
    if(l == NULL){
        /*Código de error para deshacer el realloc*/
    }
    
    g->capacity = new_capacity;
    g->nodes = n;
    g->plconnect = l;
    
    for (i = (g->num_nodes); i < g->capacity; i++) {
        g->nodes[i] = NULL;
        g->plconnect[i] = NULL;
    }
    return OK;
}

One Answer

¿Qué pasa si el segundo realloc me falla?

Pues eso mismo, que ha fallado y no hay memoria suficiente :-)

¿ Cómo puedo devolver el espacio reasignado a su tamaño original ?

¿ Un realloc con el tamaño anterior sería infalible ?

¿ O tendría que comprobar también si éste se pudo realizar ?

La documentación es bastante laxa:

The realloc function returns a pointer to the new object (which may have the same value as a pointer to the old object), or a null pointer if the new object could not be allocated.

Pero deja poco lugar a la interpretación: Un realloc( ) puede fallar en cualquier momento; cada llamada es independiente de la anterior, y no existe ninguna garantía, incluso para el caso de volver a un tamaño anterior.

... Porque de no ser así entraría en un problema recurrente. ¿ Cómo puedo hacer un programa que gestione bien esta memoria ?

Si una reserva de memoria falla, pues ha fallado. Tu única opción es volver sobre tus pasos, liberando ... hasta que obtengas una reserva exitosa.

Otra estrategia es no usar realloc( ), llamando exclusivamente a malloc( ) y free( ). De este modo, nunca se te dará el caso que expones. Simplemente, difieres la copia de los bloques hasta que se hayan satisfecho todos tus llamadas a malloc( ). Si alguna de las llamadas retorna NULL, pues simplemente llamas a free( ) y listo, tu programa queda en el estado anterior.

Intuitivamente esta solución parece poco eficiente ... hasta que caemos en la cuenta de que no hay ninguna garantía de que realloc( ) reutilice el puntero. En otras palabras ... ¿ como sabemos que realloc( ) no está haciendo ya justamente eso ?

Answered by Trauma on January 1, 2022

Add your own answers!

Related Questions

Error al iniciar servicio SQL Server

0  Asked on January 24, 2021 by jorge-galibert

     

Montar proyecto laravel 5.7 en hosting

1  Asked on January 24, 2021 by isc-ramirez

 

Solicitud Api google maps – javascript php

0  Asked on January 23, 2021 by esteban-baquero

       

Como evaluar si un audio se esta reproduciendo

1  Asked on January 23, 2021 by pancho-bolatti

       

Obtener nombre de una imagen cargada en PHP (Codeigniter)

1  Asked on January 22, 2021 by juan-luis

     

Obtener nombre de mes en Español (Laravel, Carbon)

6  Asked on January 22, 2021 by c47

   

Inyección de dependencias con listas?

0  Asked on January 22, 2021 by kenneth-steve-aguilar

       

Error al comunicar Sentry con Laravel 8

0  Asked on January 21, 2021 by dany-villarroel

   

¿como decifrar la cadena de conexion en el config?

1  Asked on January 21, 2021 by jose-leonardo-quiones

     

Conectar Angular 10 con una api en contenedores docker

0  Asked on January 20, 2021 by jodurpar

     

La conexión java con mysql no funciona

1  Asked on January 20, 2021 by carlos-aburto

     

Editar/Eliminar datos Firebase sobre un RecyclerView

1  Asked on January 19, 2021 by cristian-prieto-beltran

   

Ask a Question

Get help from others!

© 2023 AnswerBun.com. All rights reserved. Sites we Love: PCI Database, MenuIva, UKBizDB, Menu Kuliner, Sharing RPP, SolveDir