나의 구체적인 예:

나의 구체적인 예:

예측 가능한 방식으로 단일 명령(기본적으로 사용자 정의 헤더)을 기반으로 다양한 명령을 생성하려고 합니다. TeX/LaTeX에서 이를 수행할 수 있는 방법이 있습니까?

나의 구체적인 예:

나는 각 하위 제목이 등으로 표시되는 모듈 사양을 작성 중입니다 \modulespec{description}{the description}. \modulespec{learning outcomes}{the learning outcomes}TeX가 다음과 같은 명령을 생성할 수 있기를 바랍니다 \mdescription{the description}.\mlearningoutcomes{the learning outcomes}

나는 TeX와 결합된 bash와 같은 확장으로 다음을 작성할 것이라는 것을 알고 있습니다.

for i in 'description' 'learning outcomes'
do
    \def\csname m\getRidOfSpaces{$i} \endcsname{\modulespec{$i}{#1}}
done

(언어 조합을 용서한다면 ) \getRidOfSpaces여기서는 learning outcomes. learningoutcomesTeX/LaTeX로 이것이 가능/실행 가능합니까?

남(아님)WE:

\documentclass{article}
\usepackage{blindtext}

% In the real thing, this definition is much more complicated
\newcommand{\modulespec}[2]{\section{#1} #2}

% The code I want in pure TeX/LaTeX
for i in 'description' 'learning outcomes'
do
    \def\csname m\getRidOfSpaces{$i} \endcsname{\modulespec{$i}{#1}}
done
% end of non TeX code


\begin{document}

% Both work
\modulespec{description}{\blindtext}
\modulespec{learning outcomes}{\blindtext}

% These two commands should produce the same output as the previous two
\mdescription{\blindtext}
\mlearningoutcomes{\blindtext}

\end{document}

답변1

LaTeX3 구현은 다음과 같습니다.

\documentclass{article}
\usepackage[margin=1cm]{geometry} % to fit in one page
\usepackage{blindtext}
\usepackage{xparse}

\newcommand{\modulespec}[2]{\section{#1} #2}

\ExplSyntaxOn

\NewDocumentCommand{\definemodules}{m}
 {
  \farley_definemodules:n { #1 }
 }

\tl_new:N \l_farley_temp_tl
\cs_new_protected:Npn \farley_definemodules:n #1
 {
  \clist_map_inline:nn { #1 }
   {
    \tl_set:Nn \l_farley_temp_tl { ##1 }
    \tl_replace_all:Nnn \l_farley_temp_tl { ~ } { }
    \cs_new_protected:cpn { m \l_farley_temp_tl } { \modulespec { ##1 } }
   }
 }

\ExplSyntaxOff

\definemodules{
  description,
  learning outcomes
}

\begin{document}

\modulespec{description}{\blindtext}
\modulespec{learning outcomes}{\blindtext}

% These two commands should produce the same output as the previous two
\mdescription{\blindtext}
\mlearningoutcomes{\blindtext}

\end{document}

여기에 이미지 설명을 입력하세요

코드에 대한 일부 의견입니다.

우리는 한 번에 모든 모듈을 정의하기 위한 사용자 수준 매크로를 정의합니다. 이는 \definemodules단순히 프로그래머의 수준 기능에 제어권을 넘겨주는 것 입니다 \farley_definemodules:n(이것은 LaTeX3 프로그래밍 지침에 따른 모범 사례입니다).

이제 함수는 \farley_definemodules:n인수를 쉼표로 나누고 항목에 대해 루프를 수행합니다. 현재 항목은 로 사용할 수 있지만 정의 내부에 있기 때문에 #1필요합니다 .##1

각 주기마다 항목을 스크래치 토큰 목록 변수에 저장하므로 해당 항목에 \l_farley_temp_tl적용할 수 있습니다 \tl_replace_all:Nnn. 교체는 "모든 공간은 아무것도 대체되지 않습니다"입니다. 프로그래밍 환경에서는 공간이 무시되므로 "실제 공간"은 으로 표시됩니다 ~.

이제 우리는 \cs_new_protected:cpn이전 스타일과 유사한 함수를 사용합니다 \@namedef. 첫 번째 인수는 제어 시퀀스 이름으로 만들어집니다 \csname...\endcsname(토큰 목록은 여기에서 TeX 규칙에 의해 확장됩니다).

답변2

'for Each' 루프를 수행하려는 것 같습니다. LaTeX 커널에는 \@for쉼표로 구분된 목록의 각 요소에 대해 이를 수행하는 매크로가 있습니다. \zap@space공백을 제거하려면 또는 이와 유사한 것이 필요합니다 . 예를 들어:

\newcommand{\modulespec}[2]{\section{#1} #2}
\makeatletter
\@for\@tempa:=description,learning outcomes\do{%
  \edef\@tempa
    {\expandafter\expandafter\expandafter\zap@space
      \expandafter\@tempa\space\@empty}%
  \expandafter\edef\csname m\@tempa\endcsname
    {\noexpand\modulespec{\@tempa}}%
}
\makeatother

필요에 따라 \mdescription및 을 정의합니다 . 나는 올바른 위치에서 변수를 강제로 확장하기 위해 \mlearningoutcomes사용했습니다 . ( '텍스트'는 내부에서 '안전'해야 하므로 여기에 \edef적용하면 소용이 없습니다 .)\protected@edef\csname

답변3

\xintForLaTeX2e 커널 유틸리티 사용 ( @이름에 가 포함됨):

\documentclass{article}
\usepackage[english]{babel}
\usepackage{blindtext}
\usepackage{xinttools}
% In the real thing, this definition is much more complicated
\newcommand{\modulespec}[2]{\section{#1} #2}

% % The code I want in pure TeX/LaTeX
% for i in 'description' 'learning outcomes'
% do
%     \def\csname m\getRidOfSpaces{$i} \endcsname{\modulespec{$i}{#1}}
% done
% % end of non TeX code

% Nota bene: in the above you probably meant \long\def, not \def
\makeatletter
\xintFor #1 in {description, learning outcomes}\do
{\long\@namedef{m\zap@space #1 \@empty}##1{\modulespec{#1}{##1}}}
\makeatother

\begin{document}

% Both work
\modulespec{description}{\blindtext}
\modulespec{learning outcomes}{\blindtext}

% These two commands should produce the same output as the previous two
\mdescription{\blindtext}
\mlearningoutcomes{\blindtext}

\end{document}

데프 루프

관련 정보