From af44b62ae72030d27d75d2f6b9a3619fb2a54821 Mon Sep 17 00:00:00 2001 From: Karl Berry Date: Tue, 17 Dec 2019 23:24:25 +0000 Subject: intcalc split from oberdiek (18dec19) git-svn-id: svn://tug.org/texlive/trunk@53168 c570f23f-e606-0410-a88d-b1316a301751 --- Master/texmf-dist/source/latex/intcalc/intcalc.dtx | 3286 ++++++++++++++++++++ 1 file changed, 3286 insertions(+) create mode 100644 Master/texmf-dist/source/latex/intcalc/intcalc.dtx (limited to 'Master/texmf-dist/source/latex/intcalc') diff --git a/Master/texmf-dist/source/latex/intcalc/intcalc.dtx b/Master/texmf-dist/source/latex/intcalc/intcalc.dtx new file mode 100644 index 00000000000..fec737844c2 --- /dev/null +++ b/Master/texmf-dist/source/latex/intcalc/intcalc.dtx @@ -0,0 +1,3286 @@ +% \iffalse meta-comment +% +% File: intcalc.dtx +% Version: 2019/12/15 v1.3 +% Info: Expandable calculations with integers +% +% Copyright (C) +% 2007 Heiko Oberdiek +% 2016-2019 Oberdiek Package Support Group +% https://github.com/ho-tex/intcalc/issues +% +% This work may be distributed and/or modified under the +% conditions of the LaTeX Project Public License, either +% version 1.3c of this license or (at your option) any later +% version. This version of this license is in +% https://www.latex-project.org/lppl/lppl-1-3c.txt +% and the latest version of this license is in +% https://www.latex-project.org/lppl.txt +% and version 1.3 or later is part of all distributions of +% LaTeX version 2005/12/01 or later. +% +% This work has the LPPL maintenance status "maintained". +% +% The Current Maintainers of this work are +% Heiko Oberdiek and the Oberdiek Package Support Group +% https://github.com/ho-tex/intcalc/issues +% +% The Base Interpreter refers to any `TeX-Format', +% because some files are installed in TDS:tex/generic//. +% +% This work consists of the main source file intcalc.dtx +% and the derived files +% intcalc.sty, intcalc.pdf, intcalc.ins, intcalc.drv, +% intcalc-test1.tex, intcalc-test2.tex, intcalc-test3.tex, +% intcalc-test4.tex. +% +% Distribution: +% CTAN:macros/latex/contrib/intcalc/intcalc.dtx +% CTAN:macros/latex/contrib/intcalc/intcalc.pdf +% +% Unpacking: +% (a) If intcalc.ins is present: +% tex intcalc.ins +% (b) Without intcalc.ins: +% tex intcalc.dtx +% (c) If you insist on using LaTeX +% latex \let\install=y\input{intcalc.dtx} +% (quote the arguments according to the demands of your shell) +% +% Documentation: +% (a) If intcalc.drv is present: +% latex intcalc.drv +% (b) Without intcalc.drv: +% latex intcalc.dtx; ... +% The class ltxdoc loads the configuration file ltxdoc.cfg +% if available. Here you can specify further options, e.g. +% use A4 as paper format: +% \PassOptionsToClass{a4paper}{article} +% +% Programm calls to get the documentation (example): +% pdflatex intcalc.dtx +% makeindex -s gind.ist intcalc.idx +% pdflatex intcalc.dtx +% makeindex -s gind.ist intcalc.idx +% pdflatex intcalc.dtx +% +% Installation: +% TDS:tex/generic/intcalc/intcalc.sty +% TDS:doc/latex/intcalc/intcalc.pdf +% TDS:source/latex/intcalc/intcalc.dtx +% +%<*ignore> +\begingroup + \catcode123=1 % + \catcode125=2 % + \def\x{LaTeX2e}% +\expandafter\endgroup +\ifcase 0\ifx\install y1\fi\expandafter + \ifx\csname processbatchFile\endcsname\relax\else1\fi + \ifx\fmtname\x\else 1\fi\relax +\else\csname fi\endcsname +% +%<*install> +\input docstrip.tex +\Msg{************************************************************************} +\Msg{* Installation} +\Msg{* Package: intcalc 2019/12/15 v1.3 Expandable calculations with integers (HO)} +\Msg{************************************************************************} + +\keepsilent +\askforoverwritefalse + +\let\MetaPrefix\relax +\preamble + +This is a generated file. + +Project: intcalc +Version: 2019/12/15 v1.3 + +Copyright (C) + 2007 Heiko Oberdiek + 2016-2019 Oberdiek Package Support Group + +This work may be distributed and/or modified under the +conditions of the LaTeX Project Public License, either +version 1.3c of this license or (at your option) any later +version. This version of this license is in + https://www.latex-project.org/lppl/lppl-1-3c.txt +and the latest version of this license is in + https://www.latex-project.org/lppl.txt +and version 1.3 or later is part of all distributions of +LaTeX version 2005/12/01 or later. + +This work has the LPPL maintenance status "maintained". + +The Current Maintainers of this work are +Heiko Oberdiek and the Oberdiek Package Support Group +https://github.com/ho-tex/intcalc/issues + + +The Base Interpreter refers to any `TeX-Format', +because some files are installed in TDS:tex/generic//. + +This work consists of the main source file intcalc.dtx +and the derived files + intcalc.sty, intcalc.pdf, intcalc.ins, intcalc.drv, + intcalc-test1.tex, intcalc-test2.tex, intcalc-test3.tex, + intcalc-test4.tex. + +\endpreamble +\let\MetaPrefix\DoubleperCent + +\generate{% + \file{intcalc.ins}{\from{intcalc.dtx}{install}}% + \file{intcalc.drv}{\from{intcalc.dtx}{driver}}% + \usedir{tex/generic/intcalc}% + \file{intcalc.sty}{\from{intcalc.dtx}{package}}% +} + +\catcode32=13\relax% active space +\let =\space% +\Msg{************************************************************************} +\Msg{*} +\Msg{* To finish the installation you have to move the following} +\Msg{* file into a directory searched by TeX:} +\Msg{*} +\Msg{* intcalc.sty} +\Msg{*} +\Msg{* To produce the documentation run the file `intcalc.drv'} +\Msg{* through LaTeX.} +\Msg{*} +\Msg{* Happy TeXing!} +\Msg{*} +\Msg{************************************************************************} + +\endbatchfile +% +%<*ignore> +\fi +% +%<*driver> +\NeedsTeXFormat{LaTeX2e} +\ProvidesFile{intcalc.drv}% + [2019/12/15 v1.3 Expandable calculations with integers (HO)]% +\documentclass{ltxdoc} +\usepackage{wasysym} +\let\iint\relax +\let\iiint\relax +\usepackage[fleqn]{amsmath} + +\DeclareMathOperator{\opInv}{Inv} +\DeclareMathOperator{\opAbs}{Abs} +\DeclareMathOperator{\opSgn}{Sgn} +\DeclareMathOperator{\opMin}{Min} +\DeclareMathOperator{\opMax}{Max} +\DeclareMathOperator{\opCmp}{Cmp} +\DeclareMathOperator{\opInc}{Inc} +\DeclareMathOperator{\opDec}{Dec} +\DeclareMathOperator{\opAdd}{Add} +\DeclareMathOperator{\opSub}{Sub} +\DeclareMathOperator{\opShl}{Shl} +\DeclareMathOperator{\opShr}{Shr} +\DeclareMathOperator{\opMul}{Mul} +\DeclareMathOperator{\opSqr}{Sqr} +\DeclareMathOperator{\opFac}{Fac} +\DeclareMathOperator{\opPow}{Pow} +\DeclareMathOperator{\opDiv}{Div} +\DeclareMathOperator{\opMod}{Mod} +\DeclareMathOperator{\opInt}{Int} +\DeclareMathOperator{\opOdd}{ifodd} + +\newcommand*{\Def}{% + \ensuremath{% + \mathrel{\mathop{:}}=% + }% +} +\newcommand*{\op}[1]{% + \textsf{#1}% +} +\usepackage{holtxdoc}[2011/11/22] +\begin{document} + \DocInput{intcalc.dtx}% +\end{document} +% +% \fi +% +% +% +% \GetFileInfo{intcalc.drv} +% +% \title{The \xpackage{intcalc} package} +% \date{2019/12/15 v1.3} +% \author{Heiko Oberdiek\thanks +% {Please report any issues at \url{https://github.com/ho-tex/intcalc/issues}}} +% +% \maketitle +% +% \begin{abstract} +% This package provides expandable arithmetic operations +% with integers. +% \end{abstract} +% +% \tableofcontents +% +% \section{Documentation} +% +% \subsection{Introduction} +% +% Package \xpackage{intcalc} defines arithmetic operations +% that deal with integers. Integers mean numbers in \TeX. +% The same restrictions apply, the range is limited to +% [-2147483647, 2147483647]. +% +% The operations have the form of macros that take one or +% two integers as parameter and return the integer result. +% The macro name is a three letter operation name prefixed +% by the package name, e.g. \cs{intcalcAdd}|{10}{43}| returns +% |53|. +% +% The macros are fully expandable, exactly two expansion +% steps generate the result. Therefore the operations +% may be used nearly everywhere in \TeX, even inside +% \cs{number}, \cs{csname}, file names, or other +% expandable contexts. +% +% The package contains two implementations of the operations. +% If \eTeX\ is detected then the macros are implemented +% using its features (\cs{numexpr}). Otherwise the slower +% implementation without \eTeX's help is choosen. +% +% \subsection{Conditions} +% +% \subsubsection{Preconditions} +% +% \begin{itemize} +% \item +% Arguments can be anything that \TeX\ interprets as ``number''. +% Examples: plain numbers, count or length register, macros +% that expands to a number. +% \item +% The arguments are limited to the range +% -2147483647 until 2147483647. These numbers belong to the range. +% Note that some operations +% have additionals restrictions to the range. +% \item +% The argument may be expressions that \cs{numexpr} +% understands if \eTeX\ is available. +% \item +% The resulting number must fit in the allowed range. +% \end{itemize} +% +% \subsubsection{Postconditions} +% +% Additional properties of the macros apart from calculating +% a correct result (of course \smiley): +% \begin{itemize} +% \item +% The macros are fully expandable. Thus they can +% be used inside \cs{edef}, \cs{csname}, after \cs{number}, +% for example. +% \item +% Furthermore exactly two expansion steps calculate the result. +% \item +% The number consists of one optional minus sign and one to +% ten digits. The first digit is larger than zero for +% numbers that consists of more than one digit. +% +% In short, the number format is exactly the same as +% \cs{number} generates. And the tokens (minus sign, digits) +% have catcode 12 (other). +% \item +% Call by value is simulated. First the arguments are +% converted to numbers. Then these numbers are used +% in the calculations. +% +% Remember that arguments +% may contain expensive macros or \eTeX\ expressions. +% This strategy avoids multiple evaluations of such +% arguments. +% \end{itemize} +% +% \subsection{Error handling} +% +% There are two kinds of errors if a precondition is violated: +% Some errors are detected by the macros, example: division by zero. +% In this cases an undefined control sequence is called and causes +% a TeX error message, example: \cs{IntCalcError:DivisionByZero}. +% The name of the control sequence contains +% the reason for the error. The \TeX\ error may be ignored. +% Then the operation returns zero as result. +% Because the macros are supposed to work in expandible contexts. +% An traditional error message, however, is not expandable and +% would break these contexts. +% +% If a number exceeds the range of -2147483647 until 2147483647, then +% \TeX\ throws an error ``Number too big'' and recovers by +% using biggest allowed value. +% Example for the negative number -3000000000 is replaced +% by -2147483647. +% +% \subsection{Operations} +% +% Some definition equations below use the function $\opInt$ +% that converts a real number to an integer. The number +% is truncated that means rounding to zero: +% \begin{gather*} +% \opInt(x) \Def +% \begin{cases} +% \lfloor x\rfloor & \text{if $x\geq0$}\\ +% \lceil x\rceil & \text{otherwise} +% \end{cases} +% \end{gather*} +% +% \subsubsection{\op{Num}} +% +% \begin{declcs}{intcalcNum} \M{x} +% \end{declcs} +% Macro \cs{intcalcNum} converts its argument to a normalized integer +% number without unnecessary leading zeros or signs. +% The result matches the regular expression: +%\begin{quote} +%\begin{verbatim} +%0|-?[1-9][0-9]* +%\end{verbatim} +%\end{quote} +% +% \subsubsection{\op{Inv}, \op{Abs}, \op{Sgn}} +% +% \begin{declcs}{intcalcInv} \M{x} +% \end{declcs} +% Macro \cs{intcalcInv} switches the sign. +% \begin{gather*} +% \opInv(x) \Def -x +% \end{gather*} +% +% \begin{declcs}{intcalcAbs} \M{x} +% \end{declcs} +% Macro \cs{intcalcAbs} returns the absolute value +% of integer \meta{x}. +% \begin{gather*} +% \opAbs(x) \Def \vert x\vert +% \end{gather*} +% +% \begin{declcs}{intcalcSgn} \M{x} +% \end{declcs} +% Macro \cs{intcalcSgn} encodes the sign of \meta{x} as number. +% \begin{gather*} +% \opSgn(x) \Def +% \begin{cases} +% -1& \text{if $x<0$}\\ +% 0& \text{if $x=0$}\\ +% 1& \text{if $x>0$} +% \end{cases} +% \end{gather*} +% These return values can easily be distinguished by \cs{ifcase}: +%\begin{quote} +%\begin{verbatim} +%\ifcase\intcalcSgn{} +% $x=0$ +%\or +% $x>0$ +%\else +% $x<0$ +%\fi +%\end{verbatim} +%\end{quote} +% +% \subsubsection{\op{Min}, \op{Max}, \op{Cmp}} +% +% \begin{declcs}{intcalcMin} \M{x} \M{y} +% \end{declcs} +% Macro \cs{intcalcMin} returns the smaller of the two integers. +% \begin{gather*} +% \opMin(x,y) \Def +% \begin{cases} +% x & \text{if $xy$}\\ +% y & \text{otherwise} +% \end{cases} +% \end{gather*} +% +% \begin{declcs}{intcalcCmp} \M{x} \M{y} +% \end{declcs} +% Macro \cs{intcalcCmp} encodes the comparison result as number: +% \begin{gather*} +% \opCmp(x,y) \Def +% \begin{cases} +% -1 & \text{if $xy$} +% \end{cases} +% \end{gather*} +% These values can be distinguished by \cs{ifcase}: +%\begin{quote} +%\begin{verbatim} +%\ifcase\intcalcCmp{}{} +% $x=y$ +%\or +% $x>y$ +%\else +% $x +% \end{macrocode} +% +% \subsection{Reload check and package identification} +% Reload check, especially if the package is not used with \LaTeX. +% \begin{macrocode} +\begingroup\catcode61\catcode48\catcode32=10\relax% + \catcode13=5 % ^^M + \endlinechar=13 % + \catcode35=6 % # + \catcode39=12 % ' + \catcode44=12 % , + \catcode45=12 % - + \catcode46=12 % . + \catcode58=12 % : + \catcode64=11 % @ + \catcode123=1 % { + \catcode125=2 % } + \expandafter\let\expandafter\x\csname ver@intcalc.sty\endcsname + \ifx\x\relax % plain-TeX, first loading + \else + \def\empty{}% + \ifx\x\empty % LaTeX, first loading, + % variable is initialized, but \ProvidesPackage not yet seen + \else + \expandafter\ifx\csname PackageInfo\endcsname\relax + \def\x#1#2{% + \immediate\write-1{Package #1 Info: #2.}% + }% + \else + \def\x#1#2{\PackageInfo{#1}{#2, stopped}}% + \fi + \x{intcalc}{The package is already loaded}% + \aftergroup\endinput + \fi + \fi +\endgroup% +% \end{macrocode} +% Package identification: +% \begin{macrocode} +\begingroup\catcode61\catcode48\catcode32=10\relax% + \catcode13=5 % ^^M + \endlinechar=13 % + \catcode35=6 % # + \catcode39=12 % ' + \catcode40=12 % ( + \catcode41=12 % ) + \catcode44=12 % , + \catcode45=12 % - + \catcode46=12 % . + \catcode47=12 % / + \catcode58=12 % : + \catcode64=11 % @ + \catcode91=12 % [ + \catcode93=12 % ] + \catcode123=1 % { + \catcode125=2 % } + \expandafter\ifx\csname ProvidesPackage\endcsname\relax + \def\x#1#2#3[#4]{\endgroup + \immediate\write-1{Package: #3 #4}% + \xdef#1{#4}% + }% + \else + \def\x#1#2[#3]{\endgroup + #2[{#3}]% + \ifx#1\@undefined + \xdef#1{#3}% + \fi + \ifx#1\relax + \xdef#1{#3}% + \fi + }% + \fi +\expandafter\x\csname ver@intcalc.sty\endcsname +\ProvidesPackage{intcalc}% + [2019/12/15 v1.3 Expandable calculations with integers (HO)]% +% \end{macrocode} +% +% \subsection{Catcodes} +% +% \begin{macrocode} +\begingroup\catcode61\catcode48\catcode32=10\relax% + \catcode13=5 % ^^M + \endlinechar=13 % + \catcode123=1 % { + \catcode125=2 % } + \catcode64=11 % @ + \def\x{\endgroup + \expandafter\edef\csname InCa@AtEnd\endcsname{% + \endlinechar=\the\endlinechar\relax + \catcode13=\the\catcode13\relax + \catcode32=\the\catcode32\relax + \catcode35=\the\catcode35\relax + \catcode61=\the\catcode61\relax + \catcode64=\the\catcode64\relax + \catcode123=\the\catcode123\relax + \catcode125=\the\catcode125\relax + }% + }% +\x\catcode61\catcode48\catcode32=10\relax% +\catcode13=5 % ^^M +\endlinechar=13 % +\catcode35=6 % # +\catcode64=11 % @ +\catcode123=1 % { +\catcode125=2 % } +\def\TMP@EnsureCode#1#2{% + \edef\InCa@AtEnd{% + \InCa@AtEnd + \catcode#1=\the\catcode#1\relax + }% + \catcode#1=#2\relax +} +\TMP@EnsureCode{33}{12}% ! +\TMP@EnsureCode{40}{12}% ( +\TMP@EnsureCode{41}{12}% ) +\TMP@EnsureCode{42}{12}% * +\TMP@EnsureCode{43}{12}% + +\TMP@EnsureCode{45}{12}% - +\TMP@EnsureCode{47}{12}% / +\TMP@EnsureCode{58}{11}% : (letter!) +\TMP@EnsureCode{60}{12}% < +\TMP@EnsureCode{62}{12}% > +\TMP@EnsureCode{63}{14}% ? (comment!) +\edef\InCa@AtEnd{\InCa@AtEnd\noexpand\endinput} +\begingroup\expandafter\expandafter\expandafter\endgroup +\expandafter\ifx\csname InCa@TestMode\endcsname\relax +\else + \catcode63=9 % ? (ignore) +\fi +? \let\InCa@@TestMode\InCa@TestMode +% \end{macrocode} +% +% \subsection{Macros independent of \eTeX} +% +% \subsubsection{\op{Abs}, \op{Sgn}} +% +% \begin{macro}{\InCa@Abs} +% \begin{macrocode} +\def\InCa@Abs#1#2!{% + \ifx#1-% + #2% + \else + #1#2% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@Sgn} +% \begin{macrocode} +\def\InCa@Sgn#1#2!{% + \ifx#1-% + -1% + \else + \ifx#10% + 0% + \else + 1% + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Min}, \op{Max}, \op{Cmp}} +% +% \begin{macro}{\InCa@Min} +% \begin{macrocode} +\def\InCa@Min#1!#2!{% + \ifnum#1<#2 % + #1% + \else + #2% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@Max} +% \begin{macrocode} +\def\InCa@Max#1!#2!{% + \ifnum#1>#2 % + #1% + \else + #2% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@Cmp} +% \begin{macrocode} +\def\InCa@Cmp#1!#2!{% + \ifnum#1=#2 % + 0% + \else + \ifnum#1<#2 % + -% + \fi + 1% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Fac}} +% +% \begin{macro}{\InCa@Fac} +% It does not make much sense to calculate the +% faculty by an general algorithm. The allowed +% range of arguments is too low because of the +% limited integer domain. +% \begin{macrocode} +\def\InCa@Fac#1!{% + \ifcase#1 1% 0! + \or 1% 1! + \or 2% 2! + \or 6% 3! + \or 24% 4! + \or 120% 5! + \or 720% 6! + \or 5040% 7! + \or 40320% 8! + \or 362880% 9! + \or 3628800% 10! + \or 39916800% 11! + \or 479001600% 12! + \else + \ifnum#1<\z@ + 0\IntCalcError:FacNegative% + \else + 0\IntCalcError:FacOverflow% + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% +% \subsection{Implementation based on \eTeX} +% +% Only \cs{numexpr} is used from \eTeX. +% \begin{macrocode} +\begingroup\expandafter\expandafter\expandafter\endgroup +\expandafter\ifx\csname numexpr\endcsname\relax +\else +% \end{macrocode} +% +% \subsubsection{\op{Num}} +% +% \begin{macro}{\intcalcNum} +% \begin{macrocode} + \def\intcalcNum#1{% + \the\numexpr#1\relax + }% +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Inv}, \op{Abs}, \op{Sgn}} +% +% \begin{macro}{\intcalcInv} +% \begin{macrocode} + \def\intcalcInv#1{% + \number-\intcalcNum{#1} % + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcAbs} +% \begin{macrocode} + \def\intcalcAbs#1{% + \number\expandafter\InCa@Abs\the\numexpr#1! % + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcSgn} +% \begin{macrocode} + \def\intcalcSgn#1{% + \number\expandafter\InCa@Sgn\the\numexpr#1! % + }% +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Min}, \op{Max}, \op{Cmp}} +% +% \begin{macro}{\intcalcMin} +% \begin{macrocode} + \def\intcalcMin#1#2{% + \number\expandafter\InCa@Min + \the\numexpr#1\expandafter!% + \the\numexpr#2! % + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcMax} +% \begin{macrocode} + \def\intcalcMax#1#2{% + \number\expandafter\InCa@Max + \the\numexpr#1\expandafter!% + \the\numexpr#2! % + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcCmp} +% \begin{macrocode} + \def\intcalcCmp#1#2{% + \number\expandafter\InCa@Cmp + \the\numexpr#1\expandafter!\the\numexpr#2! % + }% +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Inc}, \op{Dec}} +% +% \begin{macro}{\intcalcInc} +% \begin{macrocode} + \def\intcalcInc#1{% + \the\numexpr#1+1\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcDec} +% \begin{macrocode} + \def\intcalcDec#1{% + \the\numexpr#1-1\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\IntCalcInc} +% \begin{macrocode} + \def\IntCalcInc#1!{% + \the\numexpr#1+1\relax + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcDec} +% \begin{macrocode} + \def\IntCalcDec#1!{% + \the\numexpr#1-1\relax + }% +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Add}, \op{Sub}} +% +% \begin{macro}{\intcalcAdd} +% \begin{macrocode} + \def\intcalcAdd#1#2{% + \the\numexpr#1+(#2)\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcSub} +% \begin{macrocode} + \def\intcalcSub#1#2{% + \the\numexpr#1-(#2)\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\IntCalcAdd} +% \begin{macrocode} + \def\IntCalcAdd#1!#2!{% + \the\numexpr#1+#2\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\IntCalcSub} +% \begin{macrocode} + \def\IntCalcSub#1!#2!{% + \the\numexpr#1-#2\relax + }% +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Shl}, \op{Shr}} +% +% \begin{macro}{\intcalcShl} +% \begin{macrocode} + \def\intcalcShl#1{% + \the\numexpr(#1)*2\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcShr} +% \begin{macrocode} + \def\intcalcShr#1{% + \number\expandafter\InCa@Shr\the\numexpr#1! % + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcShl} +% \begin{macrocode} + \def\IntCalcShl#1!{% + \the\numexpr#1*2\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\IntCalcShr} +% \begin{macrocode} + \def\IntCalcShr#1!{% + \the\numexpr\ifodd#1 (#1-1)\else#1\fi/2\relax + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Shr} +% \begin{macrocode} + \def\InCa@Shr#1#2!{% + \ifx#1-% + -\InCa@Shr#2!% + \else + \ifodd#1#2 % + \the\numexpr(#1#2-1)/2\relax + \else + \the\numexpr#1#2/2\relax + \fi + \fi + }% +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Mul}, \op{Sqr}, \op{Fac}} +% +% \begin{macro}{\intcalcMul} +% \begin{macrocode} + \def\intcalcMul#1#2{% + \the\numexpr(#1)*(#2)\relax + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcMul} +% \begin{macrocode} + \def\IntCalcMul#1!#2!{% + \the\numexpr#1*#2\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcSqr} +% \begin{macrocode} + \def\intcalcSqr#1{% + \number\expandafter\InCa@Sqr\the\numexpr#1! % + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Sqr} +% \begin{macrocode} + \def\InCa@Sqr#1!{% + \the\numexpr#1*#1\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcFac} +% \begin{macrocode} + \def\intcalcFac#1{% + \number\expandafter\InCa@Fac\the\numexpr#1! % + }% +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Pow}} +% +% \begin{macro}{\intcalcPow} +% \begin{macrocode} + \def\intcalcPow#1#2{% + \number\expandafter\InCa@Pow + \the\numexpr#1\expandafter!% + \the\numexpr#2! % + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Pow} +% \begin{macrocode} + \def\InCa@Pow#1#2!#3#4!{% + \ifcase#3#4 % power = 0 + 1% + \or % power = 1 + #1#2% + \or % power = 2 + \the\numexpr#1#2*#1#2\relax + \else + \ifcase#1#2 % basis = 0, power <> 0 + 0% + \ifx#3-% power < 0 + 0\IntCalcError:DivisionByZero% + \fi + \or + 1% basis = 1 + \else + \ifnum#1#2=\m@ne % basis = -1 + \ifodd#3#4 % + -% + \fi + 1% + \else % |basis| > 1 + \ifx#3-% power < 0 + 0% + \else % power > 2 + \InCa@PowRec#1#2!#3#4!1!% + \fi + \fi + \fi + \fi + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@PowRec} +%\begin{quote} +%\begin{verbatim} +%Pow(b, p) { +% PowRec(b, p, 1) +%} +%PowRec(b, p, r) { +% if p == 1 then +% return r*b +% else +% ifodd p then +% return PowRec(b*b, (p-1)/2, r*b) % p div 2 = (p-1)/2 +% else +% return PowRec(b*b, (p-1)/2, r) +% fi +% fi +%} +%\end{verbatim} +%\end{quote} +% \begin{macrocode} + \def\InCa@PowRec#1!#2!#3!{% + \ifnum#2=\@ne + \the\numexpr#1*#3\relax + \else + \ifodd#2 % + \expandafter\InCa@PowRec + \the\numexpr#1*#1\expandafter!% + \the\numexpr(#2-1)/2\expandafter!% + \the\numexpr#1*#3\expandafter\expandafter\expandafter!% + \else + \expandafter\InCa@PowRec + \the\numexpr#1*#1\expandafter!% + \the\numexpr(#2-1)/2\expandafter!% + \number#3\expandafter\expandafter\expandafter!% + \fi + \fi + }% +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Div}, \op{Mod}} +% +% \TeX's \cs{divide} truncates, +% \eTeX's \cs{numexpr} rounds the result of a division. +% The rounding method is called ``Symmetric Arithmetic Rounding'' +% or ``Round-Half-Up'' (``Kaufm\"annisches Runden'' in German): +% \begin{quote} +% | 1 = 3 divide 2 = 1.5 = numexpr 3/2 = 2|\\ +% |-1 = -3 divide 2 = -1.5 = numexpr -3/2 = -2| +% \end{quote} +% Macro \cs{intcalcDiv} follows \TeX\ and truncates. +% The calculation is done by the following formula: +% \begin{gather} +% \opDiv(X,Y) = (X - (Y-1)/2)/Y\qquad\text{for $X, Y > 0$} +% \end{gather} +% The operator `/' is \cs{numexpr}'s division. +% \begin{macro}{\intcalcDiv} +% \begin{macrocode} + \def\intcalcDiv#1#2{% + \number\expandafter\InCa@Div + \the\numexpr#1\expandafter!% + \the\numexpr#2! % + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Div} +% \begin{macrocode} + \def\InCa@Div#1!#2!{% + \ifcase#2 % + 0\IntCalcError:DivisionByZero% + \else + \ifcase#1 % + 0% + \else + \expandafter\InCa@@Div + \romannumeral 0% + \ifnum#1<\z@ + \expandafter-\number-#1% + \else + \expandafter+\number#1% + \fi + \expandafter!% + \romannumeral 0% + \ifnum#2<\z@ + \expandafter-\number-#2% + \else + \expandafter+\number#2% + \fi + !% + \fi + \fi + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcDiv} +% \begin{macrocode} + \def\InCa@Temp#1{% + \def\IntCalcDiv##1!##2!{% + \number + \ifcase##2 % + 0\IntCalcError:DivisionByZero% + \else + \ifcase##1 % + 0% + \else + \the\numexpr(##1-(##2-1)/2)/##2\relax + \fi + \fi + #1% + }% + }% + \InCa@Temp{ }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@@Div} +% \begin{macrocode} + \def\InCa@@Div#1#2!#3#4!{% + #1#3% + \the\numexpr(#2-(#4-1)/2)/#4\relax + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcMod} +% \begin{macrocode} + \def\intcalcMod#1#2{% + \number\expandafter\InCa@Mod + \the\numexpr#1\expandafter!% + \the\numexpr#2! % + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Mod} +% \begin{macrocode} + \def\InCa@Mod#1!#2!{% + \ifcase#2 % + 0\IntCalcError:DivisionByZero% + \else + \ifcase#1 % + 0% + \else + \expandafter\InCa@@Mod + \romannumeral 0% + \ifnum#1<\z@ + \expandafter-\number-#1% + \else + \expandafter+\number#1% + \fi + \expandafter!% + \romannumeral 0% + \ifnum#2<\z@ + \expandafter-\number-#2% + \else + \expandafter+\number#2% + \fi + !% + \fi + \fi + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcMod} +% \begin{macrocode} + \def\InCa@Temp#1{% + \def\IntCalcMod##1!##2!{% + \number + \ifcase##2 % + 0\IntCalcError:DivisionByZero% + \else + \ifcase##1 % + 0% + \else + \the\numexpr##1-(##1-(##2-1)/2)/##2*##2\relax + \fi + \fi + #1% + }% + }% + \InCa@Temp{ }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@@Mod} +% \begin{macrocode} + \def\InCa@@Mod#1#2!#3#4!{% + \if#3+% + \if#1+% + \the\numexpr#2-\InCa@@Div+#2!+#4!*#4\relax + \else + \expandafter\InCa@ModX + \the\numexpr-#2+\InCa@@Div+#2!+#4!*#4!#4!% + \fi + \else + -% + \if#1+% + \expandafter\InCa@ModX + \the\numexpr-#2+\InCa@@Div+#2!+#4!*#4!#4!% + \else + \the\numexpr#2-\InCa@@Div+#2!+#4!*#4\relax + \fi + \fi + }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@ModX} +% \begin{macrocode} + \def\InCa@ModX#1!#2!{% + \ifcase#1 % + 0% + \else + \the\numexpr#1+#2\relax + \fi + }% +% \end{macrocode} +% \end{macro} +% +% \begin{macrocode} + \expandafter\InCa@AtEnd +\fi% +% \end{macrocode} +% +% \subsection{Implementation without \eTeX} +% +% \subsubsection{\op{Num}} +% +% \begin{macro}{\intcalcNum} +% \begin{macrocode} +\def\intcalcNum#1{% + \number\expandafter\InCa@FirstOfOne\number#1! % +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Inv}, \op{Abs}, \op{Sgn}} +% +% \begin{macro}{\intcalcInv} +% \begin{macrocode} +\def\intcalcInv#1{% + \number\expandafter\InCa@FirstOfOne\number-#1! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@FirstOfOne} +% \begin{macrocode} +\def\InCa@FirstOfOne#1!{#1} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcAbs} +% \begin{macrocode} +\def\intcalcAbs#1{% + \number\expandafter\InCa@Abs\number#1! % +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcSgn} +% \begin{macrocode} +\def\intcalcSgn#1{% + \number\expandafter\InCa@Sgn\number#1! % +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Min}, \op{Max}, \op{Cmp}} +% +% \begin{macro}{\intcalcMin} +% \begin{macrocode} +\def\intcalcMin#1#2{% + \number\expandafter\InCa@Min + \number\number#1\expandafter!\number#2! % +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcMax} +% \begin{macrocode} +\def\intcalcMax#1#2{% + \number\expandafter\InCa@Max + \number\number#1\expandafter!\number#2! % +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcCmp} +% \begin{macrocode} +\def\intcalcCmp#1#2{% + \number\expandafter\InCa@Cmp + \number\number#1\expandafter!\number#2! % +}% +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Inc}, \op{Dec}} +% +% \begin{macro}{\intcalcInc} +% \begin{macrocode} +\def\intcalcInc#1{% + \number\expandafter\InCa@IncSwitch\number#1! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@IncSwitch} +% \begin{macrocode} +\def\InCa@IncSwitch#1#2!{% + \ifx#1-% + -% + \csname InCa@Empty% + \InCa@Dec#2!% + \else + \csname InCa@Empty% + \InCa@Inc#1#2!% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\intcalcDec} +% \begin{macrocode} +\def\intcalcDec#1{% + \number\expandafter\InCa@DecSwitch\number#1! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@DecSwitch} +% \begin{macrocode} +\def\InCa@DecSwitch#1#2!{% + \ifx#1-% + -% + \csname InCa@Empty% + \expandafter\InCa@Inc#2!% + \else + \ifx#10% + -1% + \else + \csname InCa@Empty% + \InCa@Dec#1#2!% + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\IntCalcInc} +% \begin{macrocode} +\def\IntCalcInc#1!{% + \number\csname InCa@Empty\InCa@Inc#1! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcDec} +% \begin{macrocode} +\def\IntCalcDec#1!{% + \number\csname InCa@Empty\InCa@Dec#1! % +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@Inc} +% \begin{macrocode} +\def\InCa@Inc#1#2{% + \ifx#2!% + \csname InCa@IncDigit#1\endcsname1% + \else + \csname InCa@IncDigit#1% + \expandafter\InCa@Inc\expandafter#2% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@IncDigit[0-8]} +% \begin{macrocode} +\def\InCa@Temp#1#2{% + \expandafter\def\csname InCa@IncDigit#1\endcsname##1{% + \endcsname + 0% + \ifcase##1 % + #1% + \else + #2% + \fi + }% +} +\InCa@Temp 01 +\InCa@Temp 12 +\InCa@Temp 23 +\InCa@Temp 34 +\InCa@Temp 45 +\InCa@Temp 56 +\InCa@Temp 67 +\InCa@Temp 78 +\InCa@Temp 89 +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@IncDigit9} +% \begin{macrocode} +\expandafter\def\csname InCa@IncDigit9\endcsname#1{% + \expandafter\endcsname + \ifcase#1 % + 09% + \else + 10% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@Dec} +% \begin{macrocode} +\def\InCa@Dec#1#2{% + \ifx#2!% + \csname InCa@DecDigit#1\endcsname1% + \else + \csname InCa@DecDigit#1% + \expandafter\InCa@Dec\expandafter#2% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@DecDigit[1-9]} +% \begin{macrocode} +\def\InCa@Temp#1#2{% + \expandafter\def\csname InCa@DecDigit#1\endcsname##1{% + \endcsname + 0% + \ifcase##1 % + #1% + \else + #2% + \fi + }% +} +\InCa@Temp 98 +\InCa@Temp 87 +\InCa@Temp 76 +\InCa@Temp 65 +\InCa@Temp 54 +\InCa@Temp 43 +\InCa@Temp 32 +\InCa@Temp 21 +\InCa@Temp 10 +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@DecDigit0} +% \begin{macrocode} +\expandafter\def\csname InCa@DecDigit0\endcsname#1{% + \expandafter\endcsname + \ifcase#1 % + 00% + \else + 19% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Add}, \op{Sub}} +% +% \begin{macro}{\intcalcAdd} +% \begin{macrocode} +\def\intcalcAdd#1#2{% + \number + \expandafter\InCa@AddSwitch + \number\number#1\expandafter!% + \number#2! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\intcalcSub} +% \begin{macrocode} +\def\intcalcSub#1#2{% + \number + \expandafter\InCa@AddSwitch + \number\number#1\expandafter!% + \number-\number#2! % +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@AddSwitch} +% Decision table for \cs{InCa@AddSwitch}. +% The sign of negative numbers can be removed +% by a simple \cs{@gobble} +% instead of the more expensive |\number-|. +% \begin{quote} +% \begin{tabular}[t]{@{}|l|l|l|l|l|@{}} +% \hline +% $x<0$ & $y<0$ & $ x< y$ & $-$ & $\opAdd(-x,-y)$\\ +% \cline{3-3}\cline{5-5} +% & & else & & $\opAdd(-y,-x)$\\ +% \cline{2-5} +% & else & $-x> y$ & $-$ & $\opSub(-x, y)$\\ +% \cline{3-5} +% & & else & $+$ & $\opSub( y,-x)$\\ +% \hline +% else & $y<0$ & $ x>-y$ & $+$ & $\opSub( x,-y)$\\ +% \cline{3-5} +% & & else & $-$ & $\opSub(-y, x)$\\ +% \cline{2-5} +% & else & $ x> y$ & $+$ & $\opAdd( x, y)$\\ +% \cline{3-3}\cline{5-5} +% & & else & & $\opAdd( y, x)$\\ +% \hline +% \end{tabular} +% \end{quote} +% \begin{macrocode} +\def\InCa@AddSwitch#1!#2!{% + \ifnum#1<\z@ + \ifnum#2<\z@ + -% + \ifnum#1<#2 % + \expandafter\InCa@Add\number-#1\expandafter!% + \@gobble#2!% + \else + \expandafter\InCa@Add\number-#2\expandafter!% + \@gobble#1!% + \fi + \else + \ifnum-#1>#2 % + -% + \expandafter\InCa@Sub\@gobble#1!#2!% + \else + \expandafter\InCa@Sub\number#2\expandafter!% + \@gobble#1!% + \fi + \fi + \else + \ifnum#2<\z@ + \ifnum#1>-#2 % + \expandafter\InCa@Sub\number#1\expandafter!% + \@gobble#2!% + \else + -% + \expandafter\InCa@Sub\@gobble#2!#1!% + \fi + \else + \ifnum#1>#2 % + \InCa@Add#1!#2!% + \else + \InCa@Add#2!#1!% + \fi + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcAdd} +% \begin{macrocode} +\def\IntCalcAdd#1!#2!{% + \number\InCa@Add#1!#2! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcSub} +% \begin{macrocode} +\def\IntCalcSub#1!#2!{% + \number\InCa@Sub#1!#2! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Space} +% \begin{macrocode} +\begingroup + \def\x#1{\endgroup + \let\InCa@Space= #1% + }% +\x{ } +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Add} +% \begin{macrocode} +\def\InCa@Add#1!#2!{% + \ifcase#2 % + #1% + \else + \InCa@@Add#1!#2!000000000\InCa@Space + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Sub} +% \begin{macrocode} +\def\InCa@Sub#1!#2!{% + \ifnum#1=#2 % + 0% + \else + \InCa@@Sub#1!#2!000000000\InCa@Space + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@@Add} +% \begin{macrocode} +\def\InCa@@Add#1!#2#3!{% + \ifx\InCa@Empty#3\InCa@Empty + \@ReturnAfterElseFi{% + \InCa@@@Add!!#1!#2% + }% + \else + \@ReturnAfterFi{% + \InCa@@Add#1!#3!#2% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@@Sub} +% \begin{macrocode} +\def\InCa@@Sub#1!#2#3!{% + \ifx\InCa@Empty#3\InCa@Empty + \@ReturnAfterElseFi{% + \InCa@@@Sub!!#1!#2% + }% + \else + \@ReturnAfterFi{% + \InCa@@Sub#1!#3!#2% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@@@Add} +% \begin{macrocode} +\def\InCa@@@Add#1!#2!#3#4!#5{% + \ifx\InCa@Empty#4\InCa@Empty + \csname InCa@Empty% + \@ReturnAfterElseFi{% + \InCa@ProcessAdd#1#3!#5#2% + }% + \else + \@ReturnAfterFi{% + \InCa@@@Add#1#3!#5#2!#4!% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@@@Sub} +% \begin{macrocode} +\def\InCa@@@Sub#1!#2!#3#4!#5{% + \ifx\InCa@Empty#4\InCa@Empty + \csname @gobble% + \@ReturnAfterElseFi{% + \InCa@ProcessSub#1#3!#5#2% + }% + \else + \@ReturnAfterFi{% + \InCa@@@Sub#1#3!#5#2!#4!% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@ProcessAdd} +% \begin{macrocode} +\def\InCa@ProcessAdd#1#2!#3#4{% + \ifx\InCa@Empty#2\InCa@Empty + \csname InCa@AddDigit#1\endcsname#3% + \romannumeral0#4% + \else + \csname InCa@AddDigit#1\csname InCa@DigitCarry#3% + \@ReturnAfterFi{% + \InCa@ProcessAdd#2!#4% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@ProcessSub} +% \begin{macrocode} +\def\InCa@ProcessSub#1#2!#3#4{% + \ifx\InCa@Empty#2\InCa@Empty + \csname InCa@SubDigit#1\endcsname#3% + \romannumeral0#4% + \else + \csname InCa@SubDigit#1\csname InCa@DigitCarry#3% + \@ReturnAfterFi{% + \InCa@ProcessSub#2!#4% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@DigitCarry[0-9]} +% \begin{macrocode} +\def\InCa@Temp#1#2{% + \expandafter\def\csname InCa@DigitCarry#1\endcsname##1{% + \ifcase##1 % + \endcsname#1% + \else + \endcsname#2% + \fi + }% +} +\InCa@Temp 01 +\InCa@Temp 12 +\InCa@Temp 23 +\InCa@Temp 34 +\InCa@Temp 45 +\InCa@Temp 56 +\InCa@Temp 67 +\InCa@Temp 78 +\InCa@Temp 89 +\InCa@Temp 9{{10}} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@AddDigit0} +% \begin{macrocode} +\expandafter\def\csname InCa@AddDigit0\endcsname#1{% + \ifnum#1>9 % + \endcsname10% + \else + \endcsname0#1% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@AddDigit[1-9]} +% \begin{macrocode} +\def\InCa@Temp#1#2#3{% + \expandafter\def\csname InCa@AddDigit#1\endcsname##1{% + \ifnum##1>#2 % + \endcsname 1% + \else + \endcsname 0% + \fi + \ifcase##1 #1% 0 + #3% + \else #1% 10 + \fi + }% +} +\InCa@Temp 18{% + \or 2% 1 + \or 3% 2 + \or 4% 3 + \or 5% 4 + \or 6% 5 + \or 7% 6 + \or 8% 7 + \or 9% 8 + \or 0% 9 +}% +\InCa@Temp 27{% + \or 3% 1 + \or 4% 2 + \or 5% 3 + \or 6% 4 + \or 7% 5 + \or 8% 6 + \or 9% 7 + \or 0% 8 + \or 1% 9 +}% +\InCa@Temp 36{% + \or 4% 1 + \or 5% 2 + \or 6% 3 + \or 7% 4 + \or 8% 5 + \or 9% 6 + \or 0% 7 + \or 1% 8 + \or 2% 9 +}% +\InCa@Temp 45{% + \or 5% 1 + \or 6% 2 + \or 7% 3 + \or 8% 4 + \or 9% 5 + \or 0% 6 + \or 1% 7 + \or 2% 8 + \or 3% 9 +}% +\InCa@Temp 54{% + \or 6% 1 + \or 7% 2 + \or 8% 3 + \or 9% 4 + \or 0% 5 + \or 1% 6 + \or 2% 7 + \or 3% 8 + \or 4% 9 +}% +\InCa@Temp 63{% + \or 7% 1 + \or 8% 2 + \or 9% 3 + \or 0% 4 + \or 1% 5 + \or 2% 6 + \or 3% 7 + \or 4% 8 + \or 5% 9 +}% +\InCa@Temp 72{% + \or 8% 1 + \or 9% 2 + \or 0% 3 + \or 1% 4 + \or 2% 5 + \or 3% 6 + \or 4% 7 + \or 5% 8 + \or 6% 9 +}% +\InCa@Temp 81{% + \or 9% 1 + \or 0% 2 + \or 1% 3 + \or 2% 4 + \or 3% 5 + \or 4% 6 + \or 5% 7 + \or 6% 8 + \or 7% 9 +}% +\InCa@Temp 90{% + \or 0% 1 + \or 1% 2 + \or 2% 3 + \or 3% 4 + \or 4% 5 + \or 5% 6 + \or 6% 7 + \or 7% 8 + \or 8% 9 +}% +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@SubDigit[0-9]} +% \begin{macrocode} +\def\InCa@Temp#1#2{% + \expandafter\def\csname InCa@SubDigit#1\endcsname##1{% + \ifnum##1>#1 % + \endcsname 1% + \else + \endcsname 0% + \fi + \ifcase##1 #1% 0 + #2% + \else #1% 10 + \fi + }% +} +\InCa@Temp 0{% + \or 9% 1 + \or 8% 2 + \or 7% 3 + \or 6% 4 + \or 5% 5 + \or 4% 6 + \or 3% 7 + \or 2% 8 + \or 1% 9 +} +\InCa@Temp 1{% + \or 0% 1 + \or 9% 2 + \or 8% 3 + \or 7% 4 + \or 6% 5 + \or 5% 6 + \or 4% 7 + \or 3% 8 + \or 2% 9 +} +\InCa@Temp 2{% + \or 1% 1 + \or 0% 2 + \or 9% 3 + \or 8% 4 + \or 7% 5 + \or 6% 6 + \or 5% 7 + \or 4% 8 + \or 3% 9 +} +\InCa@Temp 3{% + \or 2% 1 + \or 1% 2 + \or 0% 3 + \or 9% 4 + \or 8% 5 + \or 7% 6 + \or 6% 7 + \or 5% 8 + \or 4% 9 +} +\InCa@Temp 4{% + \or 3% 1 + \or 2% 2 + \or 1% 3 + \or 0% 4 + \or 9% 5 + \or 8% 6 + \or 7% 7 + \or 6% 8 + \or 5% 9 +} +\InCa@Temp 5{% + \or 4% 1 + \or 3% 2 + \or 2% 3 + \or 1% 4 + \or 0% 5 + \or 9% 6 + \or 8% 7 + \or 7% 8 + \or 6% 9 +} +\InCa@Temp 6{% + \or 5% 1 + \or 4% 2 + \or 3% 3 + \or 2% 4 + \or 1% 5 + \or 0% 6 + \or 9% 7 + \or 8% 8 + \or 7% 9 +} +\InCa@Temp 7{% + \or 6% 1 + \or 5% 2 + \or 4% 3 + \or 3% 4 + \or 2% 5 + \or 1% 6 + \or 0% 7 + \or 9% 8 + \or 8% 9 +} +\InCa@Temp 8{% + \or 7% 1 + \or 6% 2 + \or 5% 3 + \or 4% 4 + \or 3% 5 + \or 2% 6 + \or 1% 7 + \or 0% 8 + \or 9% 9 +} +\InCa@Temp 9{% + \or 8% 1 + \or 7% 2 + \or 6% 3 + \or 5% 4 + \or 4% 5 + \or 3% 6 + \or 2% 7 + \or 1% 8 + \or 0% 9 +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Shl}, \op{Shr}} +% +% \begin{macro}{\intcalcShl} +% \begin{macrocode} +\def\intcalcShl#1{% + \number\expandafter\InCa@ShlSwitch\number#1! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@ShlSwitch} +% \begin{macrocode} +\def\InCa@ShlSwitch#1#2!{% + \ifx#1-% + -\csname InCa@Empty% + \InCa@Shl#2!% + \else + \csname InCa@Empty% + \InCa@Shl#1#2!% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcShl} +% \begin{macrocode} +\def\IntCalcShl#1!{% + \number + \csname InCa@Empty% + \InCa@Shl#1! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCal@ShlDigit} +% \begin{macrocode} +\def\InCa@Shl#1#2{% + \ifx#2!% + \csname InCa@ShlDigit#1\endcsname0% + \else + \csname InCa@ShlDigit#1% + \@ReturnAfterFi{% + \InCa@Shl#2% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@ShlDigit0} +% \begin{macrocode} +\expandafter\def\csname InCa@ShlDigit0\endcsname{% + \endcsname0% +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@ShlDigit[1-9]} +% \begin{macrocode} +\def\InCa@Temp#1#2#3#4#5{% + \expandafter\def\csname InCa@ShlDigit#1\endcsname##1{% + \expandafter\endcsname + \ifcase##1 % + #2#3% + \else + #4#5% + \fi + }% +} +\InCa@Temp 10203 +\InCa@Temp 20405 +\InCa@Temp 30607 +\InCa@Temp 40809 +\InCa@Temp 51011 +\InCa@Temp 61213 +\InCa@Temp 71415 +\InCa@Temp 81617 +\InCa@Temp 91819 +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcShr} +% \begin{macrocode} +\def\intcalcShr#1{% + \number\expandafter\InCa@ShrSwitch\number#1! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@ShrSwitch} +% \begin{macrocode} +\def\InCa@ShrSwitch#1#2!{% + \ifx#1-% + -\InCa@Shr#2!% + \else + \InCa@Shr#1#2!% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcShr} +% \begin{macrocode} +\def\IntCalcShr#1!{% + \number\InCa@Shr#1! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Shr} +% \begin{macrocode} +\def\InCa@Shr#1#2{% + \InCa@ShrDigit#1!% + \ifx#2!% + \else + \@ReturnAfterFi{% + \ifodd#1 % + \@ReturnAfterElseFi{% + \InCa@Shr{1#2}% + }% + \else + \expandafter\InCa@Shr\expandafter#2% + \fi + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macrocode} +\def\InCa@ShrDigit#1!{% + \ifcase#1 0% 0 + \or 0% 1 + \or 1% 2 + \or 1% 3 + \or 2% 4 + \or 2% 5 + \or 3% 6 + \or 3% 7 + \or 4% 8 + \or 4% 9 + \or 5% 10 + \or 5% 11 + \or 6% 12 + \or 6% 13 + \or 7% 14 + \or 7% 15 + \or 8% 16 + \or 8% 17 + \or 9% 18 + \or 9% 19 + \fi +} +% \end{macrocode} +% +% \subsubsection{\cs{InCa@Tim}} +% +% \begin{macro}{\InCa@Tim} +% Macro \cs{InCa@Tim} implements +% ``Number \emph{tim}es digit''. +% \begin{macrocode} +\def\InCa@Temp#1{% + \def\InCa@Tim##1##2{% + \number + \ifcase##2 % 0 + 0% + \or % 1 + ##1% + \else % 2-9 + \csname InCa@Empty% + \InCa@ProcessTim##2##1!% + \fi + #1% + }% +} +\InCa@Temp{ } +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@ProcessTim} +% \begin{macrocode} +\def\InCa@ProcessTim#1#2#3{% + \ifx#3!% + \csname InCa@TimDigit#2\endcsname#10% + \else + \csname InCa@TimDigit#2\csname InCa@Param#1% + \@ReturnAfterFi{% + \InCa@ProcessTim#1#3% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Param[0-9]} +% \begin{macrocode} +\def\InCa@Temp#1{% + \expandafter\def\csname InCa@Param#1\endcsname{% + \endcsname#1% + }% +} +\InCa@Temp 0% +\InCa@Temp 1% +\InCa@Temp 2% +\InCa@Temp 3% +\InCa@Temp 4% +\InCa@Temp 5% +\InCa@Temp 6% +\InCa@Temp 7% +\InCa@Temp 8% +\InCa@Temp 9% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@TimDigit0} +% \begin{macrocode} +\expandafter\def\csname InCa@TimDigit0\endcsname#1#2{% + \endcsname + 0#2% +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@TimDigit1} +% \begin{macrocode} +\expandafter\def\csname InCa@TimDigit1\endcsname#1#2{% + \ifcase#2 % + \endcsname 0#1% + \else + \csname InCa@AddDigit#1\endcsname #2% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@TimDigit[2-9]} +% \begin{macrocode} +\def\InCa@Temp#1#2{% + \expandafter\def\csname InCa@TimDigit#1\endcsname##1{% + \expandafter\InCa@TimDigitCarry + \number + \ifcase##1 0% 0 + #2% + \fi + !% + }% +} +\InCa@Temp 2{% + \or 2% 1 + \or 4% 2 + \or 6% 3 + \or 8% 4 + \or 10% 5 + \or 12% 6 + \or 14% 7 + \or 16% 8 + \or 18% 9 +} +\InCa@Temp 3{% + \or 3% 1 + \or 6% 2 + \or 9% 3 + \or 12% 4 + \or 15% 5 + \or 18% 6 + \or 21% 7 + \or 24% 8 + \or 27% 9 +} +\InCa@Temp 4{% + \or 4% 1 + \or 8% 2 + \or 12% 3 + \or 16% 4 + \or 20% 5 + \or 24% 6 + \or 28% 7 + \or 32% 8 + \or 36% 9 +} +\InCa@Temp 5{% + \or 5% 1 + \or 10% 2 + \or 15% 3 + \or 20% 4 + \or 25% 5 + \or 30% 6 + \or 35% 7 + \or 40% 8 + \or 45% 9 +} +\InCa@Temp 6{% + \or 6% 1 + \or 12% 2 + \or 18% 3 + \or 24% 4 + \or 30% 5 + \or 36% 6 + \or 42% 7 + \or 48% 8 + \or 54% 9 +} +\InCa@Temp 7{% + \or 7% 1 + \or 14% 2 + \or 21% 3 + \or 28% 4 + \or 35% 5 + \or 42% 6 + \or 49% 7 + \or 56% 8 + \or 63% 9 +} +\InCa@Temp 8{% + \or 8% 1 + \or 16% 2 + \or 24% 3 + \or 32% 4 + \or 40% 5 + \or 48% 6 + \or 56% 7 + \or 64% 8 + \or 72% 9 +} +\InCa@Temp 9{% + \or 9% 1 + \or 18% 2 + \or 27% 3 + \or 36% 4 + \or 45% 5 + \or 54% 6 + \or 63% 7 + \or 72% 8 + \or 81% 9 +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@TimDigitCarry} +% \begin{macrocode} +\def\InCa@TimDigitCarry#1!{% + \ifnum#1<10 % + \csname InCa@AddDigit#1\expandafter\endcsname + \else + \@ReturnAfterFi{% + \InCa@@TimDigitCarry#1!% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@@TimDigitCarry} +% \begin{macrocode} +\def\InCa@@TimDigitCarry#1#2!#3{% + \csname InCa@DigitCarry#1% + \csname InCa@AddDigit#2\endcsname #3% +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Mul}} +% +% \begin{macro}{\intcalcMul} +% \begin{macrocode} +\def\intcalcMul#1#2{% + \number + \expandafter\InCa@MulSwitch + \number\number#1\expandafter!% + \number#2! % +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\InCa@MulSwitch} +% Decision table for \cs{InCa@MulSwitch}. +% \begin{quote} +% \begin{tabular}[t]{@{}|l|l|l|l|l|@{}} +% \hline +% $x<0$ & $y<0$ & $ x< y$ & $+$ & $\opMul(-x,-y)$\\ +% \cline{3-3}\cline{5-5} +% & & else & & $\opMul(-y,-x)$\\ +% \cline{2-5} +% & else & $-x> y$ & $-$ & $\opMul(-x, y)$\\ +% \cline{3-3}\cline{5-5} +% & & else & & $\opMul( y,-x)$\\ +% \hline +% else & $y<0$ & $ x>-y$ & $-$ & $\opMul( x,-y)$\\ +% \cline{3-3}\cline{5-5} +% & & else & & $\opMul(-y, x)$\\ +% \cline{2-5} +% & else & $ x> y$ & $+$ & $\opMul( x, y)$\\ +% \cline{3-3}\cline{5-5} +% & & else & & $\opMul( y, x)$\\ +% \hline +% \end{tabular} +% \end{quote} +% \begin{macrocode} +\def\InCa@MulSwitch#1!#2!{% + \ifnum#1<\z@ + \ifnum#2<\z@ + \ifnum#1<#2 % + \expandafter\InCa@Mul\number-#1\expandafter!% + \@gobble#2!% + \else + \expandafter\InCa@Mul\number-#2\expandafter!% + \@gobble#1!% + \fi + \else + -% + \ifnum-#1>#2 % + \expandafter\InCa@Mul\@gobble#1!#2!% + \else + \expandafter\InCa@Mul\number#2\expandafter!% + \@gobble#1!% + \fi + \fi + \else + \ifnum#2<\z@ + -% + \ifnum#1>-#2 % + \expandafter\InCa@Mul\number#1\expandafter!% + \@gobble#2!% + \else + \expandafter\InCa@Mul\@gobble#2!#1!% + \fi + \else + \ifnum#1>#2 % + \InCa@Mul#1!#2!% + \else + \InCa@Mul#2!#1!% + \fi + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcMul} +% \begin{macrocode} +\def\IntCalcMul#1!#2!{% + \number\InCa@Mul#1!#2! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Mul} +% \begin{macrocode} +\def\InCa@Mul#1!#2!{% + \ifcase#2 % + 0% + \or + #1% + \or + \csname InCa@Empty% + \expandafter\InCa@Shl#1!% + \else + \ifnum#2<10 % + \InCa@Tim{#1}#2% + \else + \InCa@ProcessMul!#2!#1!% + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Mul} +% \begin{macrocode} +\def\InCa@ProcessMul#1!#2#3!#4!{% + \ifx\InCa@Empty#3\InCa@Empty + \expandafter\InCa@Add\number + #10\expandafter\expandafter\expandafter!% + \InCa@Tim{#4}#2!% + \else + \ifx\InCa@Empty#1\InCa@Empty + \expandafter\expandafter\expandafter\InCa@ProcessMul + \InCa@Tim{#4}#2!% + #3!#4!% + \else + \expandafter\InCa@ProcessMul\number + \expandafter\InCa@Add\number% + #10\expandafter\expandafter\expandafter!% + \InCa@Tim{#4}#2!!% + #3!#4!% + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Sqr}, \op{Fac}} +% +% \begin{macro}{\intcalcSqr} +% \begin{macrocode} +\def\intcalcSqr#1{% + \number\expandafter\InCa@Sqr\number#1! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Sqr} +% \begin{macrocode} +\def\InCa@Sqr#1#2!{% + \ifx#1-% + \InCa@Mul#2!#2!% + \else + \InCa@Mul#1#2!#1#2!% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \begin{macro}{\intcalcFac} +% \begin{macrocode} +\def\intcalcFac#1{% + \number\expandafter\InCa@Fac\number#1! % +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Pow}} +% +% \begin{macro}{\intcalcPow} +% \begin{macrocode} +\def\intcalcPow#1#2{% + \number\expandafter\InCa@Pow + \number\number#1\expandafter!% + \number#2! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Pow} +% \begin{macrocode} +\def\InCa@Pow#1#2!#3#4!{% + \ifcase#3#4 % power = 0 + 1% + \or % power = 1 + #1#2% + \or % power = 2 + \ifx#1-% + \InCa@Mul#2!#2!% + \else + \InCa@Mul#1#2!#1#2!% + \fi + \else + \ifcase#1#2 % basis = 0, power <> 0 + 0% + \ifx#3-% power < 0 + 0\IntCalcError:DivisionByZero% + \fi + \or + 1% basis = 1 + \else + \ifnum#1#2=\m@ne % basis = -1 + \ifodd#3#4 % + -% + \fi + 1% + \else % |basis| > 1 + \ifx#3-% power < 0 + 0% + \else % power > 2 + \ifx#1-% basis < 0 + \ifodd#3#4 % + -% + \fi + \InCa@PowRec#2!#3#4!1!% + \else + \InCa@PowRec#1#2!#3#4!1!% + \fi + \fi + \fi + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@PowRec} +%\begin{quote} +%\begin{verbatim} +%Pow(b, p) { +% PowRec(b, p, 1) +%} +%PowRec(b, p, r) { +% if p == 1 then +% return r +% else +% ifodd p then +% return PowRec(b*b, p div 2, r*b) % p div 2 = (p-1)/2 +% else +% return PowRec(b*b, p div 2, r) +% fi +% fi +%} +%\end{verbatim} +%\end{quote} +% \begin{macrocode} +\def\InCa@PowRec#1!#2!#3!{% + \ifnum#2=\@ne + \ifnum#1>#3 % + \InCa@Mul#1!#3!% + \else + \InCa@Mul#3!#1!% + \fi + \else + \expandafter\InCa@PowRec + \number\InCa@Mul#1!#1!\expandafter!% + \number\intcalcShr{#2}\expandafter!% + \number + \ifodd#2 % + \ifnum#1>#3 % + \InCa@Mul#1!#3!% + \else + \InCa@Mul#3!#1!% + \fi + \else + #3% + \fi + \expandafter!% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Div}} +% +% \begin{macro}{\intcalcDiv} +% \begin{macrocode} +\def\intcalcDiv#1#2{% + \number\expandafter\InCa@Div + \number\number#1\expandafter!% + \number#2! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@Div} +% \begin{macrocode} +\def\InCa@Div#1!#2!{% + \ifcase#2 % + 0\IntCalcError:DivisionByZero% + \else + \ifcase#1 % + 0% + \else + \expandafter\InCa@DivSwitch + \number#1\expandafter!% + \number#2!% + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcDiv} +% \begin{macrocode} +\def\InCa@Temp#1{% + \def\IntCalcDiv##1!##2!{% + \number + \ifcase##2 % + 0\IntCalcError:DivisionByZero% + \else + \ifcase##1 % + 0% + \else + \InCa@@Div##1!##2!% + \fi + \fi + #1% + }% +} +\InCa@Temp{ }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@DivSwitch} +% Decision table for \cs{InCa@DivSwitch}. +% \begin{quote} +% \begin{tabular}[t]{@{}|l|l|l|l|@{}} +% \hline +% $x<0$ & $y<0$ & $+$ & $\opDiv(-x,-y)$\\ +% \cline{2-4} +% & else & $-$ & $\opDiv(-x, y)$\\ +% \hline +% else & $y<0$ & $-$ & $\opDiv( x,-y)$\\ +% \cline{2-4} +% & else & $+$ & $\opDiv( x, y)$\\ +% \hline +% \end{tabular} +% \end{quote} +% \begin{macrocode} +\def\InCa@DivSwitch#1!#2!{% + \ifnum#1<\z@ + \ifnum#2<\z@ + \expandafter\InCa@@Div\number-#1\expandafter!% + \@gobble#2!% + \else + -% + \expandafter\InCa@@Div\@gobble#1!#2!% + \fi + \else + \ifnum#2<\z@ + -% + \expandafter\InCa@@Div\number#1\expandafter!% + \@gobble#2!% + \else + \InCa@@Div#1!#2!% + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@@Div} +% \begin{macrocode} +\def\InCa@@Div#1!#2!{% + \ifnum#1>#2 % + \ifcase#2 % 0 already catched +? \IntCalcError:ThisCannotHappen% + \or % 1 + #1% + \or % 2 + \InCa@Shr#1!% + \else + \InCa@DivStart!#1!#2!#2!% + \fi + \else + \ifnum#1=#2 % + 1% + \else + 0% + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@DivStart} +% \begin{macrocode} +\def\InCa@DivStart#1!#2#3!#4#5{% + \ifx#5!% + \@ReturnAfterElseFi{% + \InCa@DivStartI{#1#2}#3=!% + }% + \else + \@ReturnAfterFi{% + \InCa@DivStart{#1#2}!#3!#5% + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@StartI} +% \begin{macrocode} +\def\InCa@DivStartI#1!#2!{% + \expandafter\InCa@DivStartII + \number#2\expandafter\expandafter\expandafter!% + \intcalcShl{#2}!% + #1!% +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@StartII} +% \begin{macrocode} +\def\InCa@DivStartII#1!#2!{% + \expandafter\InCa@DivStartIII + \number#1\expandafter!% + \number#2\expandafter\expandafter\expandafter!% + \intcalcShl{#2}!% +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@StartIII} +% \begin{macrocode} +\def\InCa@DivStartIII#1!#2!#3!{% + \expandafter\InCa@DivStartIV + \number#1\expandafter!% + \number#2\expandafter!% + \number#3\expandafter!% + \number\InCa@Add#3!#2!\expandafter\expandafter\expandafter!% + \intcalcShl{#3}!% +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@StartIV} +% \begin{macrocode} +\def\InCa@DivStartIV#1!#2!#3!#4!#5!#6!{% + \InCa@ProcessDiv#6!#1!#2!#3!#4!#5!/% +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@ProcessDiv} +% \begin{macrocode} +\def\InCa@ProcessDiv#1#2#3!#4!#5!#6!#7!#8!#9/{% + #9% + \ifnum#1<#4 % 0 + 0% + \ifx#2=% + \else + \InCa@ProcessDiv{#1#2}#3!#4!#5!#6!#7!#8!% + \fi + \else % 1-9 + \ifnum#1<#5 % 1 + 1% + \ifx#2=% + \else + \expandafter\InCa@ProcessDiv\expandafter{% + \number\InCa@Sub#1!#4!% + #2% + }#3!#4!#5!#6!#7!#8!% + \fi + \else % 2-9 + \ifnum#1<#7 % 2 3 4 5 + \ifnum#1<#6 % 2 3 + \@ReturnAfterElseFi{% + \expandafter\InCa@@ProcessDiv + \number\InCa@Sub#1!#5!!% + 23% + }% + \else % 4 5 + \@ReturnAfterFi{% + \expandafter\InCa@@ProcessDiv + \number\InCa@Sub#1!#6!!% + 45% + }% + \fi + #2#3!#4!#5!#6!#7!#8!% + \else % 6 7 8 9 + \ifnum#1<#8 % 6 7 + \@ReturnAfterElseFi{% + \expandafter\InCa@@ProcessDiv + \number\InCa@Sub#1!#7!!% + 67% + }% + \else % 8 9 + \@ReturnAfterFi{% + \expandafter\InCa@@ProcessDiv + \number\InCa@Sub#1!#8!!% + 89% + }% + \fi + #2#3!#4!#5!#6!#7!#8!% + \fi + \fi + \fi + \ifx#2=% + \expandafter\@gobble + \fi + /% +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@@ProcessDiv} +% \begin{macrocode} +\def\InCa@@ProcessDiv#1!#2#3#4#5!#6!{% + \ifnum#1<#6 % + #2% + \@ReturnAfterElseFi{% + \ifx#4=% + \expandafter\InCa@CleanupIV + \else + \@ReturnAfterFi{% + \InCa@ProcessDiv{#1#4}#5!#6!% + }% + \fi + }% + \else + #3% + \@ReturnAfterFi{% + \ifx#4=% + \expandafter\InCa@CleanupIV + \else + \@ReturnAfterFi{% + \expandafter\InCa@ProcessDiv\expandafter{% + \number\InCa@Sub#1!#6! % + #4% + }#5!#6!% + }% + \fi + }% + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@CleanupIV} +% \begin{macrocode} +\def\InCa@CleanupIV#1!#2!#3!#4!{} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{\op{Mod}} +% +% \begin{macro}{\intcalcMod} +% \begin{macrocode} +\def\intcalcMod#1#2{% + \number\expandafter\InCa@Mod + \number\number#1\expandafter!% + \number#2! % +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\intcalc@Mod} +% Pseudocode/decision table for \cs{intcalc@Mod}. +% \begin{quote} +% \begin{tabular}{@{}lll@{}} +% if & $y=0$ & DivisionByZero\\ +% elsif & $y<0$ & $-\opMod(-x,-y)$\\ +% elsif & $x=0$ & 0\\ +% elsif & $y=1$ & 0\\ +% elsif & $y=2$ & $\opOdd(x)\mathbin{?}1\mathbin{:}0$\\ +% elsif & $x<0$ & +% $z\leftarrow x-(x/y)*y;\quad (z<0)\mathbin{?}z+y\mathbin{:}z$\\ +% else & & $x-(x/y)*y$\\ +% \\ +% \end{tabular} +% \end{quote} +% \begin{macrocode} +\def\InCa@Mod#1!#2!{% + \ifcase#2 % + 0\IntCalcError:DivisionByZero% + \else + \ifnum#2<\z@ + -% + \expandafter\InCa@Mod + \number-#1\expandafter!% + \number-#2!% + \else + \ifcase#1 % + 0% + \else + \ifcase#2 % 0 already catched +? \IntCalcError:ThisCannotHappen% + \or % 1 + 0% + \or % 2 + \ifodd#1 1\else 0\fi + \else + \ifnum#1<\z@ + \expandafter\InCa@ModShift + \number-% + \expandafter\InCa@Sub + \number\@gobble#1\expandafter!% + \number\intcalcMul{#2}{% + \expandafter\InCa@Div\@gobble#1!#2!% + }!% + !#2!% + \else + \expandafter\InCa@Sub\number#1\expandafter!% + \number\intcalcMul{#2}{\InCa@Div#1!#2!}!% + \fi + \fi + \fi + \fi + \fi +} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\IntCalcMod} +% \begin{macrocode} +\def\InCa@Temp#1{% + \def\IntCalcMod##1!##2!{% + \number + \ifcase##2 % + 0\IntCalcError:DivisionByZero% + \else + \ifcase##1 % + 0% + \else + \ifcase##2 % 0 already catched +? \IntCalcError:ThisCannotHappen + \or % 1 + 0% + \or % 2 + \ifodd ##1 1\else 0\fi + \else + \expandafter\InCa@Sub\number##1\expandafter!% + \number\intcalcMul{##2}{\InCa@Div##1!##2!}!% + \fi + \fi + \fi + #1% + }% +} +\InCa@Temp{ }% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\InCa@ModShift} +% \begin{macrocode} +\def\InCa@ModShift#1!#2!{% + \ifnum#1<\z@ + \expandafter\InCa@Sub\number#2\expandafter!% + \@gobble#1!% + \else + #1% + \fi +} +% \end{macrocode} +% \end{macro} +% +% \subsubsection{Help macros} +% +% \begin{macro}{\InCa@Empty} +% \begin{macrocode} +\def\InCa@Empty{} +% \end{macrocode} +% \end{macro} +% \begin{macro}{\@gobble} +% \begin{macrocode} +\expandafter\ifx\csname @gobble\endcsname\relax + \long\def\@gobble#1{}% +\fi +% \end{macrocode} +% \end{macro} +% \begin{macro}{\@ReturnAfterFi} +% \begin{macrocode} +\long\def\@ReturnAfterFi#1\fi{\fi#1}% +% \end{macrocode} +% \end{macro} +% \begin{macro}{\@ReturnAfterElseFi} +% \begin{macrocode} +\long\def\@ReturnAfterElseFi#1\else#2\fi{\fi#1}% +% \end{macrocode} +% \end{macro} +% +% \begin{macrocode} +\InCa@AtEnd% +% \end{macrocode} +% +% \begin{macrocode} +% +% \end{macrocode} +%% \section{Installation} +% +% \subsection{Download} +% +% \paragraph{Package.} This package is available on +% CTAN\footnote{\CTANpkg{intcalc}}: +% \begin{description} +% \item[\CTAN{macros/latex/contrib/intcalc/intcalc.dtx}] The source file. +% \item[\CTAN{macros/latex/contrib/intcalc/intcalc.pdf}] Documentation. +% \end{description} +% +% +% \paragraph{Bundle.} All the packages of the bundle `intcalc' +% are also available in a TDS compliant ZIP archive. There +% the packages are already unpacked and the documentation files +% are generated. The files and directories obey the TDS standard. +% \begin{description} +% \item[\CTANinstall{install/macros/latex/contrib/intcalc.tds.zip}] +% \end{description} +% \emph{TDS} refers to the standard ``A Directory Structure +% for \TeX\ Files'' (\CTANpkg{tds}). Directories +% with \xfile{texmf} in their name are usually organized this way. +% +% \subsection{Bundle installation} +% +% \paragraph{Unpacking.} Unpack the \xfile{intcalc.tds.zip} in the +% TDS tree (also known as \xfile{texmf} tree) of your choice. +% Example (linux): +% \begin{quote} +% |unzip intcalc.tds.zip -d ~/texmf| +% \end{quote} +% +% \subsection{Package installation} +% +% \paragraph{Unpacking.} The \xfile{.dtx} file is a self-extracting +% \docstrip\ archive. The files are extracted by running the +% \xfile{.dtx} through \plainTeX: +% \begin{quote} +% \verb|tex intcalc.dtx| +% \end{quote} +% +% \paragraph{TDS.} Now the different files must be moved into +% the different directories in your installation TDS tree +% (also known as \xfile{texmf} tree): +% \begin{quote} +% \def\t{^^A +% \begin{tabular}{@{}>{\ttfamily}l@{ $\rightarrow$ }>{\ttfamily}l@{}} +% intcalc.sty & tex/generic/intcalc/intcalc.sty\\ +% intcalc.pdf & doc/latex/intcalc/intcalc.pdf\\ +% intcalc.dtx & source/latex/intcalc/intcalc.dtx\\ +% \end{tabular}^^A +% }^^A +% \sbox0{\t}^^A +% \ifdim\wd0>\linewidth +% \begingroup +% \advance\linewidth by\leftmargin +% \advance\linewidth by\rightmargin +% \edef\x{\endgroup +% \def\noexpand\lw{\the\linewidth}^^A +% }\x +% \def\lwbox{^^A +% \leavevmode +% \hbox to \linewidth{^^A +% \kern-\leftmargin\relax +% \hss +% \usebox0 +% \hss +% \kern-\rightmargin\relax +% }^^A +% }^^A +% \ifdim\wd0>\lw +% \sbox0{\small\t}^^A +% \ifdim\wd0>\linewidth +% \ifdim\wd0>\lw +% \sbox0{\footnotesize\t}^^A +% \ifdim\wd0>\linewidth +% \ifdim\wd0>\lw +% \sbox0{\scriptsize\t}^^A +% \ifdim\wd0>\linewidth +% \ifdim\wd0>\lw +% \sbox0{\tiny\t}^^A +% \ifdim\wd0>\linewidth +% \lwbox +% \else +% \usebox0 +% \fi +% \else +% \lwbox +% \fi +% \else +% \usebox0 +% \fi +% \else +% \lwbox +% \fi +% \else +% \usebox0 +% \fi +% \else +% \lwbox +% \fi +% \else +% \usebox0 +% \fi +% \else +% \lwbox +% \fi +% \else +% \usebox0 +% \fi +% \end{quote} +% If you have a \xfile{docstrip.cfg} that configures and enables \docstrip's +% TDS installing feature, then some files can already be in the right +% place, see the documentation of \docstrip. +% +% \subsection{Refresh file name databases} +% +% If your \TeX~distribution +% (\TeX\,Live, \mikTeX, \dots) relies on file name databases, you must refresh +% these. For example, \TeX\,Live\ users run \verb|texhash| or +% \verb|mktexlsr|. +% +% \subsection{Some details for the interested} +% +% \paragraph{Unpacking with \LaTeX.} +% The \xfile{.dtx} chooses its action depending on the format: +% \begin{description} +% \item[\plainTeX:] Run \docstrip\ and extract the files. +% \item[\LaTeX:] Generate the documentation. +% \end{description} +% If you insist on using \LaTeX\ for \docstrip\ (really, +% \docstrip\ does not need \LaTeX), then inform the autodetect routine +% about your intention: +% \begin{quote} +% \verb|latex \let\install=y\input{intcalc.dtx}| +% \end{quote} +% Do not forget to quote the argument according to the demands +% of your shell. +% +% \paragraph{Generating the documentation.} +% You can use both the \xfile{.dtx} or the \xfile{.drv} to generate +% the documentation. The process can be configured by the +% configuration file \xfile{ltxdoc.cfg}. For instance, put this +% line into this file, if you want to have A4 as paper format: +% \begin{quote} +% \verb|\PassOptionsToClass{a4paper}{article}| +% \end{quote} +% An example follows how to generate the +% documentation with pdf\LaTeX: +% \begin{quote} +%\begin{verbatim} +%pdflatex intcalc.dtx +%makeindex -s gind.ist intcalc.idx +%pdflatex intcalc.dtx +%makeindex -s gind.ist intcalc.idx +%pdflatex intcalc.dtx +%\end{verbatim} +% \end{quote} +% +% \begin{History} +% \begin{Version}{2007/09/09 v1.0} +% \item +% First version. +% \end{Version} +% \begin{Version}{2007/09/27 v1.1} +% \item +% \cs{intcalcNum} added. +% \item +% \cs{intcalcShl} and \cs{intcalcShr} allow negative numbers. +% The sign is preserved. +% \item +% Reuse \cs{@gobble} instead of own macro \cs{IntCalc@Gobble}. +% \item +% Small fixes. +% \item +% Shorter internal prefix. +% \item +% Some programmer's interface. +% \end{Version} +% \begin{Version}{2016/05/16 v1.2} +% \item +% Documentation updates. +% \end{Version} +% \begin{Version}{2019/12/15 v1.3} +% \item +% Documentation updates. +% \end{Version} +% \end{History} +% +% \PrintIndex +% +% \Finale +\endinput -- cgit v1.2.3