SVNiko ha scritto:
Sei sicura che compili senza errori ne warning?
sisi compila tutto, anche se ho sbagliato ad incollare grafoparser.c che invece è questo
#include <stdio.h>
#include <stdlib.h>
#include <limits.h>
#include <ctype.h>
#include "grafolista.h"
#include "grafomatrice.h"
#include "grafoparser.h"
#include <string.h>
// Elaborazione simboli NON TERMINALI
int parseGrafo (FILE *file, GrafoAdj *G, GrafoMatr *M, int tipo)
{ //Traduce il grafo [ritorna il puntatore alla radice]
int x,n=0,i=0;
char val;
n=traduciNumeroNodi(file); //leggi il numero di nodi che dovrà contenere il grafo
if(tipo==2)*M=creaGrafoMatr(n);
else *G=creaGrafoLista(n);
while(i<n)
{
x=confronto(file,ID); //verifica che dopo il numero di nodi ci sia un nodo stesso
if(x)
{
val=fgetc(file); //estrai il primo nodo
ungetc(val,file);
if(tipo==1)
{
*G=aggiungiVerticeLista(*G,val,0);
sposta(file,ID);
verticiAdj(*G,0,val,file);
}
else
{
*M=aggiungiVerticeMatr(*M,val,0,n);
sposta(file,ID);
verticiAdj(NULL,*M,val,file); //traduce i vertici adiacenti al nodo
}
}
else printf(":: ERRORE VERTICE! ::\n\n");
i++;
}
// else ERRORE NESSUN NODO PRESENTE!!!
return n;
}
int traduciNumeroNodi(FILE *file) // DOPO LA FUNZIONE LO STREAM SI TROVA DOPO LA PARENTESI CHIUSA
{//Esamina i simboli che rappresentano il numero di nodi [se ' (numeroIntero) ' ritorna il numero, altrimenti errore]
int n=0;
if(confronto(file,PARSX)) //se il simbolo corrente è una parentesi aperta è verificato il primo simbolo
{
sposta(file,PARSX);//ci si sposta al simbolo successivo la parentesi
if (confronto(file,NUM)) // se il simbolo corrente è del tipo intero è verificato il secondo simbolo
{
n=traduciIntero(file);
//sposta(file,NODO); //ci si sposta al simbolo successivo al nodo NON NECESSARIO
if(confronto(file,PARDX)) //se il simbolo corrente è una parentesi chiusa è verificato anche il terzo simbolo
{
sposta(file,PARDX); //si sposta al simbolo successivo all'interno del file
return n;}
}
}
return 0; //ritorna errore
}
int traduciIntero (FILE *file) // DOPO LA FUNZIONE LO STREAM SI TROVA DOPO L'INTERO
{//Traduci il simbolo non terminale che rappresenta un intero [ritorna il vertice intero del nodo]
int c=0,num=0,l=0;
while ((c=fgetc(file)) != EOF && isdigit(c)) {
if (num <= ((INT_MAX - (c-'0'))/10)){
num = num*10 + (c-'0');
l++;
}
// else syntax_error("Integer ID <= 2147483647",file); // Number too big: ERROR
}
//if (l==0) syntax_error("Integer ID",file); // The ID is not a number
if(c != EOF) // If EndOfFile not yet reached
ungetc(c,file); // push the last character back to the file
return num;
}
float traduciPeso (FILE *file)
{
float peso; char segno; int pintera, pdecimale; char stringa[10];
segno=fgetc(file);
pintera=traduciIntero(file);
if (confronto(file,PUNTO)) //se dopo l'intero c'è un un punto allora è un float
{
sposta(file,PUNTO); //sposta allo stream successivo al punto
pdecimale=traduciIntero(file);
}
else
{
printf("Errore Sintassi Peso! Il numero non è floating point!!\n");
return 0;
}
sprintf(stringa, "%c", segno);
sprintf(stringa, "%s%d", stringa,pintera);
sprintf(stringa, "%s%c",stringa, '.');
sprintf(stringa, "%s%d", stringa,pdecimale);
peso=atof(stringa);
sposta(file,PARDX);
return peso;
}
void verticiAdj (GrafoAdj G, GrafoMatr M, char nodo, FILE *file)
{//Traduci vertici adiacenti
int res;
char val;
float peso;
res=confronto(file,PUNT); // Cerca freccia che indica a quali vertici punta il nodo in questione
while(res!=0)
{// Se IL SIMBOLO PUNTATORE è stato trovata verificare che segua un peso
peso=0;
if (confronto(file,PARSX))
{sposta(file,PARSX);
if(confronto(file,PESO))
peso=traduciPeso(file);
}
val=fgetc(file);
if(G!=NULL) G=aggiungiArcoLista(G,nodo,val,peso);
else M=aggiungiArcoMatr(M,nodo,val,peso);
if (confronto(file,VIRG))
sposta(file,VIRG);
else
res=0;
}
//non ha altri vertici adiacenti
sposta(file,PUNTOV);
printf("\n");
}
// Elaborazione simboli TERMINALI
int confronto(FILE *file, type x)
{ //Verifica se il tipo x corrisponde al simbolo nel file [ritorna 1 se vero, 0 altrimenti]
char c;
type rp; // Read symbol type
int res=0;
while(((c = fgetc(file)) == '\t') || (c== '\n') || (c== ' '))
;
switch(c) { // Determine the read symbol type
case '(': rp = PARSX; break;
case ')': rp = PARDX; break;
case '-':
rp=MENO;
if(confronto(file,PUNT)) rp=PUNT;
else rp=PESO;
break;
case '>': rp=PUNT; break;
case '+': rp=PESO; break;
case ';': rp = PUNTOV; break;
case ',': rp = VIRG; break;
case '.': rp= PUNTO; break;
default : rp = NUM; break;
}
if(rp==NUM) //se alla fine dello switch rp è NUM è un intero altrimenti è un ID
{
if(!isdigit(c))
rp=ID;
}
ungetc(c,file); // Push the read character back to the file
if(rp==PUNT) //Se il tipo è un puntatore effettuo uno spostamento in avanti in quanto il simbolo corrente potrebbe essere il meno perchè il simbolo del punt è fatto da '-' e '>'
sposta(file,PUNT);
if (rp==x) // The expexted type et and the read symbol type rp match
res = 1;
return res;
}
void sposta (FILE *file, type x)
{//si sposta nel file al simbolo successivo a quello del tipo x
int dim = 0;
switch(x) { // Assign the read symbol type
case PARSX:; case PARDX:; case NUM:; case PUNTO:; case MENO:; case PIU:; case PUNT:; case PUNTOV:; case VIRG:; case ID:; case PESO:dim=1; break;
} //qualunque sia il simbolo ricevuto dim=1, ci si sposta di un passo
fseek(file,dim,SEEK_CUR); // Si muove di dim passi a partire da quello corrente all'interno del file
}