Pages: [1]   Go Down
Print
Author Topic: Lista C  (Read 735 times)
0 Members e 1 Utente non registrato stanno visualizzando questa discussione.
Killerluke
Matricola
*
Offline Offline

Posts: 6


« on: 08-01-2014, 15:12:24 »

Ho fatto al volo questo programmino per gestire una lista, ma devo aver fatto un errore abbastanza ###@@ nell'inserimento di più nodi alla lista.
Finchè inserisco i nodi uno ad uno e li vado a leggere, non riscontro alcun tipo di problema, al contrario, se inserisco più elementi(dal secondo "case" del swtich) e poi tento di visualizzare, mi si presenta l'ultimo numero inserito, ripetuto infinite volte.

Code:
#include <stdio.h>
#include <stdlib.h>

/*
 * Liste
 */
struct lista
    {
        int a;
        struct lista *next;   
    }*first=NULL,*new,*tmp;
    typedef struct lista nodo;

int main(int argc, char** argv)
{
    int x,dato,ndati,i;
    do
    {
        do
        {
            printf("\n\nQuale operazione vuoi eseguire sulla lista?\n\n");
            printf("1 - Inserisci un numero\n");
            printf("2 - Inserisci piu' numeri\n");
            printf("3 - Visualizza lista\n");
            printf("4 - Esci\n");
            scanf("%d",&x);
        }while(x<0 || x>4);
        switch(x)
        {
            case 1:
            {
                printf("\nInserisci il numero che desideri inserire\n");
                scanf("%d",&dato);
                new = (nodo*) malloc(sizeof(nodo));
                new->a=dato;
                new->next=NULL;
                if(first==NULL) first = new;
                else
                {
                    tmp=first;
                    while(tmp->next!=NULL)tmp=tmp->next;
                    tmp->next=new;
                }
                printf("\nDato inserito nella lista\n\n");
            }break;
            case 2:
            {
                printf("\nInserisci la quantita' di dati che vuoi inserire\n");
                scanf("%d",&ndati);
                new= (nodo*)malloc(ndati * sizeof(nodo));
                for(i=0;i<ndati;i++)
                {
                    printf("\nInserisci il numero che desideri inserire\n");
                    scanf("%d",&dato);
                    new->a=dato;
                    new->next=NULL;
                    if(first==NULL) first = new;
                    else
                    {
                        tmp=first;
                        while(tmp->next!=NULL) tmp=tmp->next;
                        tmp->next=new;
                    }
                    printf("\nIl %d dato e' stato inserito nella lista\n",i+1);
                }
                printf("\nI numeri sono stati inseriti nella lista\n");
            }break;
            case 3:
            {
                tmp=first;
                while(tmp!=NULL)
                {
                    printf("%d ",tmp->a);
                    tmp=tmp->next;
                }
            }break;
        }
    }while(x!=4);
    printf("\n");
    system("PAUSE");
}

Help!
Logged
Killerluke
Matricola
*
Offline Offline

Posts: 6


« Reply #1 on: 08-01-2014, 15:27:52 »

Mi rispondo da solo:
Code:
case 2:
            {
                printf("\nInserisci la quantita' di dati che vuoi inserire\n");
                scanf("%d",&ndati);
                //new= (nodo*)malloc(ndati * sizeof(nodo));    <----------- Eccolo qui.
                for(i=0;i<ndati;i++)
                {
                    new= (nodo*)malloc(sizeof(nodo));         //<------- Come pensavo stava nel malloc.
                    printf("\nInserisci il numero che desideri inserire\n");
                    scanf("%d",&dato);
                    new->a=dato;
                    new->next=NULL;
                    if(first==NULL) first = new;
                    else
                    {
                        tmp=first;
                        while(tmp->next!=NULL) tmp=tmp->next;
                        tmp->next=new;
                    }
                    printf("\nIl %d dato e' stato inserito nella lista\n",i+1);
                }
                printf("\nI numeri sono stati inseriti nella lista\n");
            }break;

Tuttavia mi chiedo il motivo per cui la notazione originale non funzioni.
Logged
ɹǝǝuıƃuǝsɹǝʌǝɹ
Administrator
God of the Forum
*****
Offline Offline

Gender: Male
Posts: 4.475


Più grande è la lotta, e più è glorioso il trionfo


WWW
« Reply #2 on: 08-01-2014, 16:23:03 »

Scrivendo:
Code:
new= (nodo*)malloc(ndati * sizeof(nodo));
allochi memoria per un array di un numero di "nodo" pari a nsize.

Mentre nell'altro caso, ne allochi per un solo nodo.

In ogni caso, però, la variabile che contiene il riferimento al primo dei tanti o unico nodo (a seconda dei due casi) è sempre di tipo nodo*.

Dunque, se usi la prima versione del codice, dentro il ciclo for fai riferimento sempre al primo elemento dell'array (che hai individuato scrivendo semplicemente new), mentre avresti dovuto usare la notazione new[i] oppure l'equivalente new+i (il compilatore C sa gestire elegantemente l'aritmetica dei puntatori, quando si somma un valore valutato come puntatore a un intero). Per fare poche modifiche, cambia queste due righe (seppur allocando una nuova variabile)
Code:
case 2:
            {
                printf("\nInserisci la quantita' di dati che vuoi inserire\n");
                scanf("%d",&ndati);
                new_array= (nodo*)malloc(ndati * sizeof(nodo)); //cambio nome per poter riciclare "new" dopo
                for(i=0;i<ndati;i++)
                {
                    nodo* new=new_array [i];    //assegno a "new" (per riciclarlo) l'i-esimo elemento di new_array :)
                    printf("\nInserisci il numero che desideri inserire\n");
                    scanf("%d",&dato);
                    new->a=dato;
                    new->next=NULL;
                    if(first==NULL) first = new;
                    else
                    {
                        tmp=first;
                        while(tmp->next!=NULL) tmp=tmp->next;
                        tmp->next=new;
                    }
Per il futuro, evita di usare il nome "new" come nome di identificatore: quando programmerai in C++ o in Java, altrimenti, dovrai cambiare nome, perché è riservato per l'allocazione dinamica gestita dal runtime. È bene cominciare da subito a evitare possibili casini !
Logged

La grande marcia della distruzione mentale proseguirà. Tutto verrà negato. Tutto diventerà un credo. È un atteggiamento ragionevole negare l'esistenza delle pietre sulla strada; sarà un dogma religioso affermarla. È una tesi razionale pensare di vivere tutti in un sogno; sarà un esempio di saggezza mistica affermare che siamo tutti svegli. Accenderemo fuochi per testimoniare che due più due fa quattro. Sguaineremo spade per dimostrare che le foglie sono verdi in estate. Non ci resterà quindi che difendere non solo le incredibili virtù e saggezze della vita umana, ma qualcosa di ancora più incredibile: questo immenso, impossibile universo che ci guarda dritto negli occhi. Combatteremo per i prodigi visibili come se fossero invisibili. Guarderemo l'erba e i cieli impossibili con uno strano coraggio. Saremo tra coloro che hanno visto eppure hanno creduto.

In tutto, amare e servire.

  
                            ن                           
I can deal with ads,
I can deal with buffer,
but when ads buffer
I suffer...

...nutrimi, o Signore, "con il pane delle lacrime; dammi, nelle lacrime, copiosa bevanda...

   YouTube 9GAG    anobii  S  Steam T.B.o.I. Wiki [univ] Lezioni private  ʼ  Albo d'Ateneo Unicode 3.0.1
Usa "Search" prima di aprire un post - Scrivi sempre nella sezione giusta - Non spammare - Rispetta gli altri utenti - E ricorda di seguire il Regolamento
Pages: [1]   Go Up
Print
Jump to: