2015-01-29 12 views
5

Hai 2 funzioni;virgola mobile; Division vs Multiplication

f(x)= x(((x+1)^(1/2))-(x^(1/2)))  
g(x)= x/(((x+1)^(1/2))+(x^(1/2))) 

Quale è più preciso?

Nota a margine: Se si potrebbe spiegare perché, mi sarebbe davvero aiutare, ho la sensazione che sia f (x) in quanto non v'è un denominatore ma non sono sicuro al 100%.

+1

Waaaay off-topic per SO, provare [math.stackexchange] (http://math.stackexchange.com/). –

+0

Ciao Claire, StackExchange è suddiviso in più pagine, concentrandosi su argomenti diversi. Uno di questi è [Matematica] (http://math.stackexchange.com/). Dovresti fare la tua domanda lì. – Stefan

+0

Grazie ragazzi, farò proprio questo –

risposta

5

L'aritmetica in virgola mobile è molto diversa dalla matematica reale. In particolare, l'aritmetica a virgola mobile non è associativa o distributiva. Pertanto espressioni matematicamente equivalenti non sono necessariamente equivalenti se valutate con aritmetica a virgola mobile a precisione finita. Questo è il caso anche quando le singole operazioni, come addizione, sottrazione, moltiplicazione, divisione e radice quadrata producono risultati arrotondati, come richiesto dallo IEEE-754 floating-point standard.

In questo caso, g() sarà molto più preciso di f() in media, e anche per il caso specifico di x = 500. Il motivo è che f() soffre di cancellazione sottrattiva. Ciò si verifica durante la sottrazione effettiva di due numeri in virgola mobile che sono quasi identici in grandezza. Le cifre iniziali si annullano durante la sottrazione, lasciando solo alcune cifre finali rimanenti che entrano nel calcolo successivo. Inoltre, qualsiasi errore di arrotondamento accumulato nelle cifre finali degli operandi originali da sottrarre può essere ingrandito da un calcolo successivo. Una spiegazione estesa con esempio può essere trovata in this Wikipedia article.

In questo caso, sqrt(x+1) e sqrt(x) hanno quasi la stessa magnitudine, in particolare la magnitudine degli incrementi di x. Utilizzando l'esempio di x = 500 e impiegando IEEE-754 a precisione singola aritmetica, troviamo:

x = 500 f(x) = 0x1.659ae0p+3 (11.175156) reference = 0x1.659798p+3 (11.174755) 
x = 500 g(x) = 0x1.659798p+3 (11.174755) reference = 0x1.659798p+3 (11.174755) 

L'errore in f(500) è 420 ulps, mentre g(500) batte correttamente arrotondato risultato singola precisione.

+0

Per curiosità, ci sono valori per i quali 'f' è più preciso? Non solo "in media"? – Teepeemm

+0

OT: strano che la mia risposta sia diventata automaticamente una wiki della comunità. @Teepeemm: Sì, da un controllo superficiale con argomenti a precisione singola IEEE-754 casuali, esistono numerosi casi simili. Ad esempio: 'x = 0x1.6fa276p-2 (3.59018177e-1); f (x) = 0x1.a09844p-3 (2.03415424e-1); g (x) = 0x1.a09846p-3 (2.03415439e-1); ref = 0x1.a09844p-3 (2.03415425e-1); ulperr (f) = 6.71231e-2; ulperr (g) = 9.32877e-1' – njuffa