> # Excerpts from a MUG posting > # > # Simplifications for sin(x), cos(x), tan(x), csc(x), sec(x), cot(x) > # See also arctrig, trigh, arctrigh for other trigonometric functions > # > # M. B. Monagan Oct 1985. > # G. H. Gonnet (added inverse simpl) 11/87 > # MBM Feb/89 (sign and Pi removed from sums) > # Updated MBM Mar/89 to compute f(x*Pi) accurately > # DEGH (Jun 91 - complex float case) > # MBM Oct/93 - trig(n*Pi) but not trig(x+n*Pi) > # > > unprotect('sin'): > sin := proc(x) > local n,t; > option > `Copyright (c) 1992 by the University of Waterloo. All rights reserved.`; > > if nargs <> 1 then ERROR(`expecting 1 argument, got `.nargs); > elif type(x,'complex(float)') then evalf('sin'(x)); > elif type(x,`*`) and member(I,{op(x)}) then sinh(x/I)*I > elif type(x,'complex(numeric)') then > if csgn(x) < 0 then -sin(-x) else 'sin'(x) fi > elif type(x,`*`) and type(op(1,x),'complex(numeric)') and > csgn(op(1,x)) < 0 then -sin(-x) > elif type(x,`*`) and type(x,'rational &* identical(Pi)') then > t := op(1,x); > if t < 1/2 then 'sin'(x) > elif t < 1 then sin((1-t)*Pi) > elif t < 2 then -sin((2-t)*Pi) > else sin( (t-2*iquo(trunc(t),2))*Pi ) > fi > elif type(x,`+`) and traperror(sign(x)) = -1 then -sin(-x) > elif type(x,`+`) and has(x,Pi) then > t := map(proc(x) if type(x/Pi,'rational') then x/Pi fi end, > {op(x)}); > if nops(t) = 1 then > t := op(t); > if t < 0 then sin(x-2*Pi*trunc(t/2)+2*Pi) > elif t < 1/2 then sin(x) := 'sin'(x) > elif t < 1 then cos(x-Pi/2) > elif t < 2 then -sin(x-Pi) > else sin(x-2*Pi*trunc(t/2)) > fi > else sin(x) := 'sin'(x) > fi > elif type(x,`*`) and member(Pi,[op(x)],'n') and Im(x)=0 then > # Does not handle sin(x+n*Pi) > t := subsop(n=1,x); > if frac(t)=0 then 0 > elif frac((t-1/2)/2)=0 then 1 > elif frac((t+1/2)/2)=0 then -1 > elif frac((t-1/2))=0 then (-1)^(t-1/2) > else sin(x) := 'sin'(x); > fi; > elif type(x,'function') and nops(x) = 1 then > n := op(0,x); t := op(1,x); > # function inverses and sin in terms of other inverses > if n = 'arcsin' then t > elif n = 'arccos' then sqrt(1-t^2) > elif n = 'arctan' then t/sqrt(1+t^2) > elif n = 'arccsc' then 1/t > elif n = 'arcsec' then sqrt(1-1/t^2) > elif n = 'arccot' then 1/sqrt(1+t^2) > else sin(x) := 'sin'(x) > fi > elif type(x,'arctan(algebraic,algebraic)') then > op(1,x)/sqrt(op(1,x)^2+op(2,x)^2); > else sin(x) := 'sin'(x) > fi > end: > protect(sin): > > sin(0) := 0: > sin(Pi) := 0: > sin(Pi/2) := 1: > sin(Pi/3) := 1/2*3^(1/2): > sin(Pi/4) := 1/2*2^(1/2): > sin(Pi/5) := 1/4*2^(1/2)*(5-5^(1/2))^(1/2): > sin(2*Pi/5) := 1/4*2^(1/2)*(5+5^(1/2))^(1/2): > sin(Pi/6) := 1/2: > sin(Pi/8) := 1/2*(2-2^(1/2))^(1/2): > sin(3*Pi/8) := 1/2*(2+2^(1/2))^(1/2): > sin(Pi/10) := (5^(1/2) - 1)/4: > sin(3*Pi/10) := (5^(1/2) + 1)/4: > sin(Pi/12) := 1/4*6^(1/2)*(1-1/3*3^(1/2)): > sin(5*Pi/12) := 1/4*6^(1/2)*(1+1/3*3^(1/2)): > sin(I) := 'sinh(1)*I': > > #savelib('sin','`sin.m`'): > > unprotect('cos'): > cos := proc(x) > local n,t; > option > `Copyright (c) 1992 by the University of Waterloo. All rights reserved.`; > > if nargs <> 1 then ERROR(`expecting 1 argument, got `.nargs); > elif type(x,'complex(float)') then evalf('cos'(x)) > elif type(x,`*`) and member(I,{op(x)}) then cosh(x/I) > elif type(x,'complex(numeric)') then > if csgn(x) < 0 then cos(-x) else 'cos'(x) fi > elif type(x,`*`) and type(op(1,x),'complex(numeric)') and > csgn(op(1,x)) < 0 then cos(-x) > elif type(x,`*`) and type(x,'rational &* identical(Pi)') then > t := op(1,x); > if t < 1/2 then 'cos'(x) > elif t < 1 then -cos((1-t)*Pi) > elif t < 2 then cos((2-t)*Pi) > else cos( (t-2*iquo(trunc(t),2))*Pi ) > fi > elif type(x,`+`) and traperror(sign(x)) = -1 then cos(-x) > elif type(x,`+`) and has(x,Pi) then > t := map(proc(x) if type(x/Pi,'rational') then x/Pi fi end, > {op(x)}); > if nops(t) = 1 then > t := op(t); > if t < 0 then cos(x-2*Pi*trunc(t/2)+2*Pi) > elif t < 1/2 then cos(x) := 'cos'(x) > elif t < 1 then -sin(x-Pi/2) > elif t < 2 then -cos(x-Pi) > else cos(x-2*Pi*trunc(t/2)) > fi > else cos(x) := 'cos'(x) > fi > elif type(x,`*`) and member(Pi,[op(x)],'n') and Im(x)=0 then > # Does not handle cos(x+n*Pi) > t := subsop(n=1,x); > if frac(t/2)=0 then 1 # t is even > elif frac((t-1)/2)=0 then -1 # t is odd > elif frac(t)=0 then (-1)^t # t is an integer > elif frac(t-1/2)=0 then 0 > else cos(x) := 'cos'(x); > fi; > elif type(x,'function') and nops(x) = 1 then > n := op(0,x); t := op(1,x); > # function inverses and cos in terms of other inverses > if n = 'arcsin' then sqrt(1-t^2) > elif n = 'arccos' then t > elif n = 'arctan' then 1/sqrt(1+t^2) > elif n = 'arccsc' then sqrt(1-1/t^2) > elif n = 'arcsec' then 1/t > elif n = 'arccot' then t/sqrt(1+t^2) > else cos(x) := 'cos'(x) > fi > elif type(x,'arctan(algebraic,algebraic)') then > op(2,x)/sqrt(op(1,x)^2+op(2,x)^2); > else cos(x) := 'cos'(x) > fi > end: > protect(cos): > > cos(0) := 1: > cos(Pi) := -1: > cos(Pi/2) := 0: > cos(Pi/3) := 1/2: > cos(Pi/4) := 1/2*2^(1/2): > cos(Pi/5) := (5^(1/2)+1)/4: > cos(2*Pi/5) := (5^(1/2) - 1)/4: > cos(Pi/6) := 1/2*3^(1/2): > cos(Pi/8) := 1/2*(2+2^(1/2))^(1/2): > cos(3*Pi/8) := 1/2*(2-2^(1/2))^(1/2): > cos(Pi/10) := 1/4*2^(1/2)*(5+5^(1/2))^(1/2): > cos(3*Pi/10) := 1/4*2^(1/2)*(5-5^(1/2))^(1/2): > cos(Pi/12) := 1/4*6^(1/2)*(1+1/3*3^(1/2)): > cos(5*Pi/12) := 1/4*6^(1/2)*(1-1/3*3^(1/2)): > cos(I) := 'cosh(1)': > > #savelib('cos','`cos.m`'): > > > unprotect('tan'): > tan := proc(x) > local n,t; > option > `Copyright (c) 1992 by the University of Waterloo. All rights reserved.`; > > if nargs <> 1 then ERROR(`expecting 1 argument, got `.nargs); > elif type(x,'complex(float)') then evalf('tan'(x)) > elif type(x,`*`) and member(I,{op(x)}) then tanh(x/I)*I > elif type(x,'complex(numeric)') then > if csgn(x) < 0 then -tan(-x) else 'tan'(x) fi > elif type(x,`*`) and type(op(1,x),'complex(numeric)') and > csgn(op(1,x)) < 0 then -tan(-x) > elif type(x,`*`) and type(x,'rational &* identical(Pi)') then > t := op(1,x); > if t < 1/2 then 'tan'(x) > elif t = 1/2 then ERROR(`singularity encountered`) > elif t < 1 then -tan((1-t)*Pi) > elif t < 2 then tan((t-1)*Pi) > else tan( (t-2*iquo(trunc(t),2))*Pi ) > fi > elif type(x,`+`) and traperror(sign(x)) = -1 then -tan(-x) > elif type(x,`+`) and has(x,Pi) then > t := map(proc(x) if type(x/Pi,'rational') then x/Pi fi end, > {op(x)}); > if nops(t) = 1 then > t := op(t); > if t < 0 then tan(x-Pi*trunc(t)+Pi) > elif t < 1/2 then tan(x) := 'tan'(x) > elif t < 1 then -cot(x-Pi/2) > else tan(x-Pi*trunc(t)) > fi > else tan(x) := 'tan'(x) > fi > elif type(x,`*`) and member(Pi,[op(x)],'n') and Im(x)=0 then > # Does not handle tan(x+n*Pi) > t := subsop(n=1,x); > if frac(t)=0 then 0 > elif frac(t-1/2)=0 then ERROR(`singularity encountered`) > else tan(x) := 'tan'(x); > fi > elif type(x,'function') and nops(x) = 1 then > n := op(0,x); t := op(1,x); > # function inverses and tan in terms of other inverses > if n = 'arcsin' then t/sqrt(1-t^2) > elif n = 'arccos' then sqrt(1-t^2)/t > elif n = 'arctan' then t > elif n = 'arccot' then 1/t > elif n = 'arcsec' then t*sqrt(1-1/t^2) > elif n = 'arccsc' then 1/t/sqrt(1-1/t^2) > else tan(x) := 'tan'(x) > fi > elif type(x,'arctan(algebraic,algebraic)') then > op(1,x)/op(2,x); > else tan(x) := 'tan'(x) > fi > end: > protect(tan): > > tan(0) := 0: > tan(Pi) := 0: > tan(Pi/3) := 3^(1/2): > tan(Pi/4) := 1: > tan(Pi/5) := (5-2*5^(1/2))^(1/2): > tan(2*Pi/5) := (5+2*5^(1/2))^(1/2): > tan(Pi/6) := 1/3*3^(1/2): > tan(Pi/8) := 2^(1/2)-1: > tan(3*Pi/8) := 2^(1/2)+1: > tan(Pi/10) := 1/5*5^(1/2)*(5-2*5^(1/2))^(1/2): > tan(3*Pi/10) := 1/5*5^(1/2)*(5+2*5^(1/2))^(1/2): > tan(Pi/12) := 2 - 3^(1/2): > tan(5*Pi/12) := 2 + 3^(1/2): > tan(I) := 'tanh(1)*I': > > #savelib('tan','`tan.m`'): > > > unprotect('csc'): > csc := proc(x) > local n,t; > option > `Copyright (c) 1992 by the University of Waterloo. All rights reserved.`; > > if nargs <> 1 then ERROR(`expecting 1 argument, got `.nargs); > elif type(x,'complex(float)') then evalf('csc'(x)); > elif x = 0 or x = Pi then ERROR(`singularity encountered`) > elif type(x,`*`) and member(I,{op(x)}) then -csch(x/I)*I > elif type(x,'complex(numeric)') then > if csgn(x) < 0 then -csc(-x) else 'csc'(x) fi > elif type(x,`*`) and type(op(1,x),'complex(numeric)') and > csgn(op(1,x)) < 0 then -csc(-x) > elif type(x,`*`) and type(x,'rational &* identical(Pi)') then > t := op(1,x); > if t = 0 then ERROR(`singularity encountered`) > elif t < 1/2 then 'csc'(x) > elif t < 1 then csc((1-t)*Pi) > elif t = 1 then ERROR(`singularity encountered`) > elif t < 2 then -csc((2-t)*Pi) > else csc( (t-2*iquo(trunc(t),2))*Pi ) > fi > elif type(x,`+`) and traperror(sign(x)) = -1 then -csc(-x) > elif type(x,`+`) and has(x,Pi) then > t := map(proc(x) if type(x/Pi,'rational') then x/Pi fi end, > {op(x)}); > if nops(t) = 1 then > t := op(t); > if t < 0 then csc(x-2*Pi*trunc(t/2)+2*Pi) > elif t < 1/2 then csc(x) := 'csc'(x) > elif t < 1 then sec(x-Pi/2) > elif t < 2 then -csc(x-Pi) > else csc(x-2*Pi*trunc(t/2)) > fi > else csc(x) := 'csc'(x) > fi > elif type(x,`*`) and member(Pi,[op(x)],'n') and Im(x)=0 then > # Does not handle csc(x+n*Pi) > t := subsop(n=1,x); > if frac(t)=0 then ERROR(`singularity encountered`) > elif frac((t-1/2)/2)=0 then 1 > elif frac((t+1/2)/2)=0 then -1 > elif frac((t-1/2))=0 then (-1)^(t-1/2) > else csc(x) := 'csc'(x); > fi > elif type(x,'function') and nops(x) = 1 then > n := op(0,x); t := op(1,x); > # function inverses and csc in terms of other inverses > if n = 'arcsin' then 1/t > elif n = 'arccos' then 1/sqrt(1-t^2) > elif n = 'arctan' then sqrt(1+t^2)/t > elif n = 'arccot' then sqrt(1+t^2) > elif n = 'arcsec' then 1/sqrt(1-1/t^2) > elif n = 'arccsc' then t > else csc(x) := 'csc'(x) > fi > elif type(x,'arctan(algebraic,algebraic)') then > sqrt(op(1,x)^2+op(2,x)^2)/op(1,x); > else csc(x) := 'csc'(x) > fi > end: > protect(csc): > > csc(Pi/2) := 1: > csc(Pi/3) := 2/3*3^(1/2): > csc(Pi/4) := 2^(1/2): > csc(Pi/5) := 1/5*5^(1/2)*2^(1/2)*(5+5^(1/2))^(1/2): > csc(2*Pi/5) := 1/5*2^(1/2)*5^(1/2)*(5-5^(1/2))^(1/2): > csc(Pi/6) := 2: > csc(Pi/8) := 2^(1/2)*(2+2^(1/2))^(1/2): > csc(3*Pi/8) := 2^(1/2)*(2-2^(1/2))^(1/2): > csc(Pi/10) := 5^(1/2)+1: > csc(3*Pi/10) := 5^(1/2)-1: > csc(Pi/12) := 6^(1/2)*(1+1/3*3^(1/2)): > csc(5*Pi/12) := 6^(1/2)*(1-1/3*3^(1/2)): > csc(I) := '-csch(1)*I': > > #savelib('csc','`csc.m`'): > > > unprotect('sec'): > sec := proc(x) > local n,t; > option > `Copyright (c) 1992 by the University of Waterloo. All rights reserved.`; > > if nargs <> 1 then ERROR(`expecting 1 argument, got `.nargs); > elif type(x,'complex(float)') then evalf('sec'(x)) > elif type(x,`*`) and member(I,{op(x)}) then sech(x/I) > elif type(x,'complex(numeric)') then > if csgn(x) < 0 then sec(-x) else 'sec'(x) fi > elif type(x,`*`) and type(op(1,x),'complex(numeric)') and > csgn(op(1,x)) < 0 then sec(-x) > elif type(x,`*`) and type(x,'rational &* identical(Pi)') then > t := op(1,x); > if t < 1/2 then 'sec'(x) > elif t = 1/2 then ERROR(`singularity encountered`) > elif t < 1 then -sec((1-t)*Pi) > elif t < 2 then sec((2-t)*Pi) > else sec( (t-2*iquo(trunc(t),2))*Pi ) > fi > elif type(x,`+`) and traperror(sign(x)) = -1 then sec(-x) > elif type(x,`+`) and has(x,Pi) then > t := map(proc(x) if type(x/Pi,'rational') then x/Pi fi end, > {op(x)}); > if nops(t) = 1 then > t := op(t); > if t < 0 then sec(x-2*Pi*trunc(t/2)+2*Pi) > elif t < 1/2 then sec(x) := 'sec'(x) > elif t < 1 then -csc(x-Pi/2) > elif t < 2 then -sec(x-Pi) > else sec(x-2*Pi*trunc(t/2)) > fi > else sec(x) := 'sec'(x) > fi > elif type(x,`*`) and member(Pi,[op(x)],'n') and Im(x)=0 then > # Does not handle sec(x+n*Pi) > t := subsop(n=1,x); > if frac(t/2)=0 then 1 # t even > elif frac((t-1)/2)=0 then -1 # t odd > elif frac(t)=0 then (-1)^t # t an integer > elif frac((t-1/2))=0 then ERROR(`singularity encountered`) > else sec(x) := 'sec'(x); > fi > elif type(x,'function') and nops(x) = 1 then > n := op(0,x); t := op(1,x); > # function inverses and sec in terms of other inverses > if n = 'arcsin' then 1/sqrt(1-t^2) > elif n = 'arccos' then 1/t > elif n = 'arctan' then sqrt(1+t^2) > elif n = 'arccot' then sqrt(1+t^2)/t > elif n = 'arcsec' then t > elif n = 'arccsc' then 1/sqrt(1-1/t^2) > else sec(x) := 'sec'(x) > fi > elif type(x,'arctan(algebraic,algebraic)') then > sqrt(op(1,x)^2+op(2,x)^2)/op(2,x); > else sec(x) := 'sec'(x) > fi > end: > protect(sec): > > sec(0) := 1: > sec(Pi) := -1: > sec(Pi/3) := 2: > sec(Pi/4) := 2^(1/2): > sec(Pi/5) := 5^(1/2)-1: > sec(2*Pi/5) := 5^(1/2)+1: > sec(Pi/6) := 2/3*3^(1/2): > sec(Pi/8) := 2^(1/2)*(2-2^(1/2))^(1/2): > sec(3*Pi/8) := 2^(1/2)*(2+2^(1/2))^(1/2): > sec(Pi/10) := 1/5*5^(1/2)*2^(1/2)*(5-5^(1/2))^(1/2): > sec(3*Pi/10) := 1/5*5^(1/2)*2^(1/2)*(5+5^(1/2))^(1/2): > sec(Pi/12) := 6^(1/2)*(1-1/3*3^(1/2)): > sec(5*Pi/12) := 6^(1/2)*(1+1/3*3^(1/2)): > sec(I) := 'sech(1)': > > #savelib('sec','`sec.m`'): > > > unprotect('cot'): > cot := proc(x) > local n,t; > option > `Copyright (c) 1992 by the University of Waterloo. All rights reserved.`; > > if nargs <> 1 then ERROR(`expecting 1 argument, got `.nargs); > elif type(x,'complex(float)') then evalf('cot'(x)) > elif x = 0 or x = Pi then ERROR(`singularity encountered`) > elif type(x,`*`) and member(I,{op(x)}) then -coth(x/I)*I > elif type(x,'complex(numeric)') then > if csgn(x) < 0 then -cot(-x) else 'cot'(x) fi > elif type(x,`*`) and type(op(1,x),'complex(numeric)') and > csgn(op(1,x)) < 0 then -cot(-x) > elif type(x,`*`) and type(x,'rational &* identical(Pi)') then > t := op(1,x); > if t = 0 then ERROR(`singularity encountered`) > elif t < 1/2 then 'cot'(x) > elif t < 1 then -cot((1-t)*Pi) > elif t = 1 then ERROR(`singularity encountered`) > elif t < 2 then cot((t-1)*Pi) > else cot( (t-2*iquo(trunc(t),2))*Pi ) > fi > elif type(x,`+`) and traperror(sign(x)) = -1 then -cot(-x) > elif type(x,`+`) and has(x,Pi) then > t := map(proc(x) if type(x/Pi,'rational') then x/Pi fi end, > {op(x)}); > if nops(t) = 1 then > t := op(t); > if t < 0 then cot(x-Pi*trunc(t)+Pi) > elif t < 1/2 then cot(x) := 'cot'(x) > elif t < 1 then -tan(x-Pi/2) > else cot(x-Pi*trunc(t)) > fi > else cot(x) := 'cot'(x) > fi > elif type(x,`*`) and member(Pi,[op(x)],'n') and Im(x)=0 then > # Does not handle cot(x+n*Pi) > t := subsop(n=1,x); > if frac(t)=0 then ERROR(`singularity encountered`) > elif frac(t-1/2)=0 then 0 > else cot(x) := 'cot'(x); > fi > elif type(x,'function') and nops(x) = 1 then > n := op(0,x); t := op(1,x); > # function inverses and cot in terms of other inverses > if n = 'arcsin' then sqrt(1-t^2)/t > elif n = 'arccos' then t/sqrt(1-t^2) > elif n = 'arctan' then 1/t > elif n = 'arccot' then t > elif n = 'arcsec' then 1/t/sqrt(1-1/t^2) > elif n = 'arccsc' then t*sqrt(1-1/t^2) > else cot(x) := 'cot'(x) > fi > elif type(x,'arctan(algebraic,algebraic)') then > op(2,x)/op(1,x); > else cot(x) := 'cot'(x) > fi > end: > protect(cot): > > cot(Pi/2) := 0: > cot(Pi/3) := 1/3*3^(1/2): > cot(Pi/4) := 1: > cot(Pi/5) := 1/5*5^(1/2)*(5+2*5^(1/2))^(1/2): > cot(Pi/6) := 3^(1/2): > cot(2*Pi/5) := 1/5*5^(1/2)*(5-2*5^(1/2))^(1/2): > cot(Pi/8) := 2^(1/2)+1: > cot(3*Pi/8) := 2^(1/2)-1: > cot(Pi/10) := (5+2*5^(1/2))^(1/2): > cot(3*Pi/10) := (5-2*5^(1/2))^(1/2): > cot(Pi/12) := 2 + 3^(1/2): > cot(5*Pi/12) := 2 - 3^(1/2): > cot(I) := -'coth(1)'*I: > > #savelib('cot','`cot.m`'): >