Go Down

Topic: dubbio su else if (Read 1 time) previous topic - next topic

droidprova

Ragazzi solo una conferma. Scrivere questo:

Code: [Select]
if (a==1) {
        eseguo un comando;
      }
      if (a==2) {
        eseguo un comando;
      }
      else {                                     
      if (a<3) {
        eseguo un comando;
      }
       if (a>4) {
        eseguo un comando;
      }
     }


o questo:

Code: [Select]
if (a==1) {
        eseguo un comando;
      }
      if (a==2) {
        eseguo un comando;
      }
      else if (a<3) {
        eseguo un comando;
      }
      else if (a>4) {
        eseguo un comando;
      }


è la stessa cosa vero? Grazie

gpb01

#1
Apr 16, 2018, 03:56 pm Last Edit: Apr 16, 2018, 03:57 pm by gpb01
NO, stai indentando male e mettendo male gli else ...

Code: [Select]
if (condizione) {
  // da fare se condizione vera
}
else {
  // da fare se condizione falsa
}


In caso di più if in cascata:

Code: [Select]
if (condizione) {
  // da fare se condizione vera
}
else if (condizione) {
  // da fase se la prima condizione è falsa, ma la seconda è vera
}
else if (condizione) {
  // da fare se la prima condizione è falsa, la seconda pure e la terza e vera
}
else {
  // da fare se tutte le condizioni sono false
}


Guglielmo
Search is Your friend ... or I am Your enemy !

Silente

O meglio, il codice ha senso, viene compilato e fa le sue, non ci sono errori.
Il problema è cosa gli dici di fare. Il C controlla le condizioni degli if solo quando si presentano. Nulla vieta, quindi, che il corpo di un if (tra le graffe) renda non più valida la condizione (tra le tonde), o la renda valida per un if successivo.
Se la variabile non la tocchi mai nel corpo degli if allora si, possono essere intercambiabili, ma se anche accidentalmente la tocchi... Apriti Cielo.
Infatti ecco un esempio
Code: [Select]

byte a=0;
//Codice
if (a==0)
{
a=1;
Serial.print (F("Ciao "));
}
if (a==1)
{
a=2;
Serial.println (F("Mondo"));
}
if (a==3)
{
a=0;
//...
}
//...

viene eseguito tutto, perché il programma trova che una variabile a vale zero.
Poi trova che se una variabile a vale zero (ed è vero) devo fare un insieme di cose, tra cui far valere a come 1. E quindi lo faccio, ormai sono entrato...
Uscito dall'if numero zero ho una variabile a che vale uno.
Oh, che bello, ho un altro if in cui se a vale uno (ed è vero) faccio altro, tra cui rendere a pari a 2.
...
Se, invece, anziché essere tutti if() fossero tutti else if() tranne il primo la cosa cambierebbe di molto.
Il programma trova che a vale zero
Il programma trova un if o un else. L'if dice che se a vale zero...
Essendo vera la condizione eseguo la if()
Non ho scelto la esle, che quindi ignoro, per ora.
...
Secondo giro, a adesso, facciamo, vale uno
La if a==0 non la prendo, ma scelgo la esle.
La quale else contiene un'altra scelta. Se a==1 entro nella SECONDA if, se no entro nella else
a vale uno, entro nella seconda if.
La faccio e salto la esle
Terzo giro
...


Ci tengo a chiarire una cosa: il fatto che siano messi male gli else o meno dipende tutto da cosa vuoi fare, non è assoluto.

Inoltre se devi fare tanti test di uguaglianza su una stessa variabile ti consiglio la switch case. È una forma di if su una sola variabile, molto più semplice da scrivere
Dove va un numero va una variabile o una funzione. E dove va una boolean va un insieme di test.

Se vuoi ottenere devi saper spiegare

In pochi capiscono l'importanza di formattare, sii tra di essi

Etemenanki

Piu che altro a me sembra (ma magari sbaglio), che nel primo caso, l'ultimo if puo venire eseguito anche se una delle condizioni del penultimo e' vera, se nel frattempo a cambia, mentre il secondo caso dovrebbe venire gestito diversamente ...

Cerco di spiegarmi ... siccome l'else e' un "altrimenti", in pratica, credo che introduca un controllo condizionale sulla catena ... nel primo caso, se "a" e' 2, viene eseguito quel comando, ma se intanto, prima che l'ultimo controllo venga effettuato, "a" diventa maggiore di 4 (ad esempio perche' quel comando pone "a" a 5), viene eseguito ANCHE quel comando ... mentre nel secondo caso, visto che tutti i successivi controlli sono sotto "else", se "a" e' due, viene eseguito quel comando, ma gli altri controlli vengono saltati, per cui anche se nel fratempo "a" e' diventato maggiore di 4, NON viene eseguito l'ultimo comando ... o almeno, e' questa l'impressione che mi da quella sequenza ...

... l'ho azzeccata, stavolta ? ... :D
"Sopravvivere" e' attualmente l'unico lusso che la maggior parte dei Cittadini italiani,
sia pure a costo di enormi sacrifici, riesce ancora a permettersi.

Etemenanki

...
Inoltre se devi fare tanti test di uguaglianza su una stessa variabile ti consiglio la switch case. È una forma di if su una sola variabile, molto più semplice da scrivere
pero', se non mi sbaglio, la switch case puo gestire solo sequenze numeriche unitarie regolari, giusto ?

Voglio dire, posso usare una switch case se le condizioni sono tipo 0, 1, 2, 3, 4 ... ma NON credo si possa usare se le condizioni da controllare sono, ad esempio, 0, 1, 3, 7, maggiore di 9 ... corretto ?
"Sopravvivere" e' attualmente l'unico lusso che la maggior parte dei Cittadini italiani,
sia pure a costo di enormi sacrifici, riesce ancora a permettersi.

gpb01

#5
Apr 16, 2018, 05:22 pm Last Edit: Apr 16, 2018, 05:22 pm by gpb01
pero', se non mi sbaglio, la switch case puo gestire solo sequenze numeriche unitarie regolari, giusto ?
No, il solo limite è che lo switch vuole una variabile intera e nei case dei valori di tale int (costanti).

Guglielmo
Search is Your friend ... or I am Your enemy !

Silente

E poi switch non permette "maggiore di" "minore di". Devi prevedere tutti i casi
Dove va un numero va una variabile o una funzione. E dove va una boolean va un insieme di test.

Se vuoi ottenere devi saper spiegare

In pochi capiscono l'importanza di formattare, sii tra di essi

gpb01

#7
Apr 16, 2018, 05:34 pm Last Edit: Apr 16, 2018, 05:34 pm by gpb01
E poi switch non permette "maggiore di" "minore di". Devi prevedere tutti i casi
... infatti ho scritto :

...  e nei case dei valori di tale int (costanti).
:D :D :D

Guglielmo
Search is Your friend ... or I am Your enemy !

droidprova

#8
Apr 16, 2018, 06:05 pm Last Edit: Apr 16, 2018, 06:08 pm by droidprova
Grazie a tutti....!  :smiley:

Quello che sto cercando di fare è un codice che a partire dal valore di pressione barometrica al suolo più quello dell'umidità, possa generare una sorta di previsione meteo locale. Tutti questi if, poi andranno a gestire uno switch case per la stampa dell'iconcina sull'app. Vi mostro il codice.

Queste condizioni si basano su alcune letture che ho fatto su svariat siti dedicati. Ovviamente ciò non ha valore scientifico ma può aiutare, a patto che funzioni  :smiley-mr-green: .

Ditemi se fa quello che vorrei ottenere, il codice lo fa. Grazie 1000!


Code: [Select]


void previsione()
{
  if (contatore == 0) {  // forza il confronto di p_rif e p_slm solo al primo avvio
    p_rif = p_slm;
    contatore++;
  }

  if ((millis() - tempo_prev) > 10800000) {     // intervallo tempo per i vari confronti

    if (p_slm < p_rif) {          // condizioni tempo in peggioramento
      if ((p_rif - p_slm >= 1) && (p_rif - p_slm <= 2)) {
        prev = 1; // partly cloudy/rain's cloudy
        p_rif = p_slm;
      }
      if ((p_rif - p_slm > 2) && (p_rif - p_slm <= 3)) {
        prev = 2; //rain light
        p_rif = p_slm;
      }
      if ((p_rif - p_slm >= 5) && (h > 70)) {
        prev = 3;   // thunderstorms
        p_rif = p_slm;
      }
      else if ((p_slm <1000) && (h > 70)) {             // blocco da eseguire se nessuna delle precedenti condizione è verificata
        prev = 1;   // partly cloudy/rain's cloudy
        p_rif = p_slm;
        }
    }
    if (p_slm > p_rif) {        // condizioni tempo in miglioramento
      if ((p_slm - p_rif >= 1) && (p_slm - p_rif <= 2)) {
        prev = 4;  //partly cloudy
        p_rif = p_slm;
      }
      if ((p_slm - p_rif > 2) && (p_slm - p_rif <= 3) && (h < 60)) {
        prev = 5; // sunny
        p_rif = p_slm;
      }
      else {                                            // blocco da eseguire se nessuna delle precedenti condizione è verificata
      if ((p_slm > 1001) && (p_slm <= 1015)) {            
        prev = 4; // partly cloudy
        p_rif = p_slm;
      }
      if ((p_slm > 1016) && (h < 60)) {
        prev = 5; // sunny
        p_rif = p_slm;
       }
     }
    }
    tempo_prev = millis();
  }
}

nid69ita

Sembra quasi che a molti le parentesi graffe aperte diano noia.
Per me ha molto più senso scrivere
if( test)
{
}

e non 
if(test) {
}
SOPRATTUTTO per i nuovi.
my name is IGOR, not AIGOR

gpb01

#10
Apr 16, 2018, 06:52 pm Last Edit: Apr 16, 2018, 06:56 pm by gpb01
Sembra quasi che a molti le parentesi graffe aperte diano noia ...
... non l'ho capita ... le parntesi graffe ci sono in entrambi gli stili, e solo questione di abitudine, ma non vedo che differenza faccia mettere la graffa sulla stessa linea del IF o subito sotto ... ripeto, e solo questione di scelta dello stile usato.

Guglielmo
Search is Your friend ... or I am Your enemy !

nid69ita

#11
Apr 16, 2018, 06:57 pm Last Edit: Apr 16, 2018, 07:01 pm by nid69ita
Per chi inizia è molto meglio lo stile con graffa sotto l'if (naturalmente con indentazione corretta)
Anche l'IDE di Arduino alla graffa chiusa ti evidenzia la graffa aperta.
E' solo questione di stile, ma secondo me è anche una questione di imparare a "contare" tot graffe aperte, tot graffe chiuse. Se sono su stessa colonna (quindi indentato per bene) è molto più difficile per i neofiti sbagliare.
Quindi viva Horstmann style !!  (sarà che ho iniziato con il Pascal)

@Guglielmo, prendi il codice di @droid al post#8, fagli mettere le graffe aperte su riga successiva, CTRL+T e secondo me avrà un codice più leggibile (per lui)
Ovviamente è una mia opinione. Ma ho insegnato per un pò di anni e mi pare che lo stile Horstmann aiuta ai nuovi a fare meno errori.
my name is IGOR, not AIGOR

Standardoil

Prima legge di Nelson (che sono io): Fai le stesse cose sempre alla stessa maniera: quegli errori li hai già corretti

gpb01

Per chi inizia è molto meglio lo stile con graffa sotto l'if
... de gustibus non est disputandum ... preferisco lo stile K&R :D

Guglielmo
Search is Your friend ... or I am Your enemy !

droidprova

Ragazzi a parte la forma che deriva anche dal fatto che stavo editando su un foglio note, ciò non toglie che mi avete fatto notare una cosa buona e giusta, per il resto ciò che ho scritto è più o meno giusto?

Grazie

Go Up