다른 명령의 출력을 처리하는 경우 \author에서 줄바꿈이 누락됩니다.

다른 명령의 출력을 처리하는 경우 \author에서 줄바꿈이 누락됩니다.

~ 안에이 게시물, 목록을 처리하는 좋은 방법을 찾았습니다. 아래 코드를 사용하면 선택적 구분 기호 인수를 사용하여 목록을 인쇄할 수 있습니다.

\documentclass{article}
\usepackage{etoolbox}% http://ctan.org/pkg/etoolbox
\newcommand{\printlist}[2][,]{%
  \def\itemdelim{\def\itemdelim{#1}}% Item delimiter delayed by one cycle
  \renewcommand*{\do}[1]{\itemdelim##1}% How each item is processed
  \docsvlist{#2}}% Process CSV list
\begin{document}
$\printlist{1,2,3,4,5,6,7}$ \par
$\printlist[;]{a,b,c,d,e,f}$
\end{document}

\printlist그러나 명령 내에서 \authornewline 과 함께 사용하면 \\제대로 작동하지 않습니다. 줄 바꿈은 목록의 첫 번째 요소에 대해서만 설정됩니다. 다른 모든 요소의 경우 줄 바꿈이 무시됩니다.

\documentclass{article}

\usepackage{etoolbox}% http://ctan.org/pkg/etoolbox
\newcommand{\printlist}[2][;]{%
  \def\itemdelim{\def\itemdelim{#1}}% Item delimiter delayed by one cycle
  \renewcommand*{\do}[1]{\itemdelim##1}% How each item is processed
  \docsvlist{#2}}% Process CSV list

\title{Test}
\author{\printlist[,\\]{abc,def,ghi,jkl}}
\begin{document}
\maketitle
\end{document}

실패한 사례

예를 들어 줄 바꿈 없이 구분 기호를 사용하면 ::위의 내용이 예상대로 작동합니다.

성공적인 테스트 1

\\명령 에 줄 바꿈을 추가하면 \author예상되는 결과가 나타납니다.

\author{\printlisti[::]{abc,def,ghi}\\123\\456\\789}

성공적인 테스트 2

\printlist줄 바꿈과 의 조합이 \\문제를 일으키는 것 같습니다. 왜요?

답변1

에 대한 인수 는 로 \author조판됩니다 tabular. 각 셀은 자체 그룹을 형성하므로 내부 정의 \itemdelim및 정의는 \do첫 번째 행에서 유지되지 않습니다.

기본적으로 다음과 같은 일이 일어나고 있습니다.

\begin{tabular}{c}
  \def\itemdelim{test} \\
  \itemdelim
\end{tabular}

for 와 동일합니다 \do. 하지만 두 번째 행에서는 외부와 동일한 정의를 가지며 tabular오류 메시지가 표시되지 않습니다.


\itemdelim(첫 번째 항목이 아닌 항목의 경우) 및 \do전역 정의를 수행해야 합니다 .

\newcommand{\printlist}[2][;]{%
  \def\itemdelim{\gdef\itemdelim{#1}}%
  \gdef\do##1{\itemdelim##1}%
  \docsvlist{#2}}
\author{\printlist[,\\]{abc,def,ghi,jkl}}

하지만 다음을 직접 사용하여 "트릭"을 \itemdelim직접 적용 \do하고 건너뛸 수 있습니다 .\itemdelim#1

\newcommand{\printlist}[2][;]{%
  \def\do##1{##1\gdef\do####1{#1####1}}%
  \docsvlist{#2}}
\author{\printlist[,\\]{abc,def,ghi,jkl}}

같은 또 다른 보조 매크로를 사용하면 전역 \defdo정의를 피할 수 있습니다 \do(다른 문서 전체에 정의된 매크로를 희생하여):

\newcommand*\defdo[1]{%
  \def\do##1{#1\defdo{#1}##1}}%
\newcommand{\printlist}[2][;]{%
  \def\do##1{##1\defdo{#1}}%
  \docsvlist{#2}}%
\author{\printlist[,\\]{abc,def,ghi,jkl}}

이것은 다음 행에서 사용할 수 있도록 \do행에서 행으로 의 정의를 몰래 숨깁니다 .\\


또는 목록을 사전 처리하여 다음으로 전달할 수도 있습니다 \author.

\newcommand{\savelist}[3][;]{%
  \renewcommand*\do[1]{%
    \newcommand*#3{##1}%
    \renewcommand*\do[1]{%
      \appto#3{#1####1}%
    }%
  }%
  \docsvlist{#2}}
\savelist[,\\]{abc,def,ghi,jkl}\authors
\author{\authors}

\do이 경우 문서의 최상위 수준에서 정의되므로 정의 도 "전역"입니다.

전역을 정의하는 것은 \do다음을 사용하는 다른 모든 코드 이후로 충돌을 일으키지 않아야 합니다.\do 를 사용하는 다른 모든 코드가 정의를 가정하지 않고 자체적으로 정의했어야 하므로 . 전역 및 로컬 할당/정의 혼합지저분할 수도 있다하지만 을 사용하는 것이 \savelist더 나을 수도 있습니다.


그 너머를 살펴보면 etoolboxLaTeX3의 l3clist패키지는 목록 항목 사이에 무언가( = ) \clist_use:Nn를 배치하기 위해 정의가 필요하지 않은 기능을 제공합니다.#1,\\

\documentclass{article}
\ExplSyntaxOn
\DeclareDocumentCommand{\printlist}{ O{;} m}{
  \clist_set:Nn \l_tmpa_clist {#2}
  \clist_use:Nn \l_tmpa_clist {#1}
}
\ExplSyntaxOff
\author{\printlist[,\\]{abc,def,ghi,jkl}}
\title{Test}
\begin{document}
\maketitle
\end{document}

관련 정보