The derivs package^{∗}

Andrew D. Lewis

1998/03/05

1 How to use the derivs macros

The package derivs offers some slick ways to write all those derivative you always write without having to get tedious with \frac, etc. This should be able to handle most derivative typesetting situations you will encounter.

\deriv The basic idea for using the derivs macros can be best seen via an example. If you type

     \deriv[1]{x}{t,s^2}

you get

\frac{d^{3}x}{dtds^{2}} .

The basic idea is simple. The first (non-optional) argument is the numerator (i.e., the thing getting differentiated) and the second (non-optional) argument is a comma separated list of things we are differentiating the numerator with respect to. The use of the optional is illustrated in the example. Since we are differentiating with respect to s twice, but this only appears as one item in the denominator list, we need to kludge and add one to the number of times x is being differentiated (to get a total of three). Empty arguments are allowed. That’s all there is to it!

\derivatzero I also like to use “derivative at zero” quite often. There is a macro for this. If you type

     \derivatzero{f}{x}

you will get

\frac{df}{dx}|_{x=0} .

You can also use an option \derivatzero[r]{numer}{denom} to specify the rth derivative at zero.

To get partial derivatives use \pderiv. Thus \pderiv{}{x^i} will get the tensor analysts basis vector field notation.

Just like with \frac, there are “text” (\tderiv, \tderivatzero, and

\tpderiv) and “display” (\dderiv, \dderivatzero, and \dpderiv) versions.

∗This file has version number v1.1a, last revised 1998/03/05.

2 Problems

These macros will stand up well under “everyday” use, but you can make them break by trying hard enough. I have sometimes had problems with certain denominator strings which I have solved by enclosing them in an extra set of braces {}. Also, if one of your items in the denominator list contains a legitimate comma (that’d be odd), then you’re hosed — use the regular L^{A}TEX macros.

3 Implementation

The implementation is a bit complicated. One has to figure out how to keep track of how many derivative are being used by sucking in one symbol at a time in the denominator list, reacting when a comma is present.

1 ⟨∗package⟩

First the variables we need: \@ADL@denom@ will carry the string which becomes the denominator when we’re finished processing the list, and \@ADL@numderivs@ is the number of items in the denominator list plus the value of the optional argument.

2

 3 \newtoks\@ADL@denom@
 4 \newcount\@ADL@numderivs@\@ADL@numderivs@\z@

\deriv is the first basic command and first processes the optional argument in the “usual” manner — passing to \@ADL@@deriv if the argument is present, otherwise

passing to \@ADL@deriv.
 5 \newcommand\deriv{\@ifnextchar [{\@ADL@@deriv}{\@ADL@deriv}}

Both \@ADL@@deriv and \@ADL@deriv behave basically in the same manner. The internal macro \@ADL@denomcomp cycles through and resets itself and adds one to \@ADL@numderivs@ when it encounters a comma. The purpose of the odd looking \@ADL@over@ is explained below. When the denominator has been resolved, the derivative is typeset and \@ADL@numderivs@ is set to zero, ready for another go.

 6 \def\@ADL@@deriv[#1]#2#3{\@ADL@denom@{{\normalfont\mathupper{d}}}
 7 \@ADL@denomcomp#3\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
 8 \advance\@ADL@numderivs@ by #1
 9 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{{\normalfont\mathupper{d}}#2}
10 \else
11 \def\@ADL@numer@{{\normalfont\mathupper{d}}^{\the\@ADL@numderivs@}#2}\fi
12 \frac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}
13 \newcommand\@ADL@deriv[2]{\@ADL@denom@{{\normalfont\mathupper{d}}}
14 \@ADL@denomcomp#2\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
15 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{{\normalfont\mathupper{d}}#1}
16 \else
17 \def\@ADL@numer@{{\normalfont\mathupper{d}}^{\the\@ADL@numderivs@}#1}\fi
18 \frac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}

Now for the “text” version. There is nothing different here from the standard version except when it comes to typesetting the derivative.

19

20 \newcommand\tderiv{\@ifnextchar [{\@ADL@@tderiv}{\@ADL@tderiv}}
21 \def\@ADL@@tderiv[#1]#2#3{\@ADL@denom@{{\normalfont\mathupper{d}}}
22 \@ADL@denomcomp#3\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
23 \advance\@ADL@numderivs@ by #1
24 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{{\normalfont\mathupper{d}}#2}
25 \else
26 \def\@ADL@numer@{{\normalfont\mathupper{d}}^{\the\@ADL@numderivs@}#2}\fi
27 \tfrac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}
28 \newcommand\@ADL@tderiv[2]{\@ADL@denom@{{\normalfont\mathupper{d}}}
29 \@ADL@denomcomp#2\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
30 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{{\normalfont\mathupper{d}}#1}
31 \else
32 \def\@ADL@numer@{{\normalfont\mathupper{d}}^{\the\@ADL@numderivs@}#1}\fi
33 \tfrac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}

Now for the “display” version. Ditto the above remarks for the “text” version.

34

35 \newcommand\dderiv{\@ifnextchar [{\@ADL@@dderiv}{\@ADL@dderiv}}
36 \def\@ADL@@dderiv[#1]#2#3{\@ADL@denom@{{\normalfont\mathupper{d}}}
37 \@ADL@denomcomp#3\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
38 \advance\@ADL@numderivs@ by #1
39 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{{\normalfont\mathupper{d}}#2}
40 \else
41 \def\@ADL@numer@{{\normalfont\mathupper{d}}^{\the\@ADL@numderivs@}#2}\fi
42 \dfrac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}
43 \newcommand\@ADL@dderiv[2]{\@ADL@denom@{{\normalfont\mathupper{d}}}
44 \@ADL@denomcomp#2\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
45 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{{\normalfont\mathupper{d}}#1}
46 \else
47 \def\@ADL@numer@{{\normalfont\mathupper{d}}^{\the\@ADL@numderivs@}#1}\fi
48 \dfrac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}

OK, here’s the meat in these few lines. The idea here I copied from the enumerate package which is part of the standard tools bundle. The first time around the entry will be the \@ADL@over@ string specified above and this is “gobbled.” Then the next character is processed. If it is a , then \@ADL@sepcomp is called upon to advance the number of derivatives by one and add to the denominator list. If the next character in not a , then it is added to the current denominator element by \@ADL@othercomp. Well, that’s the basic idea.

49

50 \def\@ADL@denomcomp{\futurelet\@ADL@denomtemp\@ADL@denomcomp@}
51 \def\@ADL@denomcomp@{%
52 \ifx ,\@ADL@denomtemp \let\@tempa\@ADL@sepcomp  \else
53 \ifx \@ADL@over@\@ADL@denomtemp \let\@tempa\@gobble    \else
54 \let\@tempa\@ADL@othercomp
55 \fi\fi \@tempa}
56 \def\@ADL@sepcomp#1{\advance\@ADL@numderivs@ by\@ne

57 \@ADL@denom@\expandafter{\the\@ADL@denom@{\normalfont\mathupper{d}}}
58 \@ADL@denomcomp}
59 \def\@ADL@othercomp#1{\@ADL@denom@\expandafter{\the\@ADL@denom@#1}
60 \@ADL@denomcomp}

These are the “derivative at zero” macros which are easy.

61

62 \newcommand\derivatzero{\@ifnextchar[{\@ADL@rderivatzero}{\@ADL@derivatzero}}
63 \def\@ADL@rderivatzero[#1]#2#3{\deriv{^{#1}#2}{{#3^{#1}}}\Big|_{#3=0}}
64 \newcommand\@ADL@derivatzero[2]{\deriv{#1}{#2}\Big|_{#2=0}}
65 \newcommand\tderivatzero{\@ifnextchar[{\@ADL@rtderivatzero}
66 {\@ADL@tderivatzero}}
67 \def\@ADL@rtderivatzero[#1]#2#3{\tderiv{^{#1}#2}{{#3^{#1}}}\big|_{#3=0}}
68 \newcommand\@ADL@tderivatzero[2]{\tderiv{#1}{#2}\big|_{#2=0}}
69 \newcommand\dderivatzero{\@ifnextchar[{\@ADL@rdderivatzero}
70 {\@ADL@dderivatzero}}
71 \def\@ADL@rdderivatzero[#1]#2#3{\dderiv{^{#1}#2}{{#3^{#1}}}\Big|_{#3=0}}
72 \newcommand\@ADL@dderivatzero[2]{\dderiv{#1}{#2}\Big|_{#2=0}}

Now for the \pderiv macro which works exactly like the \deriv macro except for the typesetting.

73

74 \newcommand\pderiv{\@ifnextchar [{\@ADL@@pderiv}{\@ADL@pderiv}}
75 \def\@ADL@@pderiv[#1]#2#3{\@ADL@denom@{\partial}
76 \@ADL@pdenomcomp#3\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
77 \advance\@ADL@numderivs@ by #1
78 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{\partial #2}\else
79 \def\@ADL@numer@{\partial^{\the\@ADL@numderivs@}#2}\fi
80 \frac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}
81 \newcommand\@ADL@pderiv[2]{\@ADL@denom@{\partial}
82 \@ADL@pdenomcomp#2\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
83 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{\partial #1}\else
84 \def\@ADL@numer@{\partial^{\the\@ADL@numderivs@}#1}\fi
85 \frac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}

And the “text” version.

86

87 \newcommand\tpderiv{\@ifnextchar [{\@ADL@@tpderiv}{\@ADL@tpderiv}}
88 \def\@ADL@@tpderiv[#1]#2#3{\@ADL@denom@{\partial}
89 \@ADL@pdenomcomp#3\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
90 \advance\@ADL@numderivs@ by #1
91 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{\partial #2}\else
92 \def\@ADL@numer@{\partial^{\the\@ADL@numderivs@}#2}\fi
93 \tfrac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}
94 \newcommand\@ADL@tpderiv[2]{\@ADL@denom@{\partial}
95 \@ADL@pdenomcomp#2\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
96 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{\partial #1}\else
97 \def\@ADL@numer@{\partial^{\the\@ADL@numderivs@}#1}\fi
98 \tfrac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}

And the “display” version.

100 \newcommand\dpderiv{\@ifnextchar [{\@ADL@@dpderiv}{\@ADL@dpderiv}}
101 \def\@ADL@@dpderiv[#1]#2#3{\@ADL@denom@{\partial}
102 \@ADL@pdenomcomp#3\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
103 \advance\@ADL@numderivs@ by #1
104 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{\partial #2}\else
105 \def\@ADL@numer@{\partial^{\the\@ADL@numderivs@}#2}\fi
106 \dfrac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}
107 \newcommand\@ADL@dpderiv[2]{\@ADL@denom@{\partial}
108 \@ADL@pdenomcomp#2\@ADL@over@ \advance\@ADL@numderivs@ by\@ne
109 \ifnum\@ADL@numderivs@=\@ne\def\@ADL@numer@{\partial #1}\else
110 \def\@ADL@numer@{\partial^{\the\@ADL@numderivs@}#1}\fi
111 \dfrac{\@ADL@numer@}{\the\@ADL@denom@}\@ADL@numderivs@\z@}

These macros do for \pderiv what their counterparts do for \deriv.

112

113 \def\@ADL@pdenomcomp{\futurelet\@ADL@denomtemp\@ADL@pdenomcomp@}
114 \def\@ADL@pdenomcomp@{%
115 \ifx ,\@ADL@denomtemp  \let\@tempa\@ADL@psepcomp  \else
116 \ifx \@ADL@over@\@ADL@denomtemp \let\@tempa\@gobble   \else
117 \let\@tempa\@ADL@pothercomp
118 \fi\fi \@tempa}
119 \def\@ADL@psepcomp#1{\advance\@ADL@numderivs@ by\@ne
120 \@ADL@denom@\expandafter{\the\@ADL@denom@\partial}\@ADL@pdenomcomp}
121 \def\@ADL@pothercomp#1{\@ADL@denom@\expandafter{\the\@ADL@denom@#1}
122 \@ADL@pdenomcomp}

123

Make command for roman font d.

124

125 \let\mathupper\textup

126 ⟨/package⟩