# Can Mathematica propose an exact value based on an approximate one?

Sometimes, I use Mathematica to do some hypothesis on homeworks to make the question easier. For instance, when I have to compute big sums when $n\to\infty$ and Mathematica can't give the exact answer, I set $n$ to a very big number and I get an approached value.

Is it possible with this value to get possible closed forms just like in Wolfram Alpha (which by the way runs Mathematica's kernel) ?

Example :

I have to find out the sum of all $\frac{1}{2p!}$ when $p$ goes from $0$ to $+\infty$ and let's say Mathematica doesn't directly say it's $\frac{e}{2}$, but it gives 1.66 for a big value of $n$. Is there a function which can figure out which constant is near this number ?

-
Not exactly related to your question, but if you have to calculate something as n towards some limit, you can use the Limit function. – Mike Bailey Jan 17 '12 at 23:15
I know this. In fact, in Mathematica, you can just use Infinity directly in Sum if you want to get the limit of a sum like the one I showed. – Skydreamer Jan 18 '12 at 11:43

## 10 Answers

I can offer a round-about method.

First compute the numerical approximation. I obtain, to high precision,

In[24]:= N[Sum[1/(2*n!), {n, 0, 100}], 100]

Out[24]= 1.\
3591409142295226176801437356763312488786235468499797874834838138620383\
15176773797285691089262583214


Now paste that into a Wolfram|Alpha query, accessed by clicking on the '+' sign at upper left of a fresh input cell. This gives, among other things, possible closed forms.

To the best of my knowledge, the heuristic methods used by W|A for this task are not directly exposed in any other way in Mathematica proper.

-
So I'll use Wolfram for this issue. Thank you for your answer ! – Skydreamer Jan 17 '12 at 22:10
In Mathematica 8: WolframAlpha[ToString@N[Sum[1/(2*n!), {n, 0, 100}], 100], IncludePods -> "PossibleClosedForm", AppearanceElements -> {"Pods"}] – ragfield Jan 17 '12 at 22:22
How does Wolfram Alpha compare to the inverse symbolic calculator? isc.carma.newcastle.edu.au/standard – Phira Jan 18 '12 at 17:38

Here's some code that I used recently, based on code by Paul Abbott [1, 2].

Clear[TranscendentalRecognize]
TranscendentalRecognize[num_Real, basis_List, ord_?Positive, debug:(True|False):False] :=
Module[{vect, mat, lr, ans},
vect = Round[10^Floor[ord - 1] Join[{num}, N[basis, ord]]];
mat = Append[IdentityMatrix[Length[vect]], vect];
lr = LatticeReduce[Transpose[mat]];
If[debug, Print[lr // TableForm]];
(* If a row of lr starts with zero, then it's just a relationship between the basis
element. We move such rows to the end. *)
While[lr[[1, 1]] === 0, lr = RotateLeft[lr]];
(* Now that the first element of the first row is nonzero, we choose it as our best
solution and normalize the answer *)
ans = First[lr[[1]]]^-1 Most[Rest[lr[[1]]]].basis;
Sign[N@ans] Sign[num] ans]

TranscendentalRecognize[num_Real, basis_List] :=
TranscendentalRecognize[num, basis, Precision[num]]


Then, we can identify your number using something like

num = Sum[1/(250*n!), {n, 0, 100}]
TranscendentalRecognize[num, {E, Pi, EulerGamma}]
(* Returns
1.3591409142295226176801437356763312488786235468500
E/2 *)


Compare with

WolframAlpha[ToString[num], IncludePods -> "PossibleClosedForm"]


This code can be cleaned up a little and made more efficient by using the PSLQ based algorithm FindIntegerNullVector introduced in Mathematica version 8.

This is probably something like that which Wolfram|Alpha does. It just tries a combination of various common transcendentals until it comes up with something that looks close. To see some code on how you might write something like that, look at the mpmath (Python) implementation - Number Identification. For example, here's a quick IPython session:

In [1]: from mpmath import *

In [2]: mp.dps = 20;

In [3]: identify(1.35914091422952261768014, ['e', 'pi'])
Out[3]: '((1/2)*e)'

-
Nice snippet of code but you still have to give the constant you are thinking of as an argument. – Skydreamer Jan 17 '12 at 22:35
@Skydreamer: Thanks. For some reason I thought that mpmath used heuristics to help guess the basic constants, much in the same way that W|A does. But it looks like I was wrong.... Of course, there's always the ISC and OEIS to help you guess. – Simon Jan 17 '12 at 22:44
Somehow, this having less upvotes than "ask Wolfram Alpha" bothers me... – acl Jan 18 '12 at 13:18
@acl: Well, my answer doesn't completely satisfy the OP's requirements. Also, both Paul and Daniel played with LLL based transcendental number recognition in Mma way back then (only Paul published code). So I don't mind Daniel getting more upvotes! – Simon Jan 18 '12 at 21:05
It's not Daniel (or any other person) I am bothered with... – acl Jan 18 '12 at 21:11

I asked a similar question on MathGroup some years ago.

If you read that thread, you'll get some pointers about how these algorithms work (they're based on lattice reduction, see also here).

• There's a package by Eric Weisstein for doing something like this: see ToExact and TranscendentalRecognize in Simplify.m.

• This issue of the Mathematica Journal is relevant too (see Tricks of the Trade -- Transcendental Recognition)

• Plouffe's inverter may also be of interest

-
Really nice brainstorming on this topic. Thank you ! – Skydreamer Jan 24 '12 at 15:52

Following up on Simon's note in his answer:

This code can be cleaned up a little and made more efficient by using the PSLQ-based algorithm FindIntegerNullVector[] introduced in Mathematica version 8.

here is a re-implementation of Abbott's TranscendentalRecognize[]:

TranscendentalRecognize[num_?NumericQ, basis_?VectorQ] := Module[{lr, ans},
lr = FindIntegerNullVector[Prepend[N[basis, Precision[num]], num]];
ans = Rest[lr].basis/First[lr];
Sign[N[ans]] Sign[num] ans]


As already noted, this will only work for recognizing linear combinations of any constant given in the list basis (it thus can't be used to recognize $\pi/e$ from its decimal expansion, for instance).

To use the same example:

TranscendentalRecognize[1.35914091422952261768014, {Pi, E}]
E/2

-
Nice snippet, I just can't understand why it works but that's nice ! – Skydreamer Oct 3 '12 at 16:00
Well, discussing the theory of PSLQ will take a fair amount of deep math; suffice it to say that FindIntegerNullVector[] tries its best to find integers $c_1,\dots,c_n$ such that given constants, $a_1,\dots,a_n$, $c_1 a_1+\cdots+c_n a_n$ is as near to zero as possible. – J. M. Oct 3 '12 at 16:07

Here's a variant of Danny's answer, that's perhaps a bit more automated:

WolframAlpha[ToString[
NSum[1/(2*n!), {n, 0, Infinity}, WorkingPrecision -> 50]],
{{"PossibleClosedForm", 1}, "ComputableData"}]

-

Rationalize may be an option, although I doubt it is as powerful as what WA is doing. Here's the documentation.

-
If need be, RootApproximant[] does the job for general algebraic numbers. – J. M. Jan 17 '12 at 22:16
Rationalize returns a rational number (fraction). But we know that the exact solution to the problem of the o/p is not rational, and the question is asking about a general approach, and in general the solution is not rational. I'm almost ready to downvote this reply. – Andreas Lauschke Jun 29 '12 at 16:02
@AndreasLauschke the question is "can it propose closed forms", and what I suggest does. That this won't work for an example doesn't make it not an answer to the general question. But of course you are free to downvote anything you want. – acl Jun 29 '12 at 17:18

This answer doesn't use Mathematica, but another great resource for this sort of thing is the Online Encyclopedia of Integer Sequences. I've used it successfully many times when Mathematica has given me a decimal approximation but I've been after an analytical expression. Among other things, the encyclopedia includes the decimal expansions of a huge number of exact quantities. For your example, the following search returns the result 'E/2':

You can of course also include the leading 1 in your search, but I've found it useful in the past not to -- if it turned out that the number you had was actually 2+e/2, for example, the above search would still let you determine that the decimal portion came from e/2, whereas the OEIS won't include the expansion of n+e/2 for any non-zero integers n.

-
Speakin' of which... – J. M. Jan 18 '12 at 16:44
Oh sweet, I didn't know about that one, thanks! – Michael Underwood Jan 18 '12 at 16:49

This question reminds me somewhat of a post on the Wolfram Blog about finding rational approximations to Pi. It may be of interest to you.

The only way I know to approach this sort of thing is by genetic programming. Expressions in Mathematica can be manipulated like trees. You could generate a population of random expressions, see how closely they come to your approximation, then take the best few, change them slightly, and repeat again and again.

In this way you search the space of "nice" exact expressions built from some building blocks. I imagine, however, that this would be a difficult algorithm to write.

-
Interesting blog post, I'll read about this but I don't think I'm gonna try to implement this, that's just... hard ! – Skydreamer Jan 17 '12 at 22:16
something along these lines: stackoverflow.com/a/8483298/559318 may also be fun to play with. – acl Jan 17 '12 at 22:16

This is extremely hacky, because I don't know how to do proper html processing in Mathematica. The following looks looks up the value on the Inverse Symbolic Calculator and returns the best match.

InverseSymbolic[x_] :=
Module[{url, result, start, end, preprocess, guess, formatted},
url = "http://isc.carma.newcastle.edu.au/standardCalc";
result = StringJoin[Flatten[Import[url,
"RequestMethod" -> "POST",
"RequestParameters" -> {"input" -> ToString@x}]]];

preprocess  =
StringReplace[
result, {"Best guess: " -> "!RESULT!", "</h2>" -> "!RESULT!"}];
{start, end} = StringPosition[preprocess, "!RESULT!"][[1 ;; 2]];
guess = StringTake[preprocess, {Last@start + 1, First@end - 1}];

formatted = StringReplace[guess, {"(" -> "[", ")" -> "]"}];

If[SyntaxQ[formatted],
ToExpression[formatted],
If[SyntaxQ[guess],
ToExpression[guess],
guess]
]
]


This relies on the fact that the "best guess" is located between the strings Best guess and </h2> within the HTML.

It first replaces these with a temporary marker to delineate the answer from the rest of the text. After the replacement, it finds the position of the markers and returns what's in between it.

Finally, it tries to replace parenthesis with square brackets and sees if that's syntactically correct. If not, it tries the one with parenthesis. If either of those two are fine as Mathematica statements, it converts them to expressions. Otherwise, it just returns it as a string.

-
Nice! However, it does not fail very elegantly when ISC returns "Standard inverse calculate found nothing." – Simon Jan 19 '12 at 7:29
@Simon: Like I said it's very hacky :( There's a lot more I want to fix with this. – Mike Bailey Jan 19 '12 at 7:31

Use the built in function Sum:

Sum[1/(2 p!), {p, 0, Infinity}]


Mathematica outputs E/2.

-
My question is about sums it can't compute. I gave a simple example but there are harder sums that don't give an exact result. – Skydreamer Jan 17 '12 at 21:49
If you want Wolfram|Alpha like results, you can always use WolframAlpha["Sum[1/(2 p!),{p,0,Infinity}]"]` – Eli Lansey Jan 17 '12 at 21:52
@Eli I think the question being asked is "can we get Mathematica to propose a possible exact number based on an approximation to it?" – JOwen Jan 17 '12 at 21:53
@Sky: something like a Mathematica interface for the ISC, then? – J. M. Jan 17 '12 at 21:53
@Sky: oops. Here is the new location. – J. M. Jan 17 '12 at 22:03