# Save part of memoized function

I have a function whose performing a series of expansions of a complicated function, which can take a lot of time. To avoid bottlenecks, I use memoization so I need to evaluate it only once.

For completness let's say it is simply

f[a_, trunc_] := f[a, trunc] = Series[Sin[a*x], {x, 0, trunc}] // Normal;


In my script I will need several expansions for different a at a given trunc (defined at the beginning of the script and not modified until the end). As evaluating f can take more than a minute and I need order 50 values of a, I usually place a

Save["savedExpansion.m", f];


at the end of the script so that next time I can directly load it with Get and same myself some time.

Now, I want to create a script that basically doing only the initialisation of f for both the values of a and trunc I will ever need so that I have everything that takes time to compute once and for all. I wrote the following snippet of code

listA = Table[a, {a, 1, 10}];
listTrunc = Table[trunc, {trunc, 1, 10}];

Do[
ParallelDo[Print["Going over ",a];f[a, trunc];, {a, listA}];
Save["savedExpansionTrunc" <> ToString[trunc] <> ".m", f];
, {trunc, listTrunc}];


The thing is that each created file contains the values for f of all the previous values trunc, which I want to avoid to save memory. I there a way of saving only the values of f[a,trunc] for a given trunc? Moreover, is it possible to clear the values from memory with Clear without clearing the definition of the function at the same time?

By the way, is there a best practice for these kinds of things, e.g. using Save rather than Dump, or using parallelisation?

• My ABBYLingvo does not include "memoized". Is it a new English word? What does it mean? – user64494 Jun 14 '19 at 13:36
• @user64494 Memoization, (wiki) is a common term in programming for functions that remember output for specific input. It's a relatively new word (1968). – Carl Lange Jun 14 '19 at 13:42
• Duplicate of mathematica.stackexchange.com/a/193305/26598 ? – Roman Jun 14 '19 at 14:07
• @Roman my question is more about how to save f in a file only for a subset of value (i.e. for a given trunc rather than everything) than how memoization or Once work. The file that I create will be sent to different machines, so I need to get a file in the end. – Bulkilol Jun 14 '19 at 16:57
• Is it the series expansion that takes a lot of time? Or the numerical evaluation for a given a. If the expansion takes a lot of time you can curry f by doing something like f[trunc_] := f[trunc] = Function[a, Evaluate[Normal@Series[Sin[a x], {x, 0, trunc}]]] and then calling f[0][1.23] or f[2][4.56]. When you save f you would just save the functions, not the numerical evaluations. – evanb Jun 16 '19 at 8:49

Whenever you set a value, you can later unset it. For example:

ClearAll[f];
f[n_] := f[n] = n^2;
Do[f[n], {n, 3}]; DownValues[f]
Do[f[n] =., {n, 2}]; DownValues[f]


first sets the values for f[1], f[2], f[3] and then unsets all but the last. The DownValues[f] allows you to check these values. You can now save the function f and its remaining set value.

If the expansion takes a lot of time and the subsequent numerical evaluation is easy, you might just want to store the series expansions. One way to do this is by currying f, as in

f[trunc_] := f[trunc] = Function[a, Evaluate[Normal@Series[Sin[a x], {x, 0, trunc}]]]


and then you can save f and it saves the expansions. You then evaluate f[3][4.56] (trunc=3, a=4.56, for example). Note that the result is a function of a and has an unbound x (in your example).

If you just want to remember values for a specific trunc, you can do something like

worker[trunc_, a_] := Normal@Series[Sin[a x], {x, 0, trunc}]

wrapper[trunc_, a_] := worker[trunc, a]
wrapper[1, a_] := wrapper[1,a] = worker[trunc, a]


which will save values for wrapper[1,a] but not for other values of trunc. You can add additional truncs (or as or pairs of trunc and a) to be remembered by adding additional specializations of wrapper.