[C] Occorrenze lettere di testo in file.txt esterno

di Anonimizzato19890 il
10 risposte
Ragazzi salve.

Devo creare un programma che:
1) Se lanciato con 2 o più argomenti nella riga di comando stampi un messaggio di errore;

2) Se lanciato con 1 solo argomento conti l'occorrenze delle lettere della stringa passata come argomento;

3) Se lanciato senza argomenti conta il numero di occorrenze del testo contenuto nel file "text.txt".


I punti 1) e 2) funzionano perfettamente, ma quando al punto 3) il programma mi restituisce un cursore, come se volesse qualcosa in input, ma all'infinito.

Qualcuno può farmi capire dove sbaglio? grazie a tutti!
Ecco il codice:
#include <stdio.h>
#include <string.h>
#define A_Z 26

void occorrenze (char a[]) {
	int i, j, conta[A_Z];
	for(i=0; i<strlen(a); i++){
			conta[i]=1;
			for(j=i+1; j<strlen(a); j++)
				if(a[i] == a[j])
					conta[i]++;
		}
		for(i=0; i<strlen(a); i++){
			for(j=i+1; j<strlen(a); j++)
				if(a[i] == a[j])
					conta[j]=0;
		}
		for(i=0; i<strlen(a); i++)
		{
			if(conta[i])
				printf("%c = %d\n", a[i], conta[i]);
		}
	}

int main(char argc, char *argv[]){
	char str[50];  
	FILE *fp = fopen ("text.txt", "r"); //il file text.txt contiene 42 caratteri in tutto
	
	if (argc > 2){
		printf("Errore\n");
	}
	
	else if (argc == 2) {
		occorrenze (argv[1]);
		}
	if (argc == 1) {
		fgets(str, sizeof(str), fp);
		occorrenze(str);

	}
	fclose(fp);

}

10 Risposte

  • Sicuro che il file esista e che sia aperto correttamente? Devi controllare il valore di fp (che non sia NULL) prima di utilizzarlo.

    E' bene, anche se non c'entra con l'errore, che la fopen e la fclose stiano all'interno della if relativa alla lettura del file.
  • oregon ha scritto:


    Sicuro che il file esista e che sia aperto correttamente? Devi controllare il valore di fp (che non sia NULL) prima di utilizzarlo.

    E' bene, anche se non c'entra con l'errore, che la fopen e la fclose stiano all'interno della if relativa alla lettura del file.
    Grazie per la risposta.
    Sì, il file esiste e si apre correttamente (tant'è che se faccio "puts(str)" mi stampa l'intero testo contenuto nel file).
  • Cosa c'è nel file di testo esattamente?
  • oregon ha scritto:


    Cosa c'è nel file di testo esattamente?
    "Essere o non essere questo è il problema."

    E con la puts mi stampa esattamente ciò che è contenuto, senza alcun errore. Ma dal momento che me lo stampa, come mai non posso darlo "in pasto" alla mia funzione "occorrenze"?
  • La funzione occorrenze presenta degli errori logici ... ad esempio

    conta=1;

    Come mai i va da 0 alla lunghezza della stringa quando il vettore è grande solo 26?
  • oregon ha scritto:


    La funzione occorrenze presenta degli errori logici ... ad esempio

    conta=1;

    Come mai i va da 0 alla lunghezza della stringa quando il vettore è grande solo 26?

    Grande! Ho ingrandito il vettore a 100 e ora funziona!
    Ma come mai col vettore più piccolo del testo contenuto in text.txt mi dava quel cursore che si aspettava un input all'infinito? C'è una spiegazione o è semplicemente un comportamento indefinito?
  • Con questa correzione funzionerà solo per stringhe non più lunghe di 100 caratteri ... non mi sembra una soluzione corretta.

    Del resto il vettore aveva una dimensione di 26 che si chiamava A_Z proprio perché doveva contenere i conteggi delle lettere maiuscole ... l'avevi data tu? Lo scopo era un altro, quel vettore era fatto per implementare un'altra soluzione.

    Comunque, il blocco era causato dalla corruzione dello stack per buffer overflow e conseguente cambio del valore delle variabili del ciclo. Questo comportamento è tra quelli possibili, era possibile anche un crash, ecco perché "indefinito".


    P.S. Fra l'altro, hai visto che il file non c'entrava nulla? Hai voglia a scrivere un thread per la lettura dei file ...
  • oregon ha scritto:


    Con questa correzione funzionerà solo per stringhe non più lunghe di 100 caratteri ... non mi sembra una soluzione corretta.
    Vabè, poi migliorerò il codice rendendolo più flessibile, l'importante è essermi sbloccato!

    oregon ha scritto:


    Del resto il vettore aveva una dimensione di 26 che si chiamava A_Z proprio perché doveva contenere i conteggi delle lettere maiuscole ... l'avevi data tu? Lo scopo era un altro, quel vettore era fatto per implementare un'altra soluzione.
    Sì, era un vettore che ho "riutilizzato" per un conteggio delle lettere alfabetiche, poi utilizzato in maniera differente

    oregon ha scritto:


    Comunque, il blocco era causato dalla corruzione dello stack per buffer overflow e conseguente cambio del valore delle variabili del ciclo. Questo comportamento è tra quelli possibili, era possibile anche un crash, ecco perché "indefinito".
    Grazie mille

    oregon ha scritto:


    P.S. Fra l'altro, hai visto che il file non c'entrava nulla? Hai voglia a scrivere un thread per la lettura dei file ...
    Ahahahahahah verissimo

    Grazie mille ancora!
  • In pratica si può scrivere più semplicemente (e vale per qualsiasi stringa)
    
    #define ASCII 256
    
    void occorrenze (char a[]) {
       int i, j;
       int conta[ASCII] = {0};
    
       for(i=0; i<strlen(a); i++)
          conta[a[i]]++;
       
       for(i=0; i<ASCII; i++)
          if(conta[i])
              printf("%c = %d\n", i, conta[i]);
    }
    
  • oregon ha scritto:


    In pratica si può scrivere più semplicemente (e vale per qualsiasi stringa)
    
    #define ASCII 256
    
    void occorrenze (char a[]) {
       int i, j;
       int conta[ASCII] = {0};
    
       for(i=0; i<strlen(a); i++)
          conta[a[i]]++;
       
       for(i=0; i<ASCII; i++)
          if(conta[i])
              printf("%c = %d\n", i, conta[i]);
    }
    

    puoi spiegarmi qua
    conta[a]++;

    che cosa andiamo ad incrementare? Il numero di elementi di "conta" cosa sarebbe?
Devi accedere o registrarti per scrivere nel forum
10 risposte