adicionar \chapter no KOMA scrbook gera um "! Erro LaTeX: \do indefinido."

adicionar \chapter no KOMA scrbook gera um "! Erro LaTeX: \do indefinido."

Contexto:Esta pergunta é uma continuação deManipulando _ (sublinhados) na lista de argumentos separados por vírgula de uma macro. Nesta questão eu crio a macro \codecitepque recebe como argumento uma lista separada por vírgulas e imprime essas chaves gerando hyperreflinks.

Problema:Meu MWE funciona muito bem, porém não consegui implementá-lo em meu documento real. Na verdade, recebo o seguinte erro:

! LaTeX Error: \do undefined.

Eu localizei a causa, que é... o \chaptercomando: \codecitepcomandos posicionadosanteso primeiro \chaptercompila bem, mas aquelesdepoisnão.

Solução:(Sim, a solução vem antes da pergunta!) Como sugerido emNão é possível encontrar o erro LaTeX, redefinir \doa definição após o comando causador de erro fazer a compilação funcionar.

No entanto, adicionar \def\do{}após cada \chaptercomando é muito sujo, e não acho que redefinir/corrigir \chaptero comando do KOMA \def\do{}como sufixo seja uma solução sustentável.

Pergunta:O que faz a definição de \chaptermudança \doe como evitar que ela afete minha própria \codecitepmacro?


\documentclass{scrbook}
    \usepackage{etoolbox}
    \usepackage{hyperref}
    \usepackage{lipsum}

    \newcommand{\codecitep}[1]{% cf. https://tex.stackexchange.com/a/87423/64454
        [%
        \def\nextitem{\def\nextitem{, }}% Separator
        \renewcommand*{\do}[1]{\nextitem{\hyperref[code:##1]{##1}}}% How to process each item
        \docsvlist{#1}% Process list
        ]%
    }   
\begin{document}

    \section{Body before chapter}
        A sentence with one code-citation only \codecitep{key1}.
        Another sentence with two code-citations and followed by dummy text \codecitep{key1, key2}.

\chapter{Chapter title}
%\def\do{}% <----- uncomment to make the error disappear
    \section{Body after chapter}
        A sentence with one code-citation only \codecitep{key1}.
        Another sentence with two code-citations and followed by dummy text \codecitep{key1, key2}.
        \lipsum[1-2]

    \section{Appendix}
        \lipsum[3]

        \subsection{key1}
        \label{code:key1}
        \label{code:a_123}
        \lipsum[4]

        \subsection{key2}
        \label{code:key2}
        \label{code:bb_456}
        \lipsum[5]
\end{document}

Responder1

O pacote tocbasic.styusado por scrbookdoes

\let\do\relax

como parte de \doforeachtocfile, que é executado por \chapter. Isso significa que você não pode fazer isso \renewcommand\do{...}porque \doé indefinido de acordo com o LaTeX.

Na verdade, se eu remover \let\do\relaxas duas macros internas que estão fazendo isso, o problema desaparece.

O \renewcommand{\do}{...}problema apareceu em outras situações. O melhor, na minha opinião, é usar seu próprio processador de listas.

\documentclass{scrbook}

\usepackage{etoolbox}
\usepackage{hyperref}
\usepackage{lipsum}

\newcommand{\codecitep}[1]{% cf. https://tex.stackexchange.com/a/87423/64454
  [%
  \def\nextitem{\def\nextitem{, }}% Separator
  \forcsvlist\codecitepitem{#1}% Process list
  ]%
}
\newcommand{\codecitepitem}[1]{%
  \nextitem
  \hyperref[code:#1]{\detokenize{#1}}%
}

\begin{document}

\section{Body before chapter}

A sentence with one code-citation only \codecitep{key1}.
Another sentence with two code-citations and followed by 
dummy text \codecitep{key1, key2}.

\chapter{Chapter title}

\section{Body after chapter}

A sentence with one code-citation only \codecitep{key1}.
Another sentence with two code-citations and followed by 
dummy text \codecitep{key1, key2}.
\lipsum[1-2]

\section{Appendix}

\lipsum[3]

\subsection{key1}

\label{code:key1}
\label{code:a_123}
\lipsum[4]

\subsection{key2}
\label{code:key2}
\label{code:bb_456}
\lipsum[5]

\end{document}

Responder2

\doé usado em muitas construções de látex de baixo nível, apenas olhando latex.ltx

 \global\let\do\noexpand

em\begin{document}

  \let\do\@makeother 

e

\let\do\do@noligs

dentro verbatime\verb

\let\do\@makeother

emfilecontents

Não rastreei exatamente o que está sendo redefinido em seu caso de uso, mas basicamente ele só deve ser usado para uma definição local imediatamente antes da \doexecução da lista separada.

informação relacionada