Controllo scanf

di Anonimizzato14507 il
12 risposte
Ciao ragazzi. Di solito per controllare che l'inserimento di un numero intero avvenga correttamente utilizzo il codice:
while(scanf("%d",&num) != 1)
		{ //controllo inserimento numero e non stringa
			printf("Errore, inserisci un numero intero:\n");
			/* rimuovo eventuali caratteri rimasti nel buffer fino al newline */
			while (getchar() != '\n');
		}
tuttavia ho notato che se viene inserito un numero seguito da un carattere(ad esempio "34G") il controllo non avviene e la scanf lo prende per buono. C'è un modo per controllare che tutti i caratteri inseriti siano corretti?

12 Risposte

  • Invece di utilizzare scanf() utilizza gets() e leggi in un buffer temporaneo.
    Sul buffer temporaneo puoi fare una scansione per verificare che tutti i caratteri siano cifre.
    Poi usi atoi() per trasformare il buffer in intero.
  • candaluar ha scritto:


    Invece di utilizzare scanf() utilizza gets() e leggi in un buffer temporaneo.
    Ciao,
    una piccola precisazione (più che altro di stile): la gets è segnata come deprecata. Al suo posto si può utilizzare la funzione fgets, specificando come ultimo parametro
    stdin
    corrispondente allo standard input.

  • una piccola precisazione (più che altro di stile)
    Non è solo stile: la fgets(), rispetto alla gets(), permette di specificare la dimensione del buffer che le passiamo. Per questo la gets() è segnata come deprecata e si suggerisce di utilizzare fgets().
  • Qualcuno può farmi un esempio? non ho idea di come usarla.
  • Ciao, ecco qui:
    
    #include <stdio.h>
    #include <stdlib.h>
    
    #define MAX_SIZE 100
    
    int main(int argc, char * argv[])
    {
    	char buffer[MAX_SIZE];
    	
    	printf("Inserire una stringa: ");
    	fgets(buffer, MAX_SIZE, stdin);
    	
    	printf("Hai inserito %s.\n", buffer);
    	
    	return 0;
    }
    
    Attenzione: come puoi vedere da questo esempio la funzione fgets (al contrario della gets) memorizza anche il carattere di newline (cioè '\n'). Quindi se lo vuoi eliminare devi farlo esplicitamente.
  • minomic ha scritto:


    Ciao, ecco qui:
    
    #include <stdio.h>
    #include <stdlib.h>
    
    #define MAX_SIZE 100
    
    int main(int argc, char * argv[])
    {
    	char buffer[MAX_SIZE];
    	
    	printf("Inserire una stringa: ");
    	fgets(buffer, MAX_SIZE, stdin);
    	
    	printf("Hai inserito %s.\n", buffer);
    	
    	return 0;
    }
    
    Attenzione: come puoi vedere da questo esempio la funzione fgets (al contrario della gets) memorizza anche il carattere di newline (cioè '\n'). Quindi se lo vuoi eliminare devi farlo esplicitamente.
    ok, quindi il valore inserito posso passarlo tranquillamente ad una funzione come numero intero o bisogna fare altro?
  • ururi1989 ha scritto:


    ok, quindi il valore inserito posso passarlo tranquillamente ad una funzione come numero intero o bisogna fare altro?
    Eh no, il valore letto ha la forma di una stringa, cioè di un array di char. Se vuoi i singoli interi che lo compongono (sempre ammesso che siano interi, quindi devi prima fare un controllo) allora devi chiamare la funzione atoi (ASCII-to-integer) su ogni elemento dell'array, cioè su ogni char della stringa.
  • minomic ha scritto:


    ururi1989 ha scritto:


    ok, quindi il valore inserito posso passarlo tranquillamente ad una funzione come numero intero o bisogna fare altro?
    Eh no, il valore letto ha la forma di una stringa, cioè di un array di char. Se vuoi i singoli interi che lo compongono (sempre ammesso che siano interi, quindi devi prima fare un controllo) allora devi chiamare la funzione atoi (ASCII-to-integer) su ogni elemento dell'array, cioè su ogni char della stringa.
    perfetto, provo e ti faccio sapere.
  • Ah forse però ho capito male la consegna: se l'utente inserisce 12345, tu vuoi leggere 12345 (cioè dodicimila ecc) oppure 1-2-3-4-5 (cioè uno, due, tre, ...)?
  • Ho provato ma niente, sicuramente uso male atoi()
    #include <stdio.h>
    #include <stdlib.h>
    #define MAX 10
    int main(int argc, char * argv[]){
    	int c,i=0;
    	char buf[MAX];
    	printf("Inserisci intero\n");
    	fgets(buf, sizeof buf, stdin);
    	printf("stringa: %s",buf);
    	while (buf[i] != NULL)
    	{
    		atoi(&buf[i]);
    		i++;
    	}
    	printf("numero intero: %d", buf);
    	system("pause");
    	return 0;
    }
  • Risolto:
    #include <stdio.h>
    #include <stdlib.h>
    #define MAX 10
    int main(int argc, char * argv[]){
    	int c,i;
    	char buf[MAX];
    	printf("Inserisci intero\n");
    	fgets(buf, sizeof buf, stdin);
    	printf("stringa: %s",buf);
    	i=atoi(buf);
    	printf("intero: %d\n", i);
    	system("pause");
    	return 0;
    }
    grazie a tutti.
  • minomic ha scritto:


    Ah forse però ho capito male la consegna: se l'utente inserisce 12345, tu vuoi leggere 12345 (cioè dodicimila ecc) oppure 1-2-3-4-5 (cioè uno, due, tre, ...)?
    si così. Ora devo scappare, ma proverò a fare il controllo sulla fgets. Per ora so come fare la conversione almeno. ciao a presto.
Devi accedere o registrarti per scrivere nel forum
12 risposte