PDA

Visualizza la versione completa : [C]Lista di abbreviazioni


N95
20-08-2015, 22:15
Il testo del problema è:

Si assuma presente in memoria una lista composta di abbreviazioni (ad esempio TO, MI,
RM) e dalle corrispondenti parole estese implementata tramite record e puntatori utilizzando
la seguente struttura:
struct elem {
char abbr[2];
char *estesa;
struct elem *next;
}
Scrivere una funzione C che, ricevendo come parametri il puntatore all’inizio della lista,
una abbreviazione e la corrispondente parola estesa cerchi l’abbreviazione nella lista e:
a) restituisca 0 se la coppia `e presente nella lista
b) restituisca 1 se la coppia non `e presente nella lista
c) restituisca 2 se l‘abbreviazione `e presente ma ad essa corrisponde una parola differente.
Inoltre, nel caso b) un nuovo record deve essere aggiunto in coda alla lista e nel caso c) la
parola estesa deve essere sostituita da quella passata come parametro.



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

struct elem {
char abbr[2];
char *estesa;
struct elem *next;
};

struct elem *crealista(int n);
int contr(struct elem *pun, char abb[], char est[]);
void creaelem(struct elem *t, char a[], char b[]);

int main()
{
int k;
int i=0;
do{
if(i!=0)
printf("Errore! Il numero deve essere almeno uguale a 1! \n");
printf("Inserisci il numero di elementi della lista: \n");
scanf("%d", &k);
}
while(k<1);
char ab[2];
char es[1000];
char sc;
struct elem *p;
p=crealista(k);
int y;
for( ;sc!='t'; ) {
printf("Inserisci un abbreviazione: \n");
scanf("%s", ab);
printf("Inserisci la stringa estesa: \n");
scanf("%s", es);
y=contr(p, ab, es);
if(y==0)
printf("L'abbreviazione e la stringa estesa sono presenti nella lista \n");
else {
if(y==1)
printf("L'abbreviazione non era presente nella lista ma ora \x8A stata inserita \n");
else
printf("Era presente l'abbreviazione ma non l'estensione ma ora \x8A stata inserita \n");
}
while(getchar()!='\n');
printf("Premi t per terminare: \n");
sc=getchar();
}
return 0;
}

struct elem *crealista(int n) {
struct elem *p, *pt;
p=(struct elem *)malloc(sizeof(struct elem));
printf("Inserisci l'abbrezione 1: \n");
scanf("%s", p->abbr);
p->estesa=malloc(1000*sizeof(char));
printf("Inseisci la stringa estesa 1: \n");
scanf("%s", p->estesa);
pt=p;
int i;
for(i=1; i<n; i++) {
pt->next=(struct elem *)malloc(sizeof(struct elem));
pt=pt->next;
printf("Inserisci l'abbrezione %d: \n", i+1);
scanf("%s", pt->abbr);
pt->estesa=malloc(1000*sizeof(char));
printf("Inseisci la stringa estesa %d: \n", i+1);
scanf("%s", pt->estesa);
}
pt->next=NULL;
return p;
}

int contr(struct elem *pun, char abb[], char est[]) { /* controlla che siano presenti sia l'abb. che l'est. oppure solo l'abb*/
struct elem *s, *g;
s=pun;
g=NULL;
while(s!=NULL) {
if(strcmp(s->abbr, abb)==0) {
if(strcmp(s->estesa, est)==0)
return 0;
else
g=s;
}
s=s->next;
}
if(g==NULL) {
creaelem(pun, abb, est);
return 1;
}
else
{
strcpy(g->estesa, est);
return 2;
}
}

void creaelem(struct elem *t, char a[], char b[]) { /* crea un elmento se l'abb non esiste*/
struct elem *f;
f=t;
while(f->next!=NULL)
f=f->next;
f->next=(struct elem *)malloc(sizeof(struct elem));
f=f->next;
f->estesa=malloc(strlen(b)+1);
f->next=NULL;
strcpy(f->abbr, a);
strcpy(f->estesa, b);
}



Questo codice dovrebbe funzionare, però se nel main non utilizzo la y ma metto confronto direttamente contr(p, ab, es) non funziona correttamente visto che quando inserisco una nuova abbreviazione mi stampa che era già presente.
Qualcuno mi saprebbe spiegare il perché?

Scara95
21-08-2015, 07:02
Se hai problemi su un pezzo di codice diverso, posta quello.

Attento comunque che con
char abbr[2]; puoi contenere una stringa di un solo carattere (carattere + terminatore '\0'). Se vuoi contenere due caratteri o usi un array di tre elementi o accedi separatamente ai due campi e ti scordi le funzioni che operano sulle stringhe.

N95
21-08-2015, 18:24
Se hai problemi su un pezzo di codice diverso, posta quello.

Attento comunque che con
char abbr[2]; puoi contenere una stringa di un solo carattere (carattere + terminatore '\0'). Se vuoi contenere due caratteri o usi un array di tre elementi o accedi separatamente ai due campi e ti scordi le funzioni che operano sulle stringhe.

La parte di codice in cui ho in problema è il main, però ho preferito postare tutto visto che il main è connesso alle altri parti e che questa stranezza avviene proprio richiamando una funzione. In questo caso la funzione ritorna un intero, io voglio capire se si possa utilizzare una funzione come questa come una variabile, oppure se questo può causare dei problemi.

Scara95
21-08-2015, 18:36
Cosa intendi per usare come una variabile?

Comunque ti ripeto che se vuoi memorizzare una stringa di due caratteri non ti basta un array di due caratteri.

oregon
21-08-2015, 18:44
Ti consiglio di seguire il consiglio e mettere a posto, prima di tutto, la lunghezza di quella stringa ...Linee comescanf("%s", ab);possono creare situazioni imprevedibili.

N95
21-08-2015, 18:49
Intendo poterlo confrontare con altri valori e utilizzarlo in operazioni del tipo x=funzione(generica)+1. Naturalmente a differenza di una variabile non si può assegnarli un nuovo valore come per esempio una cosa del tipo funzione(generica)=3.
Per quanto riguarda le stringe prendiamo una stringa a[2], essa non è composta dai caratteri a[0], a[1] e a[2]?
Se cosi non fosse come potrebbe funzionare corretamente un codice come questo?


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

int main()
{
char ab[2];
int i;
for(i=0; i<2; i++) {
printf("Inserisci la lettera %d:\n", i+1);
scanf("%c", &ab[i]);
while(getchar()!='\n');
}
ab[i]='\0';
printf("ab: %s\n", ab);
printf("Inserisci ab: \n");
scanf("%s", ab);
printf("ab: %s", ab);
return 0;
}

Scara95
21-08-2015, 19:00
Funziona ed è corretto sono due cose diverse
Se usi gcc prova a compilare con la flag -fno-stack-protector

N95
21-08-2015, 19:17
Io utilizzo codeblocks oppure dev-c++, posso farlo direttamente con uno di questi due ide?

oregon
21-08-2015, 20:33
Per essere concisi... devi scrivere

ab[3]

per usare gli elementi 0, 1 e 2

N95
21-08-2015, 21:18
Per essere concisi... devi scrivere

ab[3]

per usare gli elementi 0, 1 e 2

Si ma allora perché in quel codice riesco a inserire 2 caratteri?

Loading