PDA

View Full Version : [C] Problema con le liste


Krat0s
18-05-2011, 21:21
Ciao a tutti....mi hanno introdotto ieri le liste all'università e ho provato a fare un programmino. Praticamente inserisco il numero di dipendenti dell'azienda, i loro dati (nome e data di assunzione), inserisco un anno da ricercare e mi restituisce i nomi dei dipendenti assunti in quell'anno. Solamente che se io lo faccio partire in modalità debug mi funziona, altrimenti no. Uso Dev C++ su win Xp.

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

struct data {int giorno,mese,anno;};
typedef struct data Data;

struct dipendente { char nome[20];
Data datassunzione;
};
typedef struct dipendente dip;

struct El { dip info;
struct El *next;
};
typedef struct El elemento;
typedef elemento *Listadidipendenti;

struct Punt { elemento *puntatore;
struct Punt *next;};
typedef struct Punt puntavalore;
typedef puntavalore *Listadipuntatori;

void Inizializza(Listadidipendenti *lista);
void Inizializza2(Listadipuntatori *lispunt);
void Inseriscidati(Listadidipendenti *lista,int numero);
void Ricerca(Listadidipendenti lista,Listadipuntatori *lispunt, int anno);
void Scrivilista(Listadipuntatori lispunt);

main()
{
int numerodip,anno;
Listadidipendenti lista;
Listadipuntatori listapunt;
Inizializza(&lista);
Inizializza2(&listapunt);
printf("Inserire il numero di dipendenti: ");
scanf("%d",&numerodip);
Inseriscidati(&lista,numerodip);
printf("\n\nInserire l'anno da cercare: ");
scanf("%d",&anno);
Ricerca(lista,&listapunt,anno);
printf("\n\nLISTA DEI DIPENDENTI ASSUNTI NELL'ANNO %d:\n",anno);
Scrivilista(listapunt);
system("PAUSE");


}

void Inizializza(Listadidipendenti *lista)
{
*lista = NULL;
}
void Inizializza2(Listadipuntatori *lispunt)
{
*lispunt = NULL;
}
void Inseriscidati(Listadidipendenti *lista,int numero)
{
int i,j;
char c;
Listadidipendenti aux;
for (i=1;i<=numero;i++) {
aux=malloc(sizeof(dip));
printf("\nInserire il nome del dipendente numero %d: ",i);
for (j=0;j<20;j++) aux->info.nome[j] = '0';
j=1;
scanf("%c",&c);
do { scanf("%c",&c);
if (c != '\n') aux->info.nome[j] = c;
j++;
}
while (c!='\n');
printf("Inserire la data di assunzione: ");
scanf("%d %d %d",&aux->info.datassunzione.giorno,&aux->info.datassunzione.mese,&aux->info.datassunzione.anno);
aux->next = *lista;
*lista = aux;
}
}
void Ricerca(Listadidipendenti lista,Listadipuntatori *lispunt, int anno)
{
Listadipuntatori aux;
while (lista!=NULL) {
if (lista->info.datassunzione.anno == anno) {
aux = malloc(sizeof(puntavalore));
aux->puntatore = lista; aux->next=*lispunt;
*lispunt = aux;
}
lista = lista->next;
}
}
void Scrivilista(Listadipuntatori lispunt)
{
int i=0;
while (lispunt != NULL) {
i=0;
while (lispunt->puntatore->info.nome[i]!='0') { putchar(lispunt->puntatore->info.nome[i]);
i++;
}
printf("\n");
lispunt= lispunt->next;
}
}


Secondo le intenzioni utilizzo due liste, una per i dipendenti e l'altra con gli indirizzi che puntano agli elementi cercati....se qualcuno può dargli un'occhiata...

Gimli[2BV!2B]
19-05-2011, 00:14
Varie osservazioni:
ti sei impegnato molto ad aggrovigliare i puntatori, in primo luogo un typedef di questo tipo lo eviterei:typedef elemento *Listadidipendenti;
studia la struttura degli array di char, in particolare tieni presente che il carattere terminatore è '\0' non '0' e che è sufficiente che il primo elemento sia '\0' per rendere la stringa vuota
dai una letta alla documentazione di scanf (http://linux.die.net/man/3/scanf) e printf (http://linux.die.net/man/3/printf), in particolare per quanto riguarda il formato %s
mantieni uno stile di indentazione (http://en.wikipedia.org/wiki/Indent_style) costante
mantieni una convenzione di nomenclatura costante
dichiara un main canonico (tipo di dato in uscita, exit con codice di uscita alla fine)
se sono presenti dei malloc ci vogliono anche dei free (in un programmino con esecuzione singola come questo non sono assolutamente fondamentali, ma sono dell'avviso che sia meglio essere puntigliosi su questo argomento)


Frammenti esemplicativi:struct dipendente
{
char nome[ LENGTH_NOME ];
Data datassunzione;
};
typedef struct dipendente Dipendente;

struct elemento
{
Dipendente info;
struct elemento *next;
};
typedef struct elemento El;

void InserisciDati( El **lista, const int numero )
{
int i;
El *aux;
for( i = 1; i <= numero; ++i )
{
aux = (El*)malloc( sizeof( El ) );
memset( (void*)aux, 0x00, sizeof( El ) );
printf( "\nInserire il nome del dipendente numero %d: ", i );
scanf( "%s", aux->info.nome );

printf( "Inserire la data di assunzione.\n" );
printf( "Giorno: " );
scanf( "%d", &aux->info.datassunzione.giorno );
printf( "Mese: " );
scanf( "%d", &aux->info.datassunzione.mese );
printf( "Anno: " );
scanf( "%d", &aux->info.datassunzione.anno );

aux->next = *lista;
*lista = aux;
}
}

Krat0s
19-05-2011, 00:28
Domani do un'occhiata più lucida a ciò che hai scritto e al codice....a caldo ti posso dire che il typedef che mi hai segnalato lo usa la prof nel codice e almeno per ora ce lo devo mettere perchè è una che vuole vedere le cose scritte come le spiega lei....per l'immissione del nome non abbiamo visto le stringhe, quindi ho fatto un pò a caso....darò un'occhiata, e cerco di snellire il tutto. Ma sul codice hai visto qualche errore che mi può pregiudicare il funzionamento del programma?

Gimli[2BV!2B]
19-05-2011, 01:12
Direi che non torna la dimensione di questo malloc:void Inseriscidati(Listadidipendenti *lista,int numero)
{
int i,j;
char c;
Listadidipendenti aux;
for (i=1;i<=numero;i++) {
aux=malloc(sizeof(dip));dipendente/dip è solo una porzione El/elemento.

Poi c'è un errore nelle stringhe Krat0s: tutti gli info.nome iniziano con un cararattere '0' per colpa di j.

Krat0s
19-05-2011, 08:57
Perfetto, corretti gli errori....poi mi metterò a sistemare il resto ed ottimizzare il tutto...grazie per l'aiuto