Skip to main content
23-Emerald V
July 4, 2015
Solved

Feature Request: Mutual Recursion

  • July 4, 2015
  • 2 replies
  • 5652 views

Several classes of problem (eg, context-free grammar interpreters) are easily thought about and implemented by mutually recursive function calls,

For example, one of the Rosetta Code programming challenges is to implement the Hofstadter Female and Male Sequences (http://rosettacode.org/wiki/Mutual_recursion#PureBasic).  As far as I'm aware, this isn't possible in Mathcad, but appears to be in a whole host of other languages including Matlab and Mathematica (two of Mathcad's major competitors).   As the ultimate humilation, I wrote my first program in LibreOffice Basic to show that even a word processor can do mutual recursion whereas a mathematical application can't.  Indeed, it seems as if even a pocket calculator can do it (see Ti-89 entry in the Rosetta listing).

Stuart

Rosetta Code Hofstadter Female and Male Sequence Challenge


Two functions are said to be mutually recursive if the first calls the second, and in turn the second calls the first.


Write two mutually recursive functions that compute members of the Hofstadter Female and Male sequences defined as:


F(0) = 1 ; M(0)=0

F(n) = n - M(F(n-1)), n > 0

M(n) = n - F(M(n-1)), n > 0

 

n    = 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20

F(n) = 1 1 2 2 3 3 4 5 5 6  6  7  8  8  9  9 10 11 11 12 13

M(n) = 0 0 1 2 2 3 4 4 5 6  6  7  7  8  9  9 10 11 11 12 12


LibreOffice Basic Function Definitions:

Function F(n as long) as long

    If n = 0 Then

        F =  1

    ElseIf n > 0 Then

        F = n - M(F(n - 1))

    EndIf

End Function

Function M(n)

    If n = 0 Then

        M = 0

    ElseIf n > 0 Then

        M = n - F(M(n - 1))

    EndIf

End Function

Best answer by RichardJ

If there's a way of "tricking" Mathcad into being able to do this, I can't figure it out. It just fundamentally breaks Mathcad's top left to bottom right paradigm.

As for the "feature request" aspect of your post, I think the best we can hope for is that 20 years from now we can complain that is still hasn't been implemented. Like MDAs, etc etc etc.

2 replies

RichardJ19-TanzaniteAnswer
19-Tanzanite
July 4, 2015

If there's a way of "tricking" Mathcad into being able to do this, I can't figure it out. It just fundamentally breaks Mathcad's top left to bottom right paradigm.

As for the "feature request" aspect of your post, I think the best we can hope for is that 20 years from now we can complain that is still hasn't been implemented. Like MDAs, etc etc etc.

23-Emerald V
July 5, 2015

Richard Jackson wrote:

If there's a way of "tricking" Mathcad into being able to do this, I can't figure it out. It just fundamentally breaks Mathcad's top left to bottom right paradigm.

I was hoping that there'd be some way of playing around with the symbolic processor, but I haven't found a way either.    I've tried code fragments and even defining F via a global definition and M as normal definition.  Helpfully, the latter raised an error that said "recursive definition"; that's just plain cruel and I think I ought to be instructing my lawyers.  If you can't do, sue!

I did think about mutual recursion breaking the normal evaluation, but we already have a mechanism that subverts it  - the above-mentioned global definition, so that might be one means by which Mathcad could 'legally' implement double mutual recursion.  Another way might be to introduce a keyword (eg, "forward" a la Pascal) that would flag up mutual recursion during the first pass.  Following the principle of maximum laziness, however, I'd rather see a mechanism that doesn't require additional thought upon my part.  I'll have to have a think about how it might break normal order otherwise and to what degree that would be a problem, or a benefit.

It would be nice to find a means by which we could legimately have closures, deferred evaluation and memoization (rather than the special case closure mechanism I found for creating functions with (vector) memory and that is almost certainly a bug an unintended feature).

As for the "feature request" aspect of your post, I think the best we can hope for is that 20 years from now we can complain that is still hasn't been implemented. Like MDAs, etc etc etc.

I guess I'm going to have to mark your answer correct ...  not sure whether that requires a emoticon, just out of plain snarkiness, or a because you're right.

Stuart

23-Emerald V
July 5, 2015

StuartBruff wrote:

Richard Jackson wrote:

If there's a way of "tricking" Mathcad into being able to do this, I can't figure it out. It just fundamentally breaks Mathcad's top left to bottom right paradigm.

I'll have to have a think ...

I shall have to give up this thinking lark.  No sooner had I put the keyboard down on you, than I wondered if I'd missed a trick in my previous attempt to use local definitions.  If one is willing to live with the burden of defining one function twice (ie, locally and at worksheet level), then it might be possible to trick Mathcad into allowing mutual recursion.

Stuart

15-Moonstone
July 7, 2015

Nice little challenge.  F(0) through F(n-1) have to know to calculate F(n), same with M(n).  M(n) can be calculated before F(n), provided F(0) through F(n-1) are known.  See attached code and check my logic.

HofstadterChallenge.jpg

Cheers

23-Emerald V
July 8, 2015

David Tietje wrote:

Nice little challenge.  F(0) through F(n-1) have to know to calculate F(n), same with M(n).  M(n) can be calculated before F(n), provided F(0) through F(n-1) are known. 

HofstadterChallenge.jpg

Cheers

It seems to work ... see attached worksheet.

See attached code and check my logic.

I tried to but now

Stuart