A comparação de macros falha

A comparação de macros falha

Sou novo no LaTex e tive um problema com meus colegas. Eles definem um tipo de documento em um arquivo TeX (por exemplo, 'svvr', 'srs', ...). Esta definição externa corresponde às linhas 4 e 5 do meu código de exemplo (MWE 2).

Agora devo usar esta definição externa em meu arquivo TeX para decidir qual processamento dependente de documento deve ocorrer. Para fazer isso, escrevi um MWE para testar a seleção.

Meu código de teste vem originalmente da Internet e compara o nome do trabalho com uma determinada string (por exemplo, "{\detokenize{svvr}"). Chamei meu arquivo TeX de "svvr.tex" para poder fazer a comparação com \jobname.

Meu problema agora é que quando comparo com \jobname (MWE 1), a seleção funciona corretamente.

\documentclass{article}

% Own TeX file:
\begin{document}
    \edef\docTypeExt{\jobname}
    % Specify which document type is to be handled: 'svvr', 'srs', ...
    \edef\docTypeSvvr{\detokenize{svvr}} 
    \edef\docTypeSrs{\detokenize{srs}}

    \textbf{\jobname} 
    \textbf{\docShortcut}
    \textbf{\docTypeSvvr}
    \textbf{\docTypeSrs}
    \newline
    
    \ifx\docTypeExt\docTypeSvvr
        true
    \else
        false: \\
        \jobname \\
        \docShortcut \\
        \docTypeSvvr
    \fi
\newline

    \ifx\docTypeExt\docTypeSrs
        true
    \else
        false: \\
        \jobname \\
        \docShortcut \\
        \docTypeSrs
    \fi

\end{document}

Mas se eu comparar com a definição externa dos meus colegas (MWE 2), a comparação falha.

\documentclass{article}

% Given code, defined in included TeX file: 'svvr', 'srs', ...
\newcommand { \docpropPTdocShortcut } {svvr}    % Define document type here!
\gdef\docShortcut{\docpropPTdocShortcut}

% Own TeX file:
\begin{document}
    \edef\docTypeExt{\docShortcut}
    % Specify which document type is to be handled: 'svvr', 'srs', ...
    \edef\docTypeSvvr{\detokenize{svvr}} 
    \edef\docTypeSrs{\detokenize{srs}}

    \textbf{\jobname} 
    \textbf{\docShortcut}
    \textbf{\docTypeSvvr}
    \textbf{\docTypeSrs}
    \newline
    
    \ifx\docTypeExt\docTypeSvvr
        true
    \else
        false: \\
        \jobname \\
        \docShortcut \\
        \docTypeSvvr
    \fi
\newline

    \ifx\docTypeExt\docTypeSrs
        true
    \else
        false: \\
        \jobname \\
        \docShortcut \\
        \docTypeSrs
    \fi

\end{document}

Como a seleção deve ser estruturada para que funcione também com a definição externa?

Modifiquei as definições, mas todas as tentativas até agora falharam.

Responder1

Cada token de personagem entregue por \jobnameé da categoria 12 (outro). Exceção: Espaços (ponto de código número 32 tanto em ASCII quanto em Unicode) são da categoria 10 (espaço). O mesmo acontece com tokens de caracteres entregues por \detokenize.

No entanto, os tokens de caracteres que, com seu segundo exemplo, vão para o texto de substituição de \docpropPTdocShortcutnão são entregues por \jobnameou \detokenize, mas surgem devido à leitura e tokenização de coisas do TeX do arquivo de entrada .tex. Assim, outro regime de código de categoria é aplicado para que muitos tokens de caracteres que surgem desta forma tenham uma categoria diferente de 12 (outros). Por exemplo, tokens de caracteres que denotam letras do alfabeto que surgem dessa forma geralmente têm categoria 11 (letra).

Assim, um token de sequência de controle \docTypeSvvrou \docTypeSrs, cujo texto de substituição consiste apenas em tokens de caracteres que vêm de \jobnameou \detokenizee, portanto, são tokens de caracteres da categoria 12(outro) ou espaços da categoria 10(espaço), tem um significado que difere do significado de um controle sequência \docTypeExtonde os mesmos caracteres foram tokenizados com categoria 11 (letra).
Assim \ifx, -comparison com seu segundo exemplo direciona para o \else-branch.

Com o seu segundo exemplo, você pode omitir \detokenizeao definir \docTypeSvvr/ \docTypeSrsou aplicar \detokenizeou \@onelevel@sanitizeao definir \docTypeExt.

\newline, o que faz com que o LaTeX continue a composição do parágrafo, mas iniciar outra linha do parágrafo, seguida por uma linha vazia, o que faz com que o LaTeX termine o parágrafo atual, parece meio redundante para mim: você obtém a vertical \baselineskipde \newlinee a vertical \parskipse isso não é zero. Se vertical \parskipfor zero e em alguns lugares você desejar algum salto vertical entre os parágrafos, não abuse \newlinedisso, mas use \vspaceou \addvspaveou \vskipou \smallskipou \medskipou \bigskip.

\newcommand { \docpropPTdocShortcut } {svvr}, onde \docpropPTdocShortcuta tokenização é precedida por um token de espaço, não é uma boa prática. Se não estiver no ExplSyntax, onde os espaços já seriam ignorados no momento da tokenização das coisas, faça:
\newcommand{\docpropPTdocShortcut}{svvr}.

Com o exemplo abaixo, o \detokenize-route é usado para que você possa comparar com segurança com macros cujo texto de substituição é composto pela expansão de, \jobnamese desejar.

\documentclass{article}


% Given code, defined in included TeX file: 'svvr', 'srs', ...
%% (In case the TeX file in question does not produce text/a chapter of the document, 
%%  \input might be a better choice than \include ...)

\newcommand{\docpropPTdocShortcut}{svvr}% Define document type here!
\gdef\docShortcut{\docpropPTdocShortcut}

% Own TeX file:
\begin{document}
  \edef\docTypeExt{\docShortcut}%%
  \edef\docTypeExt{\detokenize\expandafter{\docTypeExt}}%%
  %\csname @onelevel@sanitize\endcsname\docTypeExt
  %-----------------------------------------------------------------  
  % Specify which document type is to be handled: 'svvr', 'srs', ...
  \edef\docTypeSvvr{\detokenize{svvr}}%%
  \edef\docTypeSrs{\detokenize{srs}}%%

  \noindent
  \verb|\jobname|: \texttt{\jobname}\\
  \verb|\docShortcut|: \texttt{\meaning\docShortcut}\\
  \verb|\docTypeExt|: \texttt{\meaning\docTypeExt}\\
  \verb|\docTypeSvvr|: \texttt{\meaning\docTypeSvvr}\\
  \verb|\docTypeSrs|: \texttt{\meaning\docTypeSrs}

  \vskip\baselineskip

  \noindent
  \ifx\docTypeExt\docTypeSvvr
      true
  \else
      false:\\
      \jobname\\
      \docShortcut\\
      \docTypeSvvr
  \fi

  \vskip\baselineskip

  \noindent
  \ifx\docTypeExt\docTypeSrs
      true
  \else
      false:\\
      \jobname\\
      \docShortcut\\
      \docTypeSrs
  \fi
\end{document}

informação relacionada