High precision expressions and functions
- To: mathgroup at smc.vnet.net
- Subject: [mg13749] High precision expressions and functions
- From: "Allan Hayes" <hay at haystack.demon.cc.uk>
- Date: Wed, 19 Aug 1998 01:38:36 -0400
- Sender: owner-wri-mathgroup at wolfram.com
The recent thread "High precision numbers and Plot", and the article "Bending Plot to Your Needs" by Stan Wagon in Education and Research Volume 7 No 2, Spring 1998 stimulated some experiments which resulted in the following code PrecisionExpression::usage = "PrecisionExpression[expr, {x1,x2..}, p] for symbols x1,x2 and positive integer p gives an expression PEexpr which, with x1=r1, x2 = r2,.., evaluates with working precision p, starting with, xi = If[InexactNumberQ[vi], SetPrecision[vi, p], vi]. PrecisionExpression[expr, x, p], for a symbol x evaluates like PrecisionExpression[expr, {x}, p] " PrecisionExpression[expr_, x_, p_] := Function[x, #][##2] &[ expr /. r_?InexactNumberQ :> SetPrecision[r, p], Sequence@@( Switch[#, _?InexactNumberQ, SetPrecision[#, p], _?NumberQ, # ] &/@Flatten[{x}] ) ] PrecisionFunction::usage = "PrecisionFunction[expr, {x1,x2..}, p] for symbols x1,x2 and positive integer p gives a function FPexpr with working precision p. PFexpr[v1,v2,..] becomes PFexpr[If[InexactNumberQ[v1], SetPrecision[v1, p], vi] ,..]. PrecisionFunction[expr, x, p], for a symbol x evaluates like PrecisionFunction[expr, {x}, p]. " PrecisionFunction[expr_, x_, p_] := Function[x, Function[x, #][##2]] &[ expr /. r_?InexactNumberQ :> SetPrecision[r,p], Sequence@@( Switch[#, _?InexactNumberQ, SetPrecision[#, p], _?NumberQ, # ] &/@Flatten[{x}] ) ] PrecisionExpression is the more flexible, but usually gives a slightly slower result. Examples: (1)Speed f1 = Normal[Series[Cos[x], {x, 0, 200}]]; expr = PrecisionExpression[f1, {x}, 30]; Block[{x = 1.2}, Do[expr, {50}] // Timing] {6.26 Second, Null} foo = PrecisionFunction[f1, {x}, 30]; Do[foo[1.2], {50}] // Timing {4.56 Second, Null} (2) Applications f2= Log[1. - Erf[x]] + x^2; Plot[#[x], {x, 0, 8}] &[PrecisionFunction[f2, x, 30]] Plot[Evaluate[PrecisionExpression[{f2, Sin[x]-1.5}, x, 30]], {x, 0, 8}] Plot3D[Evaluate[PrecisionExpression[f2 Sin[y], {x,y}, 30]], {x, 0, 8},{y,0,8}] ContourPlot[Evaluate[PrecisionExpression[f2 Sin[y], {x,y}, 30]], {x, 0, 8},{y,0,8}] Note: compiling is not used (it would spoil the precision), but we might take the precaution of setting Compiled -> False. The (brief)time used for checking if compiling is possible would also be save. ------------------------------------------------------------- Allan Hayes Training and Consulting Leicester UK http://www.haystack.demon.co.uk hay at haystack.demon.co.uk voice: +44 (0)116 271 4198 fax: +44(0)116 271 8642