Foro de elhacker.net

Programación => Programación C/C++ => Mensaje iniciado por: michellcrh en 18 Noviembre 2020, 02:28 am



Título: Linked List
Publicado por: michellcrh en 18 Noviembre 2020, 02:28 am
Hola.
No puedo generar el algoritmo para la función insertAfter, la cual inserta un elemento después de otro, según la llave tecleada.
Espero me puedan ayudar por favor.

Código
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <stdbool.h>
  4. #include <locale.h>
  5. // Definición de variables globales
  6. struct node {
  7.   int data;
  8.   struct node *next;
  9. };
  10. struct node *start = NULL; // start es el pointer al primer nodo
  11. struct node *found = NULL; // found es el pointer al nodo encontrado
  12. int count = 0; // Número de nodos
  13. // Definición de funciones
  14. void insertFirst(int); // Inserta un nodo al principio de la lista
  15. void insertLast(int); // Inserta un nodo al final de la lista
  16. void insertAfter(int, int); // Inserta un nodo después de otro
  17. int find(int); // Buscar un nodo
  18. void traverse(); // Realiza el recorrido de la lista
  19. void deleteFirst(); // Remueve el primer nodo de la lista
  20. void deleteLast(); // Remueve el último elemento de la lista
  21. void create(); // Función auxiliar, crea una lista
  22.  
  23. int main () {
  24.   int dato, opcion;
  25.    setlocale(LC_ALL, ""); // para caracteres del Español
  26.    printf(" 1 - Insertar al inicio de la linked list.\n");
  27.    printf(" 2 - Insertar al final de la linked list.\n");
  28.    printf(" 3 - Insertar después de otro.\n");
  29.    printf(" 4 - Buscar un nodo en la lista.\n");
  30.    printf(" 5 - Desplegar la linked list (traverse).\n");
  31.    printf(" 6 - Borrar elemento al inicio\n");
  32.    printf(" 7 - Borrar elemento al final.\n");
  33.    printf(" 8 - Terminar\n");
  34.    create(); // crea una lista de prueba
  35.    while (true) {
  36.        printf("Teclee la opción: ");
  37.        scanf("%d", &opcion);
  38.        switch (opcion) {
  39.        case 1: // insertar al inicio
  40.            printf("Teclee valor del elemento a insertar al inicio\n");
  41.         scanf("%d", &dato);
  42.         insertFirst(dato);
  43.            break;
  44.        case 2: // insertar al final
  45.            printf("Teclee valor del elemento a insertar al final\n");
  46.         scanf("%d", &dato);
  47.         insertLast(dato);
  48.            break;
  49.        case 3: // insertar después
  50.            printf("Teclee valor de la llave.\n");
  51.         scanf("%d", &dato);
  52.         int llave = find(dato);
  53.         if (llave == -2) { // find regresa -2 si la lista está vacía
  54.         break;
  55. }
  56.         if(llave == -1) { // find regresa -1 si no se encuentra
  57.         printf("No se encontró %d en la lista.\n", dato);
  58.         break;
  59. }
  60.         printf("Teclee valor de nodo a insertar después de llave.\n");
  61.         scanf("%d", &dato);
  62.         int nuevo = find(dato);
  63. insertAfter(llave, dato);
  64.            break;
  65.        case 4: // buscar
  66.            printf("Teclee valor del elemento a buscar.\n");
  67.         scanf("%d", &dato);
  68.         int encontrado = find(dato);
  69.         if (encontrado == -2) { // find regresa -2 si la lista está vacía
  70.         break;
  71. }
  72.         if(encontrado == -1) { // find regresa -1 si no se encuentra
  73.         printf("No se encontró %d en la lista.\n", dato);
  74. } else {
  75. printf("Se encontró %d en la lista.\n", dato);
  76. }
  77.            break;
  78.        case 5: // recorrer
  79.         traverse();
  80.            break;
  81.        case 6: // borrar el primero
  82.            deleteFirst();
  83.            break;
  84.        case 7: // borrar el último
  85.            deleteLast();
  86.            break;
  87.        case 8:
  88.            printf("Gracias por participar");
  89.            exit(0);
  90.        default:
  91.            printf("Opción inválida, intente de nuevo\n");
  92.   }
  93.    }
  94.   return 0;
  95. }
  96.  
  97. void insertFirst(int dato) {
  98.   struct node *t;
  99.   t = malloc(sizeof(struct node));  // ubica memoria para el nodo
  100.   count++;
  101.   if (start == NULL) { // primera vez
  102.      start = t;
  103.      start->data = dato;
  104.      start->next = NULL;
  105.      return;
  106.   }
  107.   t->data = dato;
  108.   t->next = start;
  109.   start = t;
  110. }
  111.  
  112. void insertLast(int dato) {
  113.   struct node *t, *temp;
  114.   t = malloc(sizeof(struct node));
  115.   count++;
  116.   if (start == NULL) { // Primera vez
  117.      start = t;
  118.      start->data = dato;
  119.      start->next = NULL;
  120.      return;
  121.   }
  122.   temp = start;
  123.   while (temp->next != NULL) {   // busca el último nodo
  124.      temp = temp->next;
  125.   }
  126.   temp->next = t;
  127.   t->data = dato;
  128.   t->next = NULL;
  129. }
  130.  
  131. void insertAfter(int llave, int dato) {
  132.  
  133.  
  134.  
  135.  
  136. }
  137.  
  138. int find(int datoBuscado) {
  139. struct node *temp;
  140.   temp = start;
  141.   if (temp == NULL) {
  142.      printf("Linked list vacía.\n");
  143.      return -2;
  144.   }
  145.   while (temp->next != NULL) {   // busca
  146.      if(temp->data == datoBuscado) {
  147.       found = temp;
  148.  return temp->data;
  149.  } else {
  150.   temp = temp->next;
  151.  }
  152.   }
  153.   if(temp->data == datoBuscado) { // en caso de que sea el último
  154.   found = temp;
  155.       return temp->data;
  156. }
  157. return -1;
  158. }
  159.  
  160. void traverse() {
  161.   struct node *t;
  162.   t = start;
  163.   if (t == NULL) {
  164.      printf("Linked list vacía.\n");
  165.      return;
  166.   }
  167.   printf("Hay %d elemento(s) en la linked list.\n", count);
  168.   while (t->next != NULL) {
  169.      printf("%d -> ", t->data);
  170.      t = t->next;
  171.   }
  172.   printf("%d\n", t->data);
  173. }
  174.  
  175. void deleteFirst() {
  176.   struct node *t;
  177.   int n;
  178.   if (start == NULL) {
  179.      printf("Linked list vacía.\n");
  180.      return;
  181.   }
  182.   n = start->data;
  183.   t = start->next;
  184.   free(start);
  185.   start = t;
  186.   count--;
  187.   printf("%d eliminado del inicio de la linked list.\n", n);
  188. }
  189.  
  190. void deleteLast() {
  191.   struct node *t, *u;
  192.   int n;
  193.   if (start == NULL) {
  194.      printf("Linked list vacía.\n");
  195.      return;
  196.   }
  197.  
  198.   count--;
  199.  
  200.   if (start->next == NULL) { // un solo nodo en la lista
  201.      n = start->data;
  202.      free(start);
  203.      start = NULL;
  204.      printf("%d eliminado del final de la linked list.\n", n);
  205.      return;
  206.   }
  207.  
  208.   t = start;
  209.  
  210.   while (t->next != NULL) {
  211.      u = t;
  212.      t = t->next;
  213.   }
  214.  
  215.   n = t->data;
  216.   u->next = NULL;
  217.   free(t);
  218.  
  219.   printf("%d eliminado del final de la linked list.\n", n);
  220. }
  221.  
  222. void create() {
  223. insertFirst(444);
  224. insertFirst(333);
  225. insertFirst(222);
  226. insertFirst(111);
  227. }
  228.  


Título: Re: Linked List
Publicado por: AlbertoBSD en 18 Noviembre 2020, 03:48 am
Pues claro que no lo puedes generar por que esta vacía esa función.

Código
  1. void insertAfter(int llave, int dato) {
  2.  
  3. }

Llevas algo de ese parte ?


Título: Re: Linked List
Publicado por: michellcrh en 18 Noviembre 2020, 03:57 am
Si, ya llevo una parte, la adjunto a continuación, pero mi problema es que si inserta el número después del número que le pido, pero los elementos que estaban después ya no los imprime.
Código
  1. void insertAfter(int llave, int dato) {
  2.    struct node *l,*t;
  3.    l = malloc(sizeof(struct node));
  4.    count++;
  5.     if (start == NULL) { // Primera vez
  6.      start = t;
  7.      start->data = dato;
  8.      start->next = NULL;
  9.      return;
  10.   }
  11.    found->data = llave;
  12.    l->data = dato;
  13.    found->next = l;
  14.  
  15. }
  16.  


Título: Re: Linked List
Publicado por: AlbertoBSD en 18 Noviembre 2020, 04:08 am
pero los elementos que estaban después ya no los imprime.

Código
  1. void insertAfter(int llave, int dato) {
  2.    struct node *l,*t;
  3.  
Código
  1.     if (start == NULL) { // Primera vez
  2.      start = t;//t en este punto no esta inicializado a nada.
  3.  


Título: Re: Linked List
Publicado por: michellcrh en 18 Noviembre 2020, 04:13 am
Si, lo modifiqué, pero sigo con el mismo problema
Código
  1. void insertAfter(int llave, int dato) {
  2.    struct node *l;
  3.    l = malloc(sizeof(struct node));
  4.    count++;
  5.     if (start == NULL) { // Primera vez
  6.      start = l;
  7.      start->data = dato;
  8.      start->next = NULL;
  9.      return;
  10.   }
  11.    found->data = llave;
  12.    l->data = dato;
  13.    found->next = l;
  14.  
  15. }


Título: Re: Linked List
Publicado por: AlbertoBSD en 18 Noviembre 2020, 04:31 am
El problema que tienes es el siguiente, imagina que tienes una lista como la que sigue

[1]->[2]->[3]->[4]

Y quieres insertar uno nuevo después de [1] efectivamente después de [1] estas insertando un [5] pero a [5] nunca le dices que el Next es [2] y por lo tanto se pierde el "Link" que tenían y deja de ser linked list...

Espero que con eso veas como solucionarlo.

Los pasos son, guardar el next después de [1] y agregarlo al elemento que acabas de agregar en este caso seria [5]->next = [2]


Saludos!


Título: Re: Linked List
Publicado por: michellcrh en 18 Noviembre 2020, 04:50 am
Muchas Gracias, ya lo resolví. Excelente explicación.


Título: Re: Linked List
Publicado por: AlbertoBSD en 18 Noviembre 2020, 04:52 am
De que, siempre que tengas problemas con este tipo de estructuras utiliza algun diagrama para validar lo que estás haciendo, ayuda muchísimo.

Saludos!