5

I'd like to make a shortcut macro to prefix function names in formulae to decorate them in some way depending on the function type. Using "normal" macros would lead to an abundance of braces and I'm looking for something cleaner.

I was trying to define a macro that would chop everything until the next space (or, if possible, until the next non-letter token), and treat that as argument. Is it possible?

Example (don't focus on the macro body):

\def\f <what goes here?> {\mathop{\mathrm{#1}}}
\def\kw <what goes here?> {\mathop{\color{red} #1}} 
...
Consider the following:
\[
   \kw return \f isBool x \kw or \f isString x
\]

would be equivalent to:

Consider the following:
\[
   \mathop{\color{red} return} 
   \mathop{\mathrm{isBool}} x 
   \mathop{\color{red} or}
   \mathop{\mathrm{isString}} x
\]

And, if possible, such a macro should be able to understand if it's receiving a braced argument so \kw{return} would take return as argument regardless of spaces, so that it can be used like a normal macro for who do not know its special behavior.

Any TeX/LaTeX solution is welcome...

  • Could you clarify if you're using LaTeX or plain: the tags suggest the latter but the text of the question suggests LaTeX. – Joseph Wright Jun 14 '16 at 7:59
  • I use LaTeX so its acceptable, but I think the solution would use \def & co. rather than \newcommand so I put plain. Is it the wrong tag? – gigabytes Jun 14 '16 at 8:03
  • 2
    The plain-tex tag is for questions specific to the plain TeX format, not simply using TeX primitives. I've clarified. – Joseph Wright Jun 14 '16 at 8:10
5

You can grab everything up to the next letter with an approach such as

\long\def\use#1{#1}
\def\grab{\futurelet\nexttoken\grabauxI}
\def\grabauxI{%
  \ifx\nexttoken\sptoken
    \expandafter\grabspace
  \else
    \ifx\nexttoken\bgroup
      \expandafter\expandafter\expandafter\grabgroup
    \else
      \expandafter\expandafter\expandafter\grabstd
    \fi
  \fi
}
\use{\let\sptoken= } %
\expandafter\def\expandafter\grabspace\space{%
  \expandafter\expandafter\expandafter\def
  \expandafter\expandafter\expandafter\grabbed
  \expandafter\expandafter\expandafter{\expandafter\grabbed\space}%
  \grab
}
\long\def\grabgroup#1{%
  \expandafter\def\expandafter\grabbed\expandafter{\grabbed{#1}}%
  \grab
}
\long\def\grabstd#1{%
  \ifcat\noexpand#1a%
    \expandafter\grabend\expandafter#1%
  \else
    \expandafter\def\expandafter\grabbed\expandafter{\grabbed#1}%
    \expandafter\grab
  \fi
}
\long\def\grabend#1{%
  \expandafter\kwaux\expandafter{\grabbed}%
  #1%
}
\def\kw{%
  \def\grabbed{}%
  \grab
}
\long\def\kwaux#1{\showtokens{#1}}

(I've just used \showtokens here as a demo 'payload'). I'm not quite sure if that is what you want as in \kw return this will grab nothing at all! Other answers have already dealt with grabbing up to space.

Note that the above could be generalised such that the grabber part does not need to 'build in' the payload (separating out \kw and the grabber), so it could be applied to several different interface commands.

  • OMG Your answer is impressive but I can barely parse it! – gigabytes Jun 14 '16 at 11:44
  • @gigabytes All standard TeX programming at the 'base' level – Joseph Wright Jun 14 '16 at 12:05
  • Yeah, I see... XD – gigabytes Jun 14 '16 at 12:07
4

Yes: \def\mymacro#1 {your definition}. Please observe the space between #1 and {.

3

Using \def\foo#1 #2 {...} the acts as an delimiter to the arguments.

This is not so easy (even impossible?) with \newcommand.

If a should survive, i.e. Second Third, this must be grouped with a {...} pair, i.e. delimited first.

\documentclass{article}

\def\foo#1 #2 {Specified parameters:

1: \textbf{#1}%

2: \textbf{#2}%

}


\begin{document}
\foo First Second Third

\foo First {Second Third} Fourth

\end{document}

enter image description here

  • Did you hang the first sentence? btw, I didn't know spaces matter in the definition of macro parameters, that's all! But what happens if the macro is called as \foo{first}{second}? Will it complain about the absence of spaces? – gigabytes Jun 14 '16 at 8:05
  • @gigabytes: It will complain, yes – user31729 Jun 14 '16 at 8:08
  • So is it possible to hack something to know if the argument was braced or not? I would like the macro to be usable as a "normal" macro if someone doesn't know its special syntax. – gigabytes Jun 14 '16 at 8:12
  • @gigabytes: Perhaps wrapping it in a command with moving arguments, I'll have to check this – user31729 Jun 14 '16 at 8:13

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.