Home > Corso di programmazione, GNU/Linux > Corso di programmazione. Scriviamo un semplice programma per calcolare la somma di due numeri forniti dall’utente

Corso di programmazione. Scriviamo un semplice programma per calcolare la somma di due numeri forniti dall’utente

In questa lezione affronteremo molti concetti che risulteranno nuovi e forse “strani” per chi non ha mai programmato, ma sono essenziali per iniziare a capirci qualcosa della programmazione. Tutti questi concetti sono legati da un filo conduttore comune: i computer non sono intuitivi e fanno solo ciò che gli si dice; non solo, i computer sono anche piuttosto limitati e sanno fare poche cose, ma velocemente.

Il altre parole i computer sono il contrario degli esseri umani: noi siamo intuitivi e fantasiosi (beh, non tutti…) ma molto lenti e ci annoiamo presto se un compito è ripetitivo. I computer invece sono stacanovisti, veloci (almeno nel fare i calcoli) ma completamente stupidi. L’insieme uomo+computer diventa quindi straordinariamente potente in quanto ognuno dei due completa le mancanze dell’altro.

Ma c’è un problema: riuscire a capirsi.

Vediamo un esempio pratico. Supponiamo di voler istruire qualcuno a darci la somma di due numeri che gli forniamo. Le istruzioni potrebbero essere:

  1. Prendi il primo numero
  2. Prendi il secondo numero
  3. Somma il primo numero con il secondo
  4. Dammi la somma

Questo è più che sufficiente per un essere umano. Ma ora facciamo finta di spiegare questo compito ad un computer che sia in grado di risponderci per cercare di capire cosa vogliamo. Vediamo come ci tratterebbe (nel dialogo questo nostro amico immaginario verrà chiamato casualmente “GCC”🙂 ):

GCC: Mmm… che significa “prendi il primo numero”?

IO: Devi acquisire dalla tastiera quello che scrive l’utente.

GCC: Bene, questo lo so fare. Ma questo “numero” sarebbe cosa?

IO: L’utente ti fornirà una sequenza di caratteri che possono essere 0, 1, ecc. fino a 9.

GCC: Bene, ho capito. Ma poi dove li metto?

IO: In che senso?

GCC: Io posso metterli nella memoria del computer, ma dobbiamo dare un nome alla celletta di memoria che conterrà il numero, per distinguerla dal resto della memoria.

IO: Ok, chiamiamola a.

GCC: Bene, allora diciamo che dobbiamo creare un’area di memoria e chiamarla a. Di che tipo deve essere questa a?

IO: Di che tipo? Non capisco….

GCC: Be’ ci sono molti tipo di dati. Numeri interi, caratteri, numeri reali (quelli con la virgola per capirsi…) …

IO: Ah…  facciamo che a sia un numero intero.

GCC: Ok, quindi possiamo dire “Acquisisci dalla tastiera una sequenza di cifre e metti il loro valore nella celletta di memoria chiamata a

IO: D’accordo.

GCC: cosa significa “Prendi il secondo numero?”

IO: la stessa cosa di prima.

GCC: quindi lo metto sempre in a?

IO: No, devi creare un’altra area… puoi chiamarla b.

GCC: Ok. Quindi dobbiamo creare un’area di memoria e chiamarla b. Di che tipo?

IO: E’ sempre un intero. E anche il numero che ti fornirà l’utente sarà intero.

GCC: Ho capito. Cosa significa “Somma i due numeri?”

IO: Devi fare a+b

GCC: Sì, lo so fare. E dove lo metto il risultato?

IO: Ah… non ci avevo pensato…. mettilo in un’area di memoria chiamata c

GCC: E di che tipo deve essere?

IO: Ma che palle! Sempre intero!

GCC: Non ti arrabbiare! Io che ne so che tu vuoi il numero intero? Magari lo volevi reale…

IO: No no, la somma di due interi è un intero, niente numeri con la virgola.

GCC. Ok, io faccio solo quello che mi dici. Ma cosa significa “Dammi il risultato”?

IO: Devi stamparlo a video

GCC: Ok, questo lo so fare. Ma cosa devo stampare?

IO: Uffa! Devi stampare c!

GCC: Ma come vuoi che te lo stampi?

IO: E come pensi che io voglia?

GCC: Non lo so, dimmelo tu.

IO: Devi stampare una sequenza di caratteri che possono essere 0, 1, 2,.. fino a 9. Insomma un numero intero!

GCC: D’accordo. E poi?

IO: E poi basta, il programma è finito.

GCC: Devo ridare un valore alla shell che ha chiamato il programma, non ricordi?

IO: Sì, sempre il solito zero.

GCC: Ok. Ora è più chiaro.

Riassumiamo quello che dobbiamo dire al computer.

  1. Crea un’area di memoria di tipo intero e chiamala a
  2. Crea un’area di memoria di tipo intero e chiamala b
  3. Crea un’area di memoria di tipo intero e chiamala c
  4. Acquisisci dalla tastiera una sequenza di caratteri numerici e metti il suo valore in a
  5. Acquisisci dalla tastiera una sequenza di caratteri numerici e metti il suo valore in b
  6. Calcola a + b e metti il risultato in c
  7. Stampa a video il valore di c sotto forma di caratteri numerici.
  8. Termina e restituisci il valore 0 al programma chiamante.

Abbiamo così creato una serie di istruzioni che scompongono il nostro problema in passaggi e che, alla fine, ci forniscano il risultato voluto. Questo metodo è chiamato “top-down” (dall’alto al basso). In parole povere si prende il problema generale e lo si scompone in parti, e poi eventualmente ciascuna parte in parti più piccole, fino a quando arriviamo a descrivere tutto il problema con una sequenza di istruzioni molto semplici. Questa sequenza prende il nome di algoritmo (tutto questo in un corso universitario prende diverse ore di spiegazione🙂 per cui non pensate che sia una banalità).

Ora proviamo a tradurre questo algoritmo in linguaggio C.

Le “aree di memoria” in cui possiamo conservare i nostri dati vengono chiamate variabili. Infatti il loro valore può variare nel corso del programma. Per definire una variabile ci basta scrivere:

tipo nome_della_variabile;

Nel nostro caso il tipo è intero, quindi la parola chiave da usare è int.

int a;
int b;
int c;

Ora dobbiamo acquisire da tastiera il primo numero e metterlo in a. La funzione che acquisisce dalla tastiera si chiama scanf .

Dobbiamo anche specificare il formato di dato che l’utente inserirà, ovvero una sequenza di caratteri che possono essere 0, 1, 2, eccetera fino a 9. Per fare ciò useremo un codice di formato che, nel nostro caso è “%d”. Vedremo in seguito gli altri formati. Il formato è il primo parametro che passeremo a scanf() (uso le parentesi dopo il nome per sottolineare che si tratta di una funzione), mentre la variabile a è il secondo. Saremmo quindi tentati di scrivere:

scanf("%d", a);

Ma sbaglieremmo di grosso. Cosa significa una sintassi del genere? Per rendercene conto, arriviamo subito all’ultima istruzione significativa, la numero 7, cioè la stampa del risultato. Abbiamo già visto che per stampare qualcosa dobbiamo usare la funzione printf(). Anche questa funzione vuole sapere in che formato stampare e usa gli stessi codici di scanf(). Quindi possiamo scrivere:

printf("%d",c);

E questo è corretto. Ma c’è una grossa differenza tra quello che abbiamo fatto ora e quello che volevamo fare prima.

Riflettiamoci.

Nel caso di printf() noi vogliamo trasmettere alla funzione il valore contenuto nella variabile c. Nel caso di scanf() invece, noi vogliamo che scanf() possa scrivere dentro a. E’ una cosa completamente differente. Come facciamo a fare in modo che scanf() possa scrivere dentro a?

Il modo è il seguente: dobbiamo dare a scanf() non il valore di a, ma il luogo dove sta.

Facciamo un esempio nella vita reale. Se vogliamo dire a qualcuno quanto siamo ricchi, possiamo fargli vedere il nostro estratto conto. Ad esempio gli diremo che abbiamo 100mila euro sul conto corrente. Se invece vogliamo ricevere dei soldi da qualcuno, non è molto importante che costui sappia quanto abbiamo sul conto, ma dobbiamo dirgli piuttosto dove sta il conto corrente: la Banca, la filiale e il numero di conto insomma (ora si usa l’IBAN, ma il concetto è lo stesso). Allo stesso modo, se vogliamo ricevere una e-mail, dobbiamo dare il nostro indirizzo e-mail

Tornando all’informatica, in termini tecnici, dobbiamo dare a scanf() l’indirizzo di memoria dove è localizzata la variabile a. Per fortuna ciò è molto semplice. Il C possiede un operatore che restituisce proprio l’indirizzo di memoria di una variabile, e questo operatore si indica con &. Scriveremo dunque:

scanf("%d",&a);

Ora siamo pronti a scrivere il nostro programma. Apriamo gedit così:

gedit somma.c

e scriviamo:

#include <stdio.h>

int main()
    {
     	int a;
     	int b;
     	int c;

     	scanf ("%d",&a);
     	scanf ("%d",&b);
     	c=a+b;
     	printf ("%d",c);
     	return 0;
    }

Salviamo e compiliamo il programma:

gcc -o somma somma.c

Siccome il programma è corretto, non ci verrà detto nulla. Infine lo eseguiamo:

./somma

Il computer attenderà il nostro input. Vuole sapere cosa mettere in a. Scriviamo 10 e premiamo invio. Ora attende ancora il nostro input. Vuole sapere cosa mettere in b. Scriviamo 20 e premiamo invio. Il computer ora stamperà la somma, cioè 30.

Vedremo nella prossima lezione come rendere il tutto più gradevole per l’utente, con messaggi esplicativi, e come scrivere il programma in modo più leggibile e compatto.

Il problema dell’uguale

Molto disinvoltamente abbiamo scritto c=a+b. Ma se ci riflettiamo, questa forma non era così scontata. Quello che è strano, in questa sintassi, è il segno di uguale. Perché? Perché noi non stiamo facendo un’uguaglianza matematica. E neppure un confronto tra delle variabili.

Stiamo invece dicendo:

calcola a + b e metti il risultato in c”.

Questa è una assegnazione.

Nella programmazione, l’uguale è un segno a volte usato anche per per qualcosa di completamente diverso: il confronto. Ad esempio:

“se a è uguale a b allora stampa il risultato di a + b”.

In questo caso “a è uguale a b” è un confronto.

Il computer confronta il valore di a con quello di b e se sono uguali esegue ciò che gli è stato detto. Per fare i confronti nel linguaggio C, come vedremo, invece del segno “=” useremo il segno di doppio uguale “==”. Altri linguaggi invece usano il segno “=” per il confronto, che è più simile al concetto matematico di uguaglianza, mentre per l’assegnazione usano un segno diverso. Ad esempio il Pascal usa “:=” per l’assegnazione. Altri linguaggi ancora “capiscono” cosa vogliamo fare, se un confronto o una assegnazione, e si comportano di conseguenza. In tal caso si userà il segno “=” sia per il confronto che per l’assegnazione.

Riassunto

Abbiamo quindi imparato che:

  1. Il C è un linguaggio che pretende di sapere precisamente cosa vogliamo fare. Non possiamo dare nulla per scontato.
  2. I dati vanno memorizzati in aree di memoria, chiamate variabili. Ogni variabile possiede un indirizzo nella memoria del computer che si può ottenere mettendo il segno & prima del suo nome. Ovviamente ogni variabile ha anche un valore, e per ottenerlo basta semplicemente il nome della variabile stessa.
  3. Le variabili possono essere di diversi tipi, per contenere diversi tipi di dati. Per ora abbiamo visto solo il tipo int che identifica i numeri interi.
  4. La funzione standard per acquisire dei dati dalla tastiera è scanf(), quella per scrivere a video è printf().
  5. Entrambe vogliono sapere il formato dell’input o dell’output. Per ora abbiamo visto solo il formato “%d” che identifica i numeri interi.
  6. Esiste una grossa differenza tra passare il valore di una variabile ad una funzione oppure il suo indirizzo.
  7. Esiste una grossa differenza tra l’assegnazione di un valore ad una variabile e il confronto.

Per oggi basta🙂

  1. SirFederix
    17 maggio 2010 alle 18:51

    Fantastico🙂
    Io imparo a scuola il C++, che a dire la verità preferisco, ma questa guida mi sembra veramente ben avviata🙂
    Complimenti!

  2. Tetsuotram
    17 maggio 2010 alle 19:14

    Grazie Guido
    scrivi veramente bene!

  3. obo
    17 maggio 2010 alle 21:43

    o’ professore. complimenti per la spiegazione semplicissima e dettagliata😀

  4. Ermes_85
    17 maggio 2010 alle 22:10

    SONO ANCORA ALLA PRIMA,… MA ARRIVO.

  5. Carmelo
    17 maggio 2010 alle 23:04

    Ottimo!

  6. thesigul
    18 maggio 2010 alle 0:24

    interessante e divertente. aspetto che le lezioni si facciamo più complicate.

  7. Alex.diste
    18 maggio 2010 alle 8:38

    Ok fino a qui sapevo, anche se ripassare la scanf e printf non fa mai male abituato a cin e cout del C++, aspetto con impazienza le prossime

  8. telperion
    18 maggio 2010 alle 17:04

    LOL
    Dal dialogo si evince che:

    a ) GCC è decisamente strazzamaroni
    b) probabilmente è femmina …

    LOL

    • 18 maggio 2010 alle 20:27

      a ) GCC è decisamente strazzamaroni

      Be’ sì, come tutti i compilatori C

      b) probabilmente è femmina …

      Di sicuro, infatti dà più errori cinque giorni ogni mese🙂

  9. lived
    20 maggio 2010 alle 9:29

    io non ci capisco una fava nonostante spieghi come se avessimo 5 anni.

    come mai?

    • telperion
      20 maggio 2010 alle 14:02

      Hai 2 anni?
      Sei femmina?
      😛

      (scherzo)

  10. 21 maggio 2010 alle 22:11

    e si potrebbe fare anche cosi?

    int main()
    {
    int a, b, somma;

    cout <> a;

    cout <> b;

    somma=a+b;

    cout << "La somma e': " << somma;

    return 0;
    }

  11. 21 maggio 2010 alle 22:29

    ah si vero… ops🙂

  12. marcomarco
    24 maggio 2010 alle 11:50

    Bella guida, come del resto tutto il tutto il blog.
    Complimenti!

  13. -luk-
    25 maggio 2010 alle 21:40

    Verso le funzioni e oltreeeeeeeeee (cit Toy story)

    Complimenti😀

  14. M
    4 giugno 2010 alle 20:35

    Manca la verifica dell’input O.o

    La guida è ottima però lol.

  15. jpdany
    20 settembre 2010 alle 9:22

    buongiorno e complimenti vivissimi,
    per la prima volta riesco ad avere un minimo di approccio
    (piu o meno) semplice con il c, questo grazie alla tua
    spiegazione sintetica ma accurata !
    Dove posso trovare altre tue lezioni?
    Grazie mille e a presto🙂

  16. manuel
    24 settembre 2010 alle 22:56

    ciao Guido,complimenti per questo corso che,in modo molto efficace,ci ha introdotti nella programmazione.Ma adesso vorrei farti una richiesta che sicuramente è venuta in mente a tutti:conosci qualche sito,o libro scaricaribile da internet o che si possa acquistare che secondo te è buono per proseguire lo studio del C?Praticamente…che materiale consiglieresti a chi vuole approfondire il C?Grazie…ciao

  17. manuel
    4 ottobre 2010 alle 17:55

    Ciao Guido,mi sono fatto prestare un libro per studiare il C e il C++…puntatori,allocazione dinamica della memoria,classi,oggetti….non ho capito niente e mi sono annoiato da morire!!invece il tuo corso di programmazione è molto chiaro e appassionante…aspetto con ansia le tue prossime lezioni!
    Ciao

  18. 28 ottobre 2011 alle 18:58

    telperion :
    Hai 2 anni?
    Sei femmina?

    (scherzo)

    ahahahahahhhh

  19. Iride
    16 aprile 2012 alle 15:56

    sei na Bomba ….. mi puoi girare del materiale per imparare a programmare te ne sarei grato …. ciao

  20. Apla
    9 novembre 2012 alle 14:51

    Ciao, sono in 3 superiore (indirizzo progrmmazzione) e vorrei una dritta su come fare un programma in c++ che legga una sequenza di numeri (dati in input dall’utente) e si fermi quando incontra il valore 0. Mi dareste una mano? Grazie Mille!🙂

  21. 19 novembre 2014 alle 2:22

    Wonderful beat ! I wish to apprentice even as you amend your website, how could i subscribe for a weblog web site?
    Thhe account helped me a applicable deal. I
    hage been a little bit acquainted of this your
    broadcast provided brilliant transparent idea

  1. No trackbacks yet.

Lascia un commento

Inserisci i tuoi dati qui sotto o clicca su un'icona per effettuare l'accesso:

Logo WordPress.com

Stai commentando usando il tuo account WordPress.com. Chiudi sessione / Modifica )

Foto Twitter

Stai commentando usando il tuo account Twitter. Chiudi sessione / Modifica )

Foto di Facebook

Stai commentando usando il tuo account Facebook. Chiudi sessione / Modifica )

Google+ photo

Stai commentando usando il tuo account Google+. Chiudi sessione / Modifica )

Connessione a %s...

%d blogger cliccano Mi Piace per questo: