diff options
author | Karl Berry <karl@freefriends.org> | 2016-02-13 22:37:21 +0000 |
---|---|---|
committer | Karl Berry <karl@freefriends.org> | 2016-02-13 22:37:21 +0000 |
commit | 6aad496527f7643fd4ce0ec486e8204cab355281 (patch) | |
tree | fd76656717c7958282922af93a193ef6721e54fb /Master/texmf-dist/tex/generic/apnum | |
parent | 17a147917f94e99da6ae505ccb374b794db49117 (diff) |
apnum (13feb16)
git-svn-id: svn://tug.org/texlive/trunk@39710 c570f23f-e606-0410-a88d-b1316a301751
Diffstat (limited to 'Master/texmf-dist/tex/generic/apnum')
-rw-r--r-- | Master/texmf-dist/tex/generic/apnum/apnum.tex | 127 |
1 files changed, 73 insertions, 54 deletions
diff --git a/Master/texmf-dist/tex/generic/apnum/apnum.tex b/Master/texmf-dist/tex/generic/apnum/apnum.tex index e3a7bb53161..4c2e885904f 100644 --- a/Master/texmf-dist/tex/generic/apnum/apnum.tex +++ b/Master/texmf-dist/tex/generic/apnum/apnum.tex @@ -1,10 +1,10 @@ % Arbitrary precision numbers -%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -% 2014, 2015 Petr Olsak +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +% 2014, 2015, 2016 Petr Olsak % See the documentation apnum.pdf or apnum.d for more information -\def\apVERSION{1.5 <Jan 2016>} +\def\apVERSION{1.6 <Feb 2016>} \message{The Arbitrary Precision Numbers, \apVERSION} %%%%%%%%%%%% Internal registers, sec. 2.1 in apnum.pdf @@ -20,13 +20,15 @@ \newcount\apE \newcount\apTOT \apTOT=0 \newcount\apFRAC \apFRAC=20 +\newcount\apEX \apEX=10 \apnumZ=\catcode`\@ \catcode`\@=12 %%%%%%%%%%%% Evaluation of the expression, sec. 2.2 in apnum.pdf -\def\evaldef{\relax \apEVALa} -\def\apEVALa#1#2{\begingroup \apnumA=0 \apnumE=1 \apEVALb#2\limits \tmpb \apEND \let#1=\OUT} +\def\evaldef{\relax \apEVALa{\apEadd\OUT}} +\def\evalmdef{\relax \apEVALa{}} +\def\apEVALa#1#2#3{\begingroup \apnumA=0 \apnumE=1 \apEVALb#3\limits \tmpb \apEND #1\let#2=\OUT} \def\apEVALb{\def\tmpa{}\apEVALc} \def\apEVALc#1{% \ifx+#1\apEVALd \apEVALc \fi @@ -111,7 +113,7 @@ %%%%%%%%%%%% Preparation of the parameter, sec. 2.3 in apnum.pdf \def\apPPa#1#2{\expandafter\apPPb#2@#1} -\def\apPPb{\def\tmpc{}\apSIGN=1 \apE=0 \apXfalse \expandafter\expandafter\expandafter\apPPc} +\def\apPPb{\def\tmpc{}\apSIGN=1 \apE=0 \expandafter\expandafter\expandafter\apPPc} \def\apPPc#1{% \ifx+#1\apPPd \fi \ifx-#1\apSIGN=-\apSIGN \apPPd \fi @@ -119,8 +121,8 @@ \apPPg#1% } \def\apPPd#1\apPPg#2{\fi\expandafter\expandafter\expandafter\apPPc} -\def\apPPe#1\apPPg#2#3@{\fi\apXtrue - \begingroup#3% execution of the parameter in the group +\def\apPPe#1\apPPg#2#3@{\fi + \begingroup\apE=0 #3% execution of the parameter in the group \edef\tmpb{\apE=\the\apE\relax\noexpand\apPPf\OUT@}\expandafter\endgroup\tmpb } \def\apPPf#1{\ifx-#1\apSIGN=-\apSIGN \expandafter\apPPg\else\expandafter\apPPg\expandafter#1\fi} @@ -133,7 +135,7 @@ \expandafter\apPPi\tmpc } \def\apPPh#1\apPPi\tmpc{\fi\apPPg} -\def\apPPi{\ifapX \expandafter\apPPj \else \expandafter\apPPk \fi} +\def\apPPi{\ifnum\apE=0 \expandafter\apPPk \else \expandafter\apPPj \fi} \def\apPPj#1@#2{\def#2{#1}} \def\apPPk#1@#2{\ifx@#1@\apSIGN=0 \def#2{0}\else \apPPl#1E@#2\fi} \def\apPPl#1E#2@#3{% @@ -702,7 +704,7 @@ %%%%%%%%%%%% Function-like macros, sec. 2.10 in apnum.pdf \def\ABS#1{\relax % mandatory \relax for "function-like" macros - \evaldef\OUT{#1}% % evaluation of the input parameter + \evalmdef\OUT{#1}% % evaluation of the input parameter \ifnum\apSIGN<0 % if (input < 0) \apSIGN=1 % sign = 1 \apREMfirst\OUT % remove first "minus" from OUT @@ -710,33 +712,33 @@ } \def\SGN#1{\relax \evaldef\OUT{#1}\edef\OUT{\the\apSIGN}\apE=0 } \def\iDIV#1#2{\relax \apINIT % calculation in group - \evaldef\apAparam{#1}\apEadd\apAparam - \evaldef\apBparam{#2}\apEadd\apBparam % evaluation of the parameters + \evalmdef\apAparam{#1}\apEnum\apAparam + \evalmdef\apBparam{#2}\apEnum\apAparam % evaluation of the parameters \apTOT=0 \apFRAC=0 \apDIV\apAparam\apBparam % integer division \apEND % end of group } \def\iMOD#1#2{\relax \apINIT % calculation in group - \evaldef\apAparam{#1}\apEadd\apAparam - \evaldef\apBparam{#2}\apEadd\apBparam % evaluation of the parameters + \evalmdef\apAparam{#1}\apEnum\apAparam + \evalmdef\apBparam{#2}\apEnum\apBparam % evaluation of the parameters \apTOT=0 \apFRAC=0 \apDIV\apAparam\apBparam % integer division \let\OUT=\XOUT % remainder is the output \apEND % end of group } -\def\iFLOOR#1{\relax \evaldef\OUT{#1}\apEnum\OUT \apROUND\OUT0% +\def\iFLOOR#1{\relax \evalmdef\OUT{#1}\apEnum\OUT \apROUND\OUT0% \ifnum\apSIGN<0 \ifx\XOUT\empty \else \apPLUS\OUT{-1}\fi\fi \def\tmp{0}\ifx\tmp\OUT \apSIGN=0 \fi } \def\iFRAC#1{\relax - \evaldef\OUT{#1}\apEnum\OUT \apROUND\OUT0% % preparing the parameter - \ifx\XOUT\empty \def\OUT{0}\apSIGN=0 % empty fraction part means zero + \evalmdef\OUT{#1}\apEnum\OUT \apROUND\OUT0% % preparing the parameter + \ifx\XOUT\empty \def\OUT{0}\apSIGN=0 % empty fraction part means zero \else \ifnum\apSIGN<0 - \edef\XOUT{-.\XOUT}\apPLUS1\XOUT % OUT = 1 - .\XOUT - \else \edef\OUT{.\XOUT}\apSIGN=1 % else OUT = .\XOUT + \edef\XOUT{-.\XOUT}\apPLUS1\XOUT % OUT = 1 - .\XOUT + \else \edef\OUT{.\XOUT}\apSIGN=1 % else OUT = .\XOUT \fi \fi } \def\FAC#1{\relax \apINIT % "function-like" in the group, FAC = factorial - \evaldef\OUT{#1}\apEnum\OUT % preparing the parameter + \evalmdef\OUT{#1}\apEnum\OUT % preparing the parameter \localcounts \N;% % local \newcount \ifnum\apSIGN<0 \apERR{\string\FAC: argument {\OUT} cannot be negative}\apRETURN\fi \let\tmp=\OUT \apROUND\tmp0% % test, if parameter is integer @@ -748,8 +750,8 @@ \apEND % end of group } \def\BINOM#1#2{\relax \apINIT % BINOM = {#1 \choose #2} ... - \evaldef\apAparam{#1}\apEnum\apAparam - \evaldef\apBparam{#2}\apEnum\apBparam % preparation of the parameters + \evalmdef\apAparam{#1}\apEnum\apAparam + \evalmdef\apBparam{#2}\apEnum\apBparam % preparation of the parameters \localcounts \A \B \C ;% % local \newcounts \let\OUT=\apBparam \apROUND\OUT0% % test if B is integer \ifx\XOUT\empty\else\apERR{\string\BINOM: second arg. {\apBparam} must be integer}\apRETURN\fi @@ -775,7 +777,7 @@ \apEND } \def\SQRT#1{\relax \apINIT % OUT = SQRT(#1) ... - \evaldef\A{#1}% % parameter preparation + \evalmdef\A{#1}% % parameter preparation \localcounts \M \E ;% % local counters \E=\apE \apE=0 \ifnum\apSIGN=0 \apRETURN\fi % SQRT(0) = 0 (OUT is set to 0 by previous \evaldef) @@ -819,39 +821,53 @@ \edef\OUT{\expandafter\apNOPT\the\dimen0}% OUT = dimen0 } \def\EXP#1{\relax\apINIT % OUT = EXP(#1) ... - \evaldef\OUT{#1}\apEnum\OUT % OUT = #1 + \evalmdef\OUT{#1}\apEnum\OUT % OUT = #1 \localcounts \N \K ;% \ifnum\apSIGN=0 \def\OUT{1}\apSIGN=1 \apRETURN \fi - \edef\digits{\the\apFRAC}\advance\apFRAC by3 + \edef\digits{\the\apFRAC}\advance\apFRAC by4 \edef\signX{\the\apSIGN}% \ifnum\apSIGN<0 \apSIGN=1 \apREMfirst\OUT \fi % remove "minus" sign - \K=0 \N=0 % K = 0, N = 0 + \def\testBig ##1##2##3\relax##4{\ifx##1.\apXfalse \else + \ifx##2.\ifnum##1<4 \apXfalse \else \apXtrue \fi \else \apXtrue + \fi \fi \ifapX}% + \expandafter\testBig \OUT.\relax + \iftrue \apEXPb \else \apEXPa \fi % OUT = e^OUT + \ifnum\signX<0 \K=-\apE \apDIV 1\OUT \apE=\K \fi % if (signX < 0) OUT = 1 / OUT + \apSIGN=1 % EXP is always positive + \apEND +} +\def\apEXPa{% \def\testDot ##1##2\relax##3{\ifx##1.}% - \loop \expandafter \testDot\OUT \relax % loop if (OUT >= 1) - \iftrue \else % OUT = OUT/2 - \apDIV\OUT{2}% % K++ - \advance\K by1 % repeat - \repeat % now: #1 = 2^K * OUT, OUT < 1 + \K=0 \N=0 % K = 0, N = 0 + \loop \expandafter \testDot\OUT \relax % loop if (OUT >= 1) + \iftrue \else % OUT = OUT/2 + \apDIV\OUT{2}% % K++ + \advance\K by1 % repeat + \repeat % oriOUT = 2^K * OUT, OUT < 1 \advance\apFRAC by\K - \def\S{1}\def\Sn{1}\N=0 \let\X=\OUT % S = 1, Sn = 1, N = 0, X = OUT - \loop \advance\N by1 % loop N++ - \do\Sn=\apDIV{\apMUL\Sn\X}{\the\N};% % Sn = Sn * X / N - \apTAYLOR\iftrue \repeat % S = S + Sn (... Taylor) + \def\S{1}\def\Sn{1}\N=0 \let\X=\OUT % S = 1, Sn = 1, N = 0, X = OUT + \loop \advance\N by1 % loop N++ + \do\Sn=\apDIV{\apMUL\Sn\X}{\the\N};% % Sn = Sn * X / N + \apTAYLOR\iftrue \repeat % S = S + Sn (... Taylor) \N=0 - \loop \ifnum\N < \K % loop if (N < K) - \apPOW\OUT{2}\apROUND\OUT\apFRAC % OUT = OUT^2 - \advance\N by1 \repeat % N++ - \ifnum\signX<0 \apDIV 1\OUT \fi % if (signX < 0) OUT = 1 / OUT - \apROUND\OUT\digits \apSIGN=1 % EXP is always positive - \apEND + \loop \ifnum\N < \K % loop if (N < K) + \apPOW\OUT{2}% % OUT = OUT^2 + \advance\N by1 \repeat % N++ + \apFRAC=\digits\relax \apROUND\OUT\apFRAC } \def\apTAYLOR#1{\ifnum\apSIGN=0 \let\OUT=\S \else \apPLUS\S\Sn \let\S=\OUT } - -\def\LN#1{\relax \apINIT % OUT = LN(#1) ... - \evaldef\X{#1}% % X = #1 +\def\apEXPb{% + \let\X=\OUT \apLNtenexec \apDIV\X\apLNten \let\D=\OUT + \apROUND\D{0}% % D = floor( X/ln(X) ) + \ifnum\D<\apEX \advance\apFRAC by\D \relax \apLNtenexec \fi + \EXP{\X-\D*\apLNten}% % mantissa = EXP(X-D*LN(10)) + \ifnum\D<\apEX \apROLL\OUT\D \apE=0 \else \apE=\D \relax \fi + \apFRAC=\digits \apROUND\OUT\apFRAC % OUT = mantissa * 10^D +} +\def\LN#1{\relax \apINIT % OUT = LN(#1) ... + \evalmdef\X{#1}% % X = #1 \localcounts \M \N \E;% \E=\apE - \def\round{\apROUND\OUT\apFRAC}% \edef\digits{\the\apFRAC}\advance\apFRAC by4 \ifnum\apSIGN>0 \else \apERR{\string\LN: argument {\X} is out of range}\apRETURN\fi \apDIG\OUT\relax \M=\apnumD % find M: X = mantissa * 10^M @@ -880,10 +896,10 @@ \apDIV{\apPLUS{\A}{-1}}{\apPLUS{\A}{1}}% % OUT = (A-1) / (A+1) \ifnum\apSIGN=0 \def\OUT{0}\else % ln 1 = 0 else: \let\Sn=\OUT \let\Kn=\OUT \let\S=\OUT % Sn = OUT, Kn = OUT, S = OUT - \apPOW\OUT{2}\round \let\XX=\OUT % XX = OUT^2 + \apPOW\OUT{2}\apROUND\OUT\apFRAC \let\XX=\OUT % XX = OUT^2 \N=1 % N = 1 \loop \advance\N by2 % loop N = N + 2 - \do\Kn=\apMUL\Kn\XX\round;% % Kn = Kn * XX + \do\Kn=\apMUL\Kn\XX\apROUND\OUT\apFRAC;% Kn = Kn * XX \do\Sn=\apDIV\Kn{\the\N};% % Sn = Kn / N \apTAYLOR\iftrue \repeat % S = S + Sn (Taylor) \apMUL\S{2}% % OUT = 2 * OUT @@ -965,7 +981,7 @@ \def\COS{\relax \let\apSINCOSx=\apCOSx \apSINCOSa} \def\apSINCOSa#1{\apINIT \advance\apFRAC by3 - \evaldef\X{#1}\apEnum\X + \evalmdef\X{#1}\apEnum\X \def\signK{1}\apSINCOSo\apCOSx \ifnum\apSIGN<0 \apREMfirst\X \def\sign{-}\else\def\sign{+}\fi \ifx\apSINCOSx\apCOSx \def\sign{+}\fi @@ -1013,7 +1029,7 @@ \def\apSINCOSo#1{\ifnum\apSIGN=0 \ifx#1\SCgo \apSIGN=\signK \let\OUT=\signK \fi \apRETURN\fi} \def\TAN#1{\relax \apINIT \advance\apFRAC by3 - \evaldef\X{#1}\apEnum\X + \evalmdef\X{#1}\apEnum\X \advance\apFRAC by-3 \do\denom=\COS\X;% \ifnum\apSIGN=0 \apERR{\string\TAN: argument {\X} is out of range}\apRETURN\fi @@ -1023,7 +1039,7 @@ } \def\ATAN#1{\relax \apINIT \advance\apFRAC by3 - \evaldef\X{#1}\apEnum + \evalmdef\X{#1}\apEnum\X \ifnum\apSIGN=0 \def\OUT{0}\apRETURN\fi \ifnum\apSIGN<0 \def\sign{-}\apREMfirst\X \else\def\sign{}\fi \let\tmp=\X \apDIG\tmp\relax @@ -1053,7 +1069,7 @@ \apTAYLOR \iftrue \repeat } \def\ASIN#1{\relax \apINIT - \evaldef\X{#1}\apEnum\X \edef\sign{\the\apSIGN}% + \evalmdef\X{#1}\apEnum\X \edef\sign{\the\apSIGN}% \apPLUS 1{-\apPOW\X2}% OUT = 1 - X^2 \ifnum\apSIGN<0 \apERR{\string\ASIN: argument {\X} is out of range}\apRETURN\fi \do\sqrt=\SQRT\OUT;% sqrt = SRQT {1 - X^1} @@ -1138,7 +1154,7 @@ \let\SIGN=\apSIGN \let\ROUND=\apROUND \let\NORM=\apNORM \let\ROLL=\apROLL \ifx\documentclass\undefined \else % please, don't remove this message -\message{SORRY, you are using LaTeX. I don't recommend this. Petr Olsak}\fi +\message{WARNING: the author of apnum package recommends: Never use LaTeX.}\fi \catcode`\@=\apnumZ \endinput @@ -1167,8 +1183,11 @@ - \ATAN, \ASIN, \ACOS added - \SIN, \COS, \TAN added - \apTOT=0 by default -1.4a \end -> \limits, internal change in \ebvaldef because LaTeX redefines \end +1.4a \end -> \limits, internal change in \evaldef because LaTeX redefines \end 1.4b \apSINCOS: \ifx\OUT eq 0 added after \apROUND (bug fixed). -1.5 <Jan 2015> +1.5 <Jan 2016> - \iROUND replaced by \iFLOOR, \iFRAC corrected (for negative numbers) - \eprint introduced +1.6 <Feb 2016> + - \evalmdef introduced + - \EXP for arg>=4 rewritten, \apEX register introduced |