Visualizzazione dei risultati da 1 a 5 su 5
  1. #1
    Utente bannato
    Registrato dal
    Jul 2007
    Messaggi
    66

    [c] indirizzare una variabile da un puntatore

    ciao a tutti...
    Ho creato uno struct di cui ne creo un array di puntatori più o meno così

    codice:
    struct nodo
    {
      int label;
      struct nodo *to[50];
      int dir;
      int jump_to; 
    };
    
    typedef struct nodo NODE;
    
    NODE *alberi[G];
    e poi faccio qualcosa di questo genere

    codice:
    void Converti(int i, NODE *start)
    {
      NODE nuovo;
      nuovo.label=i;
      nuovo.dir=0;
      nuovo.jump_to=NOWHERE;
      start=&nuovo;
    }
    chiamandola in questo modo

    Converti(1,alberi[1]);

    però mi accorgo che appena esce dalle funzioni, realmente, sui puntatori nn ci sta un tubo...

    come mai? C'è un modo x conservare quelle locazioni di memoria o mi creo un array di VERI nodi (cioè, tolgo i puntatori a monte)?

  2. #2
    Utente di HTML.it
    Registrato dal
    Mar 2004
    Messaggi
    30
    succede questo per 2 motivi. Il primo è che con l'ultima istruzione non esporti il risultato vero e proprio ma vai a modificare una variabile LOCALE (start è una variabile locale e come tale non esporta i dati in uscita. per avere le modifiche in uscita devi usare l' * con il quale accedi alla cella di memoria voluta).
    secondo è che la variabile nuovo di tipo NODE viene allocata nello stack della funzione Converti, con la conseguenza che all'uscita della funzione la perdi o in ogni caso anche se non vengono eliminati i dati puoi aver problemi di varia natura(sovrascrittura, segmentation fault ecc.)

    un modo corretto per riuscire ad avere la struttura all'uscita è allocandola nello heap.

    codice:
    void Converti(int i, NODE *start)
    {
      NODE* nuovo;
      /*chiediamo al sistema operativo della memoria di dimensione sizeof(NODE) 
      e castiamo il puntatore (malloc restituisce void*) come puntatore a NODE (NODE*). */
      nuovo =(NODE*) malloc(sizeof(NODE)); 
      nuovo->label=i;
      nuovo->dir=0;
      nuovo->jump_to=NOWHERE;
      *start=nuovo;
    }
    se non mi sono incasinato coi puntatori(nell'ultima istruzione) questa dovrebbe essere la procedura corretta.

  3. #3
    Utente di HTML.it
    Registrato dal
    Mar 2004
    Messaggi
    30
    ho provato ora e ho notato che effettivamente ho fatto un errore coi puntatori.
    Cioè visto che tu vuoi che in una funzione venga modificato un puntatore a struttura. dovrai passare esso per riferimento. ovvero visto che esso stesso è un puntatore la funzione Converti dovrà ricevere come parametro un DOPPIO puntatore.

    Forse il concetto non è chiaro.

    se alberi è un vettore di puntatori a strutture e la funzione Converti fa "qualcosa" che modifica uno di questi puntatori. vorrà dire che alla funzione Converti passerai L'INDIRIZZO DI UNO DI QUESTI PUNTATORI, altrimenti non riuscirai ad avere in uscita dalla funzione dei dati modificati xkè la modifica di questi avverrà unicamente a livello locale nella funzione Converti.
    Se non hai capito(cosa molto probabile date le mie spiegazioni :P) ti consiglio di leggerti una buona guida sui puntatori visto che sono un argomento non proprio banale.

    in ogni caso ti mostro la funzione nuova:
    codice:
    void Converti(int i, NODE **start) //NOTA IL DOPPIO PUNTATORE
    {
      NODE* nuovo;
      /*chiediamo al sistema operativo della memoria di dimensione sizeof(NODE) 
      e castiamo il puntatore (malloc restituisce void*) come puntatore a NODE (NODE*). */
      nuovo =(NODE*) malloc(sizeof(NODE)); 
      nuovo->label=i;
      nuovo->dir=0;
      nuovo->jump_to=NOWHERE;
      *start=nuovo;
    }
    e questa è la chiamata corretta:
    codice:
     Converti(1,&(alberi[1])); //NOTA L'OPERATORE INDIRIZZO &

  4. #4
    Utente bannato
    Registrato dal
    Jul 2007
    Messaggi
    66
    no no...ansi...credo di aver capito bene...
    una cosa che mi sfugge: una volta allocato lo spazio, come deallocarlo?

  5. #5
    Utente di HTML.it
    Registrato dal
    Mar 2004
    Messaggi
    30
    quando hai finito e non ti servono più quelle celle di memoria le restituisci al Sistema operativo con la funzione free()

    sintassi:
    codice:
     free(ptr);
    ptr deve essere un puntatore a una zona di memoria, allocata DINAMICAMENTE, quindi con malloc o derivati(calloc,realloc ecc.).

    Ciao!

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2024 vBulletin Solutions, Inc. All rights reserved.