# Background

It can be shown that for any integer k >= 0, f(k) = tan(atan(0) + atan(1) + atan(2) + ... + atan(k)) is a rational number.

# Goal

Write a complete program or function which when given k >= 0, outputs f(k) as a single reduced fraction (the numerator and denominator are coprime).

# Test cases

The first few values are

f(0) = (0,1)
f(1) = (1,1)
f(2) = (-3,1)
f(3) = (0,1)
f(4) = (4,1)
f(5) = (-9,19)
f(6) = (105,73)


# Rules

• Standard loopholes are forbidden.
• Input and output may be in any convenient format. You may output f(k) as a string numerator/denominator, as a tuple of two integers, a fraction or rational object, etc. If you output a string, give two integers only, that is, output 3/2 instead of 1 1/2.
• This is code-golf, the shortest answer (in bytes) wins.
• Can you further specify in your test cases what the input/output values are? Aug 8 '17 at 6:22
• Are the integers in the range in degrees or radians? Aug 8 '17 at 6:59
• OEIS: A180657 Aug 8 '17 at 7:00
• The atan(0) term is unnecessary.
Aug 8 '17 at 7:08
• @pizzapants184 f(0) = tan∑∅ = tan 0 = 0
Aug 8 '17 at 7:14

# Mathematica, 28 bytes

Fold[+##/(1-##)&,0,Range@#]&


Try it online!

A longer, but more interesting approach (32 bytes):

Im@#/Re@#&@Product[1+n I,{n,#}]&


Try it online!

• +1 o'_'o Mathematica and its built-ins o'_'o Aug 8 '17 at 7:37
• @Mr.Xcoder Not really in this case. OP is using series summation cleverly (if I read the code right).
Aug 8 '17 at 7:38

# Python 2, 76 72 bytes

from fractions import*
f=lambda k:Fraction(k and(k+f(k-1))/(1-k*f(k-1)))


Use the identity:

tan(A + B) = (tan(A) + tan(B)) / (1 - tan(A) * tan(B))


We have:

f(k) = 0                                    if k = 0
= (k + f(k - 1)) / (1 - k * f(k - 1))  if k > 0


Try it online!

Thanks to Luis Mendo, save 4 bytes.

• Hope you do not mind: I added a TiO link. Aug 8 '17 at 7:05
• @LuisMendo LGTM, Edited.
– tsh
Aug 8 '17 at 10:08

# M, 11 bytes

×C÷@+
R0;ç/


Try it online!

Uses the OEIS formula x(n) = (x(n-1)+n)/(1-n*x(n-1)) with x(0) = 0.

# APL (Dyalog), 14 bytes

Requires ⎕FR←1287 (128 bit Floating-point Representation) for small input. Takes k as right argument.

1(∧÷,)3○¯3+.○⍳


Try it online!

⍳ integers one through k (zero is not needed as 0 = arctan 0)

¯3+.○ sum of arcus tangents

3○ tangent

1() apply the following tacit function with 1 as left argument and the above as right argument:

∧ the lowest common multiple (of 1 and the right argument); gives the numerator

÷ divided by

, the concatenation (of 1 and the right argument); gives the numerator and the denominator

This uses the OEIS series expansion:

import Data.Ratio
f 0=0%1
f n|p<-f\$n-1=(p+n)/(1-n*p)


Try it online!

Or a pointfree version:

(scanl1(\f n->(f+n)/(1-n*f))[0%1..]!!)


## JavaScript (ES6), 80 bytes

f=n=>n?([a,b]=f(n-1),g=(a,b)=>a?g(b%a,a):b,c=g(d=b*n+a,e=b-n*a),[d/c,e/c]):[0,1]


Returns a [numerator, denominator] pair. Explanation: Let f(n-1) = a/b then f(n) = atan(tan(n)+tan(a/b)) = (n+a/b)/(1-n*a/b) = (b*n+a)/(b-n*a). It then remains to reduce the fraction to its lowest terms.

Online ES6 Environment

# Pari/GP, 36 bytes

n->imag(x=prod(i=0,n,1+i*I))/real(x)


Try it online!

Or the same length:

n->fold((x,y)->(x+y)/(1-x*y),[0..n])


Try it online!

# 05AB1E, 33 26 bytes

0X)Iƒ©N*+®sN*-‚D¿D_i\¤}/


Try it online!

Explanation

0X)                          # initialize stack with [0,1]
Iƒ                        # for N in range [0 ... input] do:
©                       # store a copy of the current pair in the register
                      # push the pair separately to the stack
N*                    # multiply the denominator with N
®s                # push the denominator then the numerator to the stack
N*              # multiply the numerator by N
-             # subtract it from the denominator
D¿D          # get 2 copies of the greatest common divisor
0Qi  }    # if the gcd equals 0
\¤     # replace it with the denominator
/   # divide the pair with this number


# Octave, 30 bytes

format rat
tan(sum(atan(0:k)))


Try it online!

# Casio-Basic, 35 bytes

tExpand(tan(sum(seq(tan⁻¹(n),n,0,k


tan-1 should be entered as the one on the Trig keyboard; or the -1 can be entered separately from the abc>Math keyboard. According to the fx-CP400's manual, it's a single two-byte character (764).

Function, 34 bytes for the code, +1 byte to add k as an argument.

Explanation

seq(tan-1(n),n,0,k) generates all the values for tan-1(n) from 0 to k.

sum adds them all together, then tan does the tangent function on them.

tExpand will then turn them into a single fraction.

• @Adám This is Casio, not TI, so it's not done the same way. Aug 8 '17 at 7:55
• According to Wikipedia, ⁻ and ¹ are two bytes each; E5CC and E5C1.
Aug 8 '17 at 8:05
• @Adám oh nice, I didn't realise that article existed! However, this is an fx-CP400, not the 9860G; I just checked the manual, and the superscript -1 is actually a single character, code 764; so it's a single two byte character. Aug 8 '17 at 8:14

# Forth (gforth), 130 bytes

: g dup if tuck mod recurse then ;
: f 0 1 rot for 2dup i * + -rot swap i * - next
2dup g + abs over 0< 2* 1+ * >r i / swap r> / ;


Try it online!

Uses my own implementation of gcd, and the OEIS formula. Takes k from the stack and returns two integers denom num on the stack. It took a lot of effort (and bytes) to normalize the fraction.

: g ( x y -- gcd 0 )
dup if tuck mod recurse then
;

: f ( k -- denom num )
0 1               \ push initial fraction with num=0, denom=1
rot for           \ ( num denom ) loop from k to 0 inclusive
2dup i * + -rot \ ( denom*k+num num denom )
swap i * -      \ ( denom*k+num denom-num*k )
next
2dup g + abs      \ ( num denom gcd ) evaluate positive gcd and remove 0
over 0< 2* 1+ *   \ ( num denom gcd' ) negate gcd if denom < 0
>r i / swap r> /  \ ( denom/gcd' num/gcd' )
;


## Julia 0.6.0 40 bytes

k->rationalize(tan(sum(x->atan(x),1:k)))

It's a straightforward implementation of the question. The precision of rationalize can sometimes be weird but works fine 99% of the time.