from math import pi,sin,sqrt; from functools import partial; #------------------------------------------------------------------------------# def fFormat(x): return ':{0:.3f}'.format(x); def output(tpl): (v,s)=tpl; if s=='': s+=''; print('y'+fFormat(v)+' # '+s,'\n'); # end def #------------------------------------------------------------------------------# def fSin(x): return sin(x); def fSqrt(x): # Pre: x>=0 return sqrt(x); def fCompoSinSqrt(x): # Pre: x>=0 return sin(sqrt(x)); # h(g(f(x))) ? def fCompo(x,f): return f(x); #------------------------------------------------------------------------------# def wSin(x): y=fSin(x); s=fFormat(y); return(y,s); def wSqrt(x): # Pre: x>=0 y=fSqrt(x); s=fFormat(y); return(y,s); def wComp_wSin_wSqrt(x): # Pre: x>=0 (y1,s1)=wSqrt(x); (y2,s2)=wSin(y1); return (y2,s2+s1); #------------------------------------------------------------------------------# def mBind(xs:tuple,wf)->tuple: assert isinstance(xs,tuple); (x,s1)=xs; (y,s2)=wf(x); return (y,s2+s1); def mUnit(x)->tuple: return (x,''); #------------------------------------------------------------------------------# def mLift(x,f): return mUnit(f(x)); def fSquare(x): return x*x; wSquare=partial(mLift, f=fSquare); #------------------------------------------------------------------------------# def dLift(f): def lift(x): v=f(x); s=fFormat(v); return (v,s); return lift; # end def @dLift def dSqrt(x): return sqrt(x); #------------------------------------------------------------------------------# #------------------------------------------------------------------------------# if __name__ == '__main__': print('\n# Beginning...'); #------------------------------------------------------------------------------# if False: x=pi/2; y=wSin(x); output(y); x=2; y=wSqrt(x); output(y); x=2; y=wComp_wSin_wSqrt(x); output(y); x=2; y=fCompo(fCompo(x,fSqrt),fSin); print(y); #------------------------------------------------------------------------------# x=2; y=mBind(mBind(mUnit(x),wSqrt),wSin); assert(str(y)=="(0.9877659459927356, ':0.988:1.414')"); y=mBind(mBind(mUnit(x),wSqrt),lambda z : (z*z,fFormat(z*z))); assert(str(y)=="(2.0000000000000004, ':2.000:1.414')"); y=mBind(mBind(mBind(mUnit(x),wSqrt),wSqrt),wSqrt); assert(str(y)=="(1.0905077326652577, ':1.091:1.189:1.414')"); #------------------------------------------------------------------------------# x=2; assert(mBind(mUnit(x),wSqrt)==wSqrt(x)); # Linksidentität ( x+0=x ) assert(mBind(mUnit(x),mUnit)==mUnit(x)); # Rechtsidentität ( 0+x=x ) y1=mBind(mBind(mUnit(x),wSqrt),wSin); y2=mBind(mUnit(x),lambda z : mBind(wSqrt(z),wSin)); assert(y1==y2); # Assoziativität ( (x+y)+z=x+(y+z)=x+y+z ) #------------------------------------------------------------------------------# x=2; y=wSquare(x); assert(str(y)=="(4, '')"); #------------------------------------------------------------------------------# x=2; y=mBind(mUnit(x),dSqrt); y=mBind(y,wSin); assert(str(y)=="(0.9877659459927356, ':0.988:1.414')"); #------------------------------------------------------------------------------# print('\n# Finished\n'); # end if main #------------------------------------------------------------------------------#