Memoization is a technique for improving performance by having a function remember its previous arguments. For example,
f[x_]:=f[x]=mySlowFunction[x]
will be slow on its first evaluation for a given x
, but will be vastly faster on subsequent calls for that x
, whereas repeated calls to mySlowFunction[x]
will always be slow.
My case is that I would like to discretize the parameter space to increase performance at the expense of accuracy. Any Real
value of x
should be evaluated only at the rounded value, which itself should be memoized. Compare these toy examples:
Clear[f];
f[x_] := f[x] = Total[Table[x, {100000}]]
Clear[g];
g[x_Real] := g[Round[x]];
g[x_Integer] := g[x] = Total[Table[x, {100000}]]
Timing[f[0]][[1]]
(* 0.002007 *)
Timing[f[0.1]][[1]]
(* 0.001523 *)
Timing[g[0]][[1]]
(* 0.002059 *)
Timing[g[0.1]][[1]]
(* 0.000013 *)
The 2nd call to g[x]
is much faster than the first call, even though the actual input (0.1
) has not been memoized itself. The second call is less accurate, and I can live with that.
But I would like to Round[]
to arbitrary precision. For example, I could try
g[x_Real] := g[Round[x,0.01]];
The g[x_Integer]
pattern of the 2nd definition would fail in this case. I tried the naive
h[x_Real] := h[Round[x,0.01]] = Total[Table[x, {100000}]]
which does not produce the desired effect.
How could one memoize a function's inputs, such that subsequent calls to the function at values near the (rounded) memoized inputs are replaced by calls at those memoized inputs?
For the curious, I am tracing particles under the influence of a force. That force can be calculated to high precision at arbitrary locations, but this is slow. I'd like to cache the force at discrete locations, so that particles within some distance of a previously-calculated value use the cached value.
f[x,y,z]
and not justf[x]
, right? For the 1D case I had some easy ideas for good precision (interpolation), but the multidimensional one is more complex. $\endgroup$f[x_ /; Round[x, prec] == x] := f[x] = slowf[x]; f[x_] := f[Round[x, prec]]
. The variableprec
gives you the precision. $\endgroup$Interpolation[]
approach $\endgroup$