[C] Inserimento in coda
Buonasera, vorrei sapere: come mai in questa funzione dell'inserimento in coda si utilizza il doppio puntatore e non il semplice puntatore? Perchè $text(*ptrptr)$ punta il primo elemento di $text(*next_ptr)$ e in particolare il suo primo elemento?
Grazie
struct list {
float value;
struct list *next_ptr;
};
void suf_insert(struct list **ptrptr, float v) {
while (*ptrptr != NULL) {
ptrptr = &((*ptrptr)->next_ptr);
}
pre_insert(ptrptr, v);
}Grazie
Risposte
Perché nel caso in cui sia ptrptr == NULL, il puntatore va modificato in modo che contenga il nuovo nodo.
Esiste una implementazione alternativa delle liste in cui, invece di usare un valore uguale a NULL per le definire la fine della lista si usa un nodo particolare. Perché sia possibile farlo è tuttavia necessario fare uso di una struttura separata che definisca la lista. L'implementazione di molte funzioni diventa più semplice perché spariscono alcuni casi particolari da gestire separatamente (come il primo o l'ultimo elemento della lista).
struct list_node {
float value;
struct list *next;
};
struct list {
struct list_node ROOT;
};
void list_init(struct list *lst) {
lst->ROOT->next = &(lst->ROOT);
}
/* Ogni lista ha almeno un nodo per cui non c'è alcun caso particolare */
void list_insert(struct list_node *n, float v) {
struct list_node *new_node = malloc(sizeof(struct list_node));
new_node->value = v;
new_node->next = n->next;
n->next = new_node;
}
void pre_insert(struct list *lst, float v) {
return list_insert(lst->ROOT, v);
}
struct list_node *find_last(struct list *lst) {
struct list_node *current = lst->ROOT;
while (current->next != lst->ROOT) { current = current->next; }
return current;
}
void suf_insert(struct list *lst, float v) {
list_insert(find_last(lst), v);
}
Ok, però non sono riuscito a capire come mai viene usato il doppio puntatore invece del puntatore a una variabile, eppure il doppio puntatore serve soltanto a entrare nella lista, cosa che può essere fatta anche da un puntatore a una variabile, così $text(ptr->value)$
E poi un'altra cosa: questa funzione sotto è per l'inserimento ordinato in ordine crescente ma è un inserimento ordinato che riguarda il singolo elemento $text((*ptrptr)->value)$ o tutta la lista viene ordinata? E anche qua sempre il solito dubbio del doppio puntatore:
Grazie
E poi un'altra cosa: questa funzione sotto è per l'inserimento ordinato in ordine crescente ma è un inserimento ordinato che riguarda il singolo elemento $text((*ptrptr)->value)$ o tutta la lista viene ordinata? E anche qua sempre il solito dubbio del doppio puntatore:
void ord_insert(struct list **ptrptr, float v) {
while (*ptrptr != NULL && ((*ptrptr)->value<v)) {
ptrptr = &((*ptrptr)->next_ptr);
}
pre_insert(ptrptr, v);
}Grazie
Nel caso in cui la lista sia vuota il puntatore al primo elemento deve cambiare ed è quindi necessario che sia un puntatore a puntatore. Se passassi solo un puntatore la sua modifica rimarrebbe limitata al corpo della funzione.