View Full Version : [C] Ma mi fa le operazioni??
Marinelli
03-02-2005, 20:10
Buonasera a tutti, oggi ho scritto per esercizio un programma per il calcolo della radice quadrata e questa è la funzione che fa l'effettivo calcolo della radice:
float Radice (float Num, float N)
{
float Temp, Scarto, Media;
if (0==Num) return (Num);
Temp=Num/N;
Scarto=Temp-N;
Media=((Temp+N)/2);
if ((Scarto<Precisione)&&(Scarto>-Precisione)) return (Media);
else return (Radice (Num, (Temp+N)/2));
}
Num è il numero di qui trovare la radice, N è un numero intero positivo che io ho scelto come 2.
Non capisco come sia possibile che Temp sia uguale a Media quando lo scarto è diverso da 0... restituire Temp o resistituire Media è la stessa cosa.
Ciao e grazie :)
Alberto
Scarto=Num/N-N
Media = ((Num/N + N)/2) = ((Scarto + 2*N)/2) = Scarto / 2 + N
Temp = Num/N = Scarto + N
Quindi Media = temp se Scarto + N = Scarto / 2 + N...cioè solo se scarto == 0...
Marinelli
04-02-2005, 09:45
Invece Media e Temp mi risultano uguali anche se lo scarto è diverso da zero (di poco ovviamente).
Vuoi che ti passi il sorgente?
Ciao
Ok...allega... Comunque ricordati che il risultato di sequenze di operazioni diverse floating point che comunque porterebbero ad un risultato equivalente dal punto di vista matematico, possono portare ad un risultato "informatico" diverso...
Per questo lo zero in questi casi praticamente non esiste...
Prova ad usare i double e non i float..e vedi se la situazione migliora...
Marinelli
04-02-2005, 12:36
Ho provato con i double, ma mi viene tutto un casino, con numeri stranissimi.
Ciao.
P.S. Cambia l'estensione del file da .zip a .c ;)
Ora funziona ;)
#include <stdio.h>
double Radice (double Num, double N);
double Precisione;
int main()
{
float Numero;
double Ris;
printf ("Inserisci il numero di cui calcolare la radice: ");
scanf ("%f", &Numero);
Precisione=0.00001;
if ((Numero<0)||(Numero>16777216))
{
printf ("Numero negativo o troppo grande\n");
system("PAUSE");
return (0);
}
if (Numero>16392) Precisione=0.0001;
if (Numero>1049088) Precisione=0.001;
printf ("Temp\t\t Scarto\t\t Media\t\t\n");
Ris=Radice (Numero, 3);
printf ("Risultato: %f\n", Ris);
system("PAUSE");
return (0);
}
double Radice (double Num, double N)
{
double Temp, Scarto, Media;
if (0==Num) return (Num);
Temp=Num/N;
Scarto=Temp-N;
Media=((Temp+N)/2);
printf ("%f\t %f\t %f \n", Temp, Scarto, Media);
if ((Scarto<Precisione)&&(Scarto>-Precisione)) return (Temp);
else return (Radice (Num, (Temp+N)/2));
}
Mi raccomando indenta...
lombardp
04-02-2005, 14:35
Originariamente inviato da Marinelli
Invece Media e Temp mi risultano uguali anche se lo scarto è diverso da zero (di poco ovviamente).
Se non ho capito male, dovrebbe essere un esempio di "errore di cancellazione", tipico nei calcoli a virgola mobile con numero finito di cifre.
Faccio un esempio:
A= 1,0
B= 0,0000000...(tanti zeri)...1
Se calcoli A+B ottieni
A+B = 1,0
Perché il singolo numero floating point non ha abbastanza cifre per rappresentare il numero grande e il numero piccolo.
... se poi non è errore di cancellazione, dimentica tutto.
Marinelli
04-02-2005, 18:48
Ci avevo pensato anche io... ma lo scarto era apprezzabile anche con la precisione dei float.
X Cionci, grazie, adesso ci guardo... hai solo modificato float con double ?
Ciao
Marinelli
04-02-2005, 18:52
Originariamente inviato da cionci
Ora funziona ;)
Mi raccomando indenta...
Ma Numero è un float e lo passi alla funzione come double?
Indenta in che senso? :confused:
Ciao e grazie ancora ;)
Fenomeno85
04-02-2005, 21:58
Originariamente inviato da Marinelli
Ma Numero è un float e lo passi alla funzione come double?
Indenta in che senso? :confused:
Ciao e grazie ancora ;)
significa effettuare le rientranze ;) è per la lettura e per la chiarezza ;)
~§~ Sempre E Solo Lei ~§~
Marinelli
04-02-2005, 22:14
Yes, le rientranze le faccio sui blocchi... qui praticamente non ce ne sono...
Ogni volta che apri una grafa è un nuovo blocco quindi questo codice andrebbe scritto così:
double Radice (double Num, double N)
{
double Temp, Scarto, Media;
if (0==Num) return (Num);
Temp=Num/N;
Scarto=Temp-N;
Media=((Temp+N)/2);
printf ("%f\t %f\t %f \n", Temp, Scarto, Media);
if ((Scarto<Precisione)&&(Scarto>-Precisione)) return (Temp);
else return (Radice (Num, (Temp+N)/2));
}
Togli l'ultimo else...non serve a niente...anzi, alcuni compilatori ti potrebbero dare anche un warning...
Puoi mettere double anche numero, ma devi cambiare la scanf in questo modo: scanf ("%lf", &Numero);
Marinelli
05-02-2005, 11:06
Originariamente inviato da cionci
Puoi mettere double anche numero, ma devi cambiare la scanf in questo modo: scanf ("%lf", &Numero);
Ah, ecco... il problema era quello. Grazie di tutto ;)
vBulletin® v3.6.4, Copyright ©2000-2025, Jelsoft Enterprises Ltd.