PDA

View Full Version : [C] un'occhiata al listato thanks


danny2005
19-06-2007, 15:17
Un processo P conta il numero di servizi che ogni utente gli invia. Il processo P preleva le richieste da una stack, le elabora ed inserisce i risultati in una lista dinamica. Le richieste nello stack e gli elementi nella lista hanno le seguenti strutture:

struct richiesta
{

int codice_servizio;

char cognome [20];

}

struct elemento
{

char cognome [20];

int num_servizi;

}

Il processo P gestisce le richieste nel seguente modo:

- verifica che il codice_servizio della richiesta abbia un valore compreso tra 1 e 1024, altrimenti scarta la richiesta;
- verifica che nella lista, che è ordinata rispetto al campo cognome esista un elemento con lo stesso cognome presente nella richiesta.ùSe tale elemento è presente, ne incrementa di 1 unità la variabile num_servizi, altrimenti inserisce un nuovo elemento nella lista in maniera ordinata con il valore di num_servizi pari a 1.

Ecco come ci ho messo mano....

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

struct richiesta
{
int codice_servizio;
char cognome [20];
struct richiesta *next;
};

struct elemento
{
char cognome[20];
int num_servizi;
struct elemento *next;
};

PROTOTIPI DI FUNZIONE

struct elemento * preleva_richiesta_da_stack(struct richiesta **, struct richiesta **);

int elabora_elemento_stack (struct richiesta *);

void in_lista_ordinata (struct elemento **, struct elemento **);

int main ()
{
struct richiesta * testa_stack=NULL;
struct elemento *testa_lista=NULL;
struct elemento *elem=NULL;
struct richiesta * y=NULL;

int codice, esci;

while(!esci)
{
esci=1;
elem= preleva_richiesta_da_stack(&testa_stack, &y);
codice= elabora_elemento_stack(y);

if (codice >=1 && codice <= 1024)
{
esci=0;
in_lista_ordinata(&testa_lista, &elem);
}

}

retrurn 0;
}


DEFINIZIONE DELLE FUNZIONI

struct elemento * preleva_richiesta_da_stack(struct richiesta **head, struct richiesta ** query)

{
struct elemento *new;
new= (struct elemento *)malloc(sizeof(struct elemento));

if (*head ==NULL)
printf("Errore stack vuota!\n");

else
{
*query=*head;
*head= (*head)-> next;
}

strcpy(new->cognome, (*query)->cognome);
new->num_servizi= (*query)->codice_servizio;

return new;
}

int elabora_elemento_stack(struct richiesta *punt)
{

return (punt->codice_servizio);

}

void in_lista_ordinata(struct elemento **head, struct elemento ** element)

{ struct elemento *prec, *curr, *new;
new=(struct elemento *)malloc(sizeof(struct elemento));
strcpy (new->cognome, (*element)->cognome);
new->num_servizi= (*element)->num_servizi;

prec=NULL;
curr=*head;

while(curr != NULL && strcmp( curr->cognome, new->cognome)<=0)
{


[ho bisogno di allocare lo spazio per il puntatore new e ricopiare li dentro il tutto, oppure confronto direttamente *element con curr? io eviterei di usare new, voi che dite?]

if(strcmp(curr->cognome, new->cognome)==0)

(curr->num_servizi)++;

else
{
prec=curr;
curr=curr->next;
}

}

if(prec==NULL)
{ new-<next=*head;
*head=new;
new->num_servizi =1;
}

else
{
prec->next=new;
new->next=curr;
new->num_servizi =1;
}

}


senza new ci sarebbe *element nei vari passaggi

danny2005
21-06-2007, 17:26
up

nessuno che si sbilancia?

danny2005
25-06-2007, 12:39
up up up

Ziosilvio
25-06-2007, 14:21
Faresti bene a usare il tag "code" e a sfruttare l'indentazione.
struct elemento * preleva_richiesta_da_stack(struct richiesta **head, struct richiesta ** query)

{
struct elemento *new;
new= (struct elemento *)malloc(sizeof(struct elemento));
if (*head ==NULL)
printf("Errore stack vuota!\n");
else
{ *query=*head;
*head= (*head)-> next;
}

strcpy(new->cognome, (*query)->cognome);
new->num_servizi= (*query)->codice_servizio;

return new;
}
Perché la copia dei campi avviene anche se non c'è spazio per new?

Nella parte successiva puoi fare i confronti direttamente, senza bisogno di creare una copia.
void in_lista_ordinata(struct elemento **head, struct elemento ** element)

{ struct elemento *prec, *curr, *new;
new=(struct elemento *)malloc(sizeof(struct elemento));
strcpy (new->cognome, (*element)->cognome);
new->num_servizi= (*element)->num_servizi;

prec=NULL;
curr=*head;

while(curr != NULL && strcmp( curr->cognome, new->cognome)<=0)

{ if(strcmp(curr->cognome, new->cognome)==0
Qui ci va una parentesi tonda chiusa.
(curr->num_servizi)++;

else {

prec=curr;

curr=curr->next;
}
}

if(prec==NULL)

{ new-<next=*head;
*head=new;
new->num_servizi =1;
}
else
{
prec->next=new;
new->next=curr;
new->num_servizi =1;
}
}
Qui c'è un problema: prec può essere NULL non solo all'inizio, ma anche se viene inserito un nominativo che precede, in ordine alfabetico, tutti quelli della lista.

cionci
28-06-2007, 09:04
Prima di tutto dai una bella indentata a tutto il codice seguendo uno dei metodi classici del C...

Ad esempio:

int pippo(int pluto, int paperino)
{
if(pluto = paperino)
{
return 1;
}
else
{
return 0;
}
}

Soprattutto per le parentesi è importantissimo che siano messe secondo una logica, altrimenti non ci si capisce niente...

cionci
28-06-2007, 09:58
Ancora non ci siamo...ti faccio vedere il main come lo farei io:

int main ()
{
struct richiesta * testa_stack = NULL;
struct elemento *testa_lista = NULL;
struct elemento *elem = NULL;
struct richiesta * y = NULL;

int codice, esci;

while(!esci)
{
esci = 1;
elem = preleva_richiesta_da_stack(&testa_stack, &y);
codice = elabora_elemento_stack(y);

if(codice >= 1 && codice <= 1024)
{
esci = 0;
in_lista_ordinata(&testa_lista, &elem);
}
}

return 0;
}

cionci
28-06-2007, 10:33
Ancora no...i blocchi che sono allo stesso livello devono essere allineati...
Che editor usi per scrivere il codice ? Molti editor permettono di usare il tab per indentare il codice, tab che viene poi convertito in un numero di spazi impostabile a piacere (solitamente 3 o 4)...

danny2005
28-06-2007, 10:38
Ancora no...i blocchi che sono allo stesso livello devono essere allineati...
Che editor usi per scrivere il codice ? Molti editor permettono di usare il tab per indentare il codice, tab che viene poi convertito in un numero di spazi impostabile a piacere (solitamente 3 o 4)...

Il fatto è che non uso editor...l'ho scritto a mano qua...:D

cmq se puoi fare uno sforzo......(per stavolta) :help:

Non lo faccio più...giuro......

cionci
28-06-2007, 10:53
Tanto gli editor la fanno da soli la formattazione ;)

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

struct richiesta
{
int codice_servizio;
char cognome[20];
struct richiesta *next;
};

struct elemento
{
char cognome[20];
int num_servizi;
struct elemento *next;
};

/*PROTOTIPI DI FUNZIONE*/
struct elemento *preleva_richiesta_da_stack (struct richiesta **,
struct richiesta **);

int elabora_elemento_stack (struct richiesta *);

void in_lista_ordinata (struct elemento **, struct elemento **);

int
main ()
{
struct richiesta *testa_stack = NULL;
struct elemento *testa_lista = NULL;
struct elemento *elem = NULL;
struct richiesta *y = NULL;

int codice, esci;

while (!esci)
{
esci = 1;
elem = preleva_richiesta_da_stack (&testa_stack, &y);
codice = elabora_elemento_stack (y);

if (codice >= 1 && codice <= 1024)
{
esci = 0;
in_lista_ordinata (&testa_lista, &elem);
}

}

retrurn 0;
}


/*DEFINIZIONE DELLE FUNZIONI */
struct elemento *
preleva_richiesta_da_stack (struct richiesta **head, struct richiesta **query)
{
struct elemento *new;
new = (struct elemento *) malloc (sizeof (struct elemento));

if (*head == NULL)
printf ("Errore stack vuota!\n");

else
{
*query = *head;
*head = (*head)->next;
}

strcpy (new->cognome, (*query)->cognome);
new->num_servizi = (*query)->codice_servizio;

return new;
}

int
elabora_elemento_stack (struct richiesta *punt)
{

return (punt->codice_servizio);

}

void
in_lista_ordinata (struct elemento **head, struct elemento **element)
{
struct elemento *prec, *curr, *new;
new = (struct elemento *) malloc (sizeof (struct elemento));
strcpy (new->cognome, (*element)->cognome);
new->num_servizi = (*element)->num_servizi;

prec = NULL;
curr = *head;

while (curr != NULL && strcmp (curr->cognome, new->cognome) <= 0)
{
/*[ho bisogno di allocare lo spazio per il puntatore new e
* ricopiare li dentro il tutto,
* oppure confronto direttamente *
* element con curr ? io eviterei di usare new,
* voi che dite ?] */
if (strcmp (curr->cognome, new->cognome) == 0)
(curr->num_servizi)++;
else
{
prec = curr;
curr = curr->next;
}

}

if (prec == NULL)
{
new - <next = *head;
*head = new;
new->num_servizi = 1;
}
else
{
prec->next = new;
new->next = curr;
new->num_servizi = 1;
}

}

danny2005
28-06-2007, 10:56
ok ma...va bene? non parlo dell'indentazione ma di ciò che è indentato........

cionci
28-06-2007, 11:05
Se funziona va bene ;)
L'hai provato ?

danny2005
28-06-2007, 11:18
ancora no......
è che volevo un parere da uno esperto; per essere sicuro di non aver scritto cose strane.........

cionci
28-06-2007, 11:27
Tanto l'insegnante migliore è il compilatore...
Se non l'avessi scritto tutto insieme ora avresti potuto fare varie prove prima di terminarlo per vedere se quello che stavi facendo era corretto ;)