Catalan numbers appear in several areas of mathematics. For example, the nth Catalan number is the number of planar binary trees with n nodes, and is the number of ways of cutting up a polygon with n+2 sides into triangles by drawing non-intersecting diagonals.
Catalan numbers 0-8 are: 1 1 2 5 14 42 132 429 1430
The question we will look at here is how to calculate the nth Catalan number, for n taking values of 5, 10, 1000, 10000 and up.
In [ ]:
    
n=: 5
    
In [ ]:
    
(!2*n) % (!n) * (!n+1)
    
In [ ]:
    
(n ! 2*n) % n+1
    
In [ ]:
    
(n ! +: n) % >: n
    
In [ ]:
    
n=: i.8
    
In [ ]:
    
(n ! +: n) % >: n
    
In [ ]:
    
cat1=: (! +:) % >:
    
In [ ]:
    
cat1 i.8
    
In [ ]:
    
n=: i.8
    
In [ ]:
    
n ,. cat1 n
    
In [ ]:
    
(,. cat1) i.8
    
In [ ]:
    
cat1 100
    
In [ ]:
    
cat1 x: 100
    
In [ ]:
    
cat2=: cat1 @ x:
    
In [ ]:
    
cat2 100
    
In [ ]:
    
(,. cat2) 100+i.10
    
In [ ]:
    
cat2 1000
    
In [ ]:
    
$":cat2 1000
    
In [ ]:
    
load 'general/misc/format'
    
In [ ]:
    
xfmt cat2 1000
    
Can cat2 be used to generate the 10,000th Catalan number?
Yes - with a fast PC and enough memory. On the authors PC, this calculation takes just under a second and results in a number with 6,015 digits. However, it is near the limit of what can be achieved using this simple formula. If you try this, you might find that your PC runs out of memory, and starts paging memory to hard disk. This slows the calculation down enormously, and should be avoided.
It turns out that you can calculate !n by calculating the exponents in !n of each prime up to n, and this leads to a more efficient technique for computing the Catalan numbers where n is very large.
The idea is that for each prime p up to n, you calculate a list, lp, of the prime powers of p up to n, and then the exponent of p in !n is given by:
  ```+/ <. n % lp```
To keep numbers small, We will illustrate this for the calculation of !100.
In [ ]:
    
<. 3 ^. 100
    
In [ ]:
    
3 ^ 1 2 3 4 5
    
In [ ]:
    
<. 7 ^. 100
    
In [ ]:
    
7 ^ 1 2 3
    
In [ ]:
    
+/ <. 100 % 3 ^ >: i. <. 3 ^. 100
    
In [ ]:
    
a=: !100x
    
In [ ]:
    
b=: 3^48x
    
In [ ]:
    
a -: b * a <.@% b
    
In [ ]:
    
b=: 3^49x
    
In [ ]:
    
a -: b * a <.@% b
    
In [ ]:
    
pexp=: [: +/ ] <.@% [ ^ >: @ i. @ (<.@^.)
    
In [ ]:
    
3 pexp 100
    
In [ ]:
    
7 pexp 100
    
In [ ]:
    
p: 7                 NB. 7th prime
    
In [ ]:
    
p: inverse 19        NB. which prime is 19?
    
In [ ]:
    
p: i. p: inverse 19  NB. primes 0-6 (=i.7)
    
In [ ]:
    
p: i. p: inverse 20  NB. primes 0-7 (=i.8)
    
In [ ]:
    
ple=: p: @ i. @ (p: inverse) @ >:
    
In [ ]:
    
ple 19
    
In [ ]:
    
n=: 100
    
In [ ]:
    
ple n
    
In [ ]:
    
(ple n) pexp"0 n
    
In [ ]:
    
cat3=: 3 : 0
p=. ple +: y
e1=. p pexp"0 +: y
e2=. p pexp"0 y
e3=. p pexp"0 >: y
*/ p ^ x: e1-e2+e3
)
    
In [ ]:
    
(cat2 1000) -: cat3 1000
    
cat3 can be used to calculate the 10,000th Catalan number.
You can try larger numbers, but be warned this may take a long time, or run out of memory. On the PC of the author, cat3 100,000 takes just under 1 second and returns a result with 60,199 digits.
The next section calculates cat3 10000.
In [ ]:
    
a=: cat3 10000
    
In [ ]:
    
$":a
    
In [ ]: