
Я хочу использовать @ifstar
для определения команды, чья не-звездочная версия сохраняет значение в переменной, а чья звездочная версия считывает значение из переменной. Я попробовал следующее. Это не выдает ошибку, но и не выводит значение.
\def\sndname#1{\@ifstar\@sndname{\def\@sndname{#1}}}
\sndname{Hello U2}
\sndname*
Я знаю, что могу использовать этот шаблон, но есть ли способ сделать это в одну строку?
\def\foo{\@ifstar\@foo\@@foo}
\def\@foo#1{...}
\def\@@foo#1{...}
решение1
\documentclass{article}
\makeatletter
\def\sndname{\@ifstar\@sndname{\def\@sndname}}
\makeatother
\begin{document}
Set it \sndname{Hello U2}and use it \sndname*.
\end{document}
Фокус в том, что он \sndname
читает не аргумент, а то, что \def
внутри \sndname
.
решение2
Вы злоупотребляете правилами синтаксиса LaTeX. *-версия команды обычно должна иметь те же обязательные аргументы, что и стандартная версия.
Вместо этого вы можете использовать необязательный аргумент:
\documentclass{article}
\usepackage{xparse}
\ExplSyntaxOn
\NewDocumentCommand{\sndname}{o}
{
\IfNoValueTF{#1}
{\tl_use:N \l_cocomore_sndname_tl}
{\tl_set:Nn \l_cocomore_sndname_tl { #1 }}
}
\tl_new:N \l_cocomore_sndname_tl
\ExplSyntaxOff
\begin{document}
\sndname[Hello U2]
\sndname
\end{document}
Однако лучшим подходом было бы использование разных команд для установки переменной и для ее использования.
решение3
Дополнение к ответу @egreg, который, как я согласен, имеет лучший синтаксис, но без xparse
. Закомментированная версия — это определение команды в стиле TeX, а незакомментированная — это определение в стиле LaTeX. В определении LaTeX необязательный аргумент может принимать только значение по умолчанию, здесь установлено значение \empty
, которое затем можно проверить в коде. Это должно работать, пока оно не загружено с \empty
. Точки вокруг команд при использовании нужны только для проверки того, что не добавляются лишние пробелы. (На самом деле, версию LaTeX, вероятно, можно рассматривать как однострочную, но так ее удобнее читать:-)
\documentclass{article}
%%%% TeX style definition
% \makeatletter
% \def\sndname{\@ifnextchar[\opt@sndname\@sndnamevar}
% \def\opt@sndname[#1]{\def\@sndnamevar{#1}}
% \makeatother
%%%% LaTeX style definition
\newcommand\sndname[1][\empty]{%
\ifx#1\empty
\sndnamevar
\else
\def\sndnamevar{#1}%
\fi}
%%%% Load with nothing (just in case \sndname is used before loaded)
\sndname[]
%%%%
\begin{document}
Load: .\sndname[Name of snd].
Print: .\sndname.
\end{document}