[tex-eplain] optional arguments

Oleg Katsitadze olegkat at gmail.com
Tue Feb 26 06:43:24 CET 2008


On Mon, Feb 25, 2008 at 01:32:46PM +0000, Adam Fenn wrote:
> why the brackets after \cmd at arg{} ?

Just to have the space token after it, to be consistent with the \else
clause.  Without the braces the newline is ignored and is not
converted into a space token.  BTW, your later usage is most probably
wrong, because I doubt you want a space there:

> \let\name=\architect at arg{}

And if you want to be completely confused, the space is ignored here:

>            \sidx{\name, {\it architect}}

Strictly speaking, the space token _is_ there, inside the definition
of \finisharchitect (look it up with \show\finisharchitect), but
silent indexing macros say \ignorespaces at the end, so the space is,
well, ignored.

Now to your problems.

> Firstly, it only typesets the last occurrence of \architect.

That's because you end up writing literal "\name" and "\location" into
the index file, instead of expanding them, so they get expanded at the
time of reading the index file, instead of at the time of writing to
it.  Getting correct expansion is tricky but possible -- it relies on
the fact that \the\toksreg, where \toksreg is a token register,
expands only once ("one level") inside \edef.  See the modified macros
below.  Note that inside \edef you have to prefix macros with
\noexpand, otherwise \edef will expand them and bad things may happen.

> Secondly, it puts them in the wrong alphabetical order and whilst I
> understand why this happens I don't know how to rectify it

I don't understand -- how can the order be wrong if the names are all
the same? :)  But if you mean, relative to other ("non-architect")
entries, then the problem is again with non-expanding \name, because
makeindex sorts the string "\name" instead of what this macro stands
for.

> thirdly it typesets too much when the optional argument isn't
> present.

Again, I don't understand.  But see if the macros below fix your
problems.

> All in all a triumph in the art of macro writing.

Actually, you're doing great :).

Cheers,
Oleg


\makeatletter

\newtoks\arch at name
\newtoks\arch at loc

\def\architect#1{%
  \arch at name={#1}%
  \@getoptionalarg\finisharchitect
}

\def\finisharchitect{%
  \arch at loc=\expandafter{\@optionalarg}%
  \ifx\@optionalarg\empty
    % No optional argument present.
    \expandafter\sidx\expandafter{\the\arch at name}
  \else
    % One was present.
    \edef\temp{architects!\the\arch at name, {\noexpand\it \the\arch at loc}}%
    \expandafter\sidx\expandafter{\temp}%
    \edef\temp{\the\arch at name, {\noexpand\it architect, \the\arch at loc}}%
    \expandafter\sidx\expandafter{\temp}%
  \fi
}

\resetatcatcode


More information about the tex-eplain mailing list