目标

目标

扩张让我头疼。我需要一些帮助。问题如下:日志输出片段 AtEndAfterFileList

这是我基于上下文的日志条目问题的扩展:

如何在调用宏时(以及在任何地方)将 <section counter value>:<section title>:<page>:<file>:<line> 写入日志?

目标

我希望以下特定于上下文的宏在附加到之前进行扩展\trackedmacrolist,因为我不想\trackedmacrolist直到最后才调用。

\thenumber:\thetitle:[\thepage]:\currfilepath:\the\inputlineno

代码

\listfiles
\documentclass{article}
\usepackage{atveryend}
\usepackage{currfile}% adds \currfilepath

% Define a couple commands to track
\DeclareRobustCommand{\myproduct}[1]{MacGyver.\textit{#1}}

% The following is normally put into separate file as to modularize the application of patches
% Define a context macro as described
\def\contextinfo{\thenumber:\thetitle:[\thepage]:\currfilepath:\the\inputlineno}
\def\trackedmacro{Tracked Macro List}% initialize macro
\AtEndAfterFileList{\typeout{\trackedmacro}}

\makeatletter
% Apply Patches
\usepackage{regexpatch}
\xapptocmd{\myproduct}{\typeout{MacMessage: \contextinfo}\g@addto@macro{\trackedmacro}{^^J==> #1 (\contextinfo)}}{}{}% <-- I'd rather show MacGyver.monkey shampoo, but unsure how best to implement
% Note: \typeout is always fully expanded due to \write %https://tex.stackexchange.com/a/60976/13552
\makeatother

%\usepackage{xparse}% Loaded by regexpatch
\let\oldsection\section
\makeatletter
\RenewDocumentCommand{\section}{s o m}{%
  \begingroup
  % Extract the counter representation
  \stepcounter{section}%
  \xdef\thenumber{\thesection}%
  \addtocounter{section}{-1}%
  \protected@xdef\thetitle{#3}%
  \endgroup
  % Regular section
  \IfBooleanTF{#1}
    {\oldsection*{#3}}
    {\IfValueTF{#2}
       {\oldsection[#2]{#3}}
       {\oldsection{#3}}}
}
\makeatother

\begin{document}

\section{About \myproduct{elephant shampoo}}
\section{About \myproduct{monkey shampoo}}
\section{About \myproduct{giraffe shampoo}}
\section{About \myproduct{tiger shampoo}}

\end{document}

日志输出片段正在运行xelatex example.tex | grep MacMessage

看起来不错!

MacMessage: (1:About \myproduct {elephant shampoo}:[1]:example.tex:44)
MacMessage: (2:About \myproduct {monkey shampoo}:[1]:example.tex:45)
MacMessage: (3:About \myproduct {giraffe shampoo}:[1]:example.tex:46)
MacMessage: (4:About \myproduct {tiger shampoo}:[1]:example.tex:47)

日志输出片段AtEndAfterFileList

这里不太好

Tracked Macro List
==> elephant shampoo (4:About \myproduct {tiger shampoo}:[2]:example.tex:49)
==> monkey shampoo (4:About \myproduct {tiger shampoo}:[2]:example.tex:49)
==> giraffe shampoo (4:About \myproduct {tiger shampoo}:[2]:example.tex:49)
==> tiger shampoo (4:About \myproduct {tiger shampoo}:[2]:example.tex:49)

与上面的输出相比,您可以看到页码不再对应于代码中宏存在的位置,而是对应于宏首次展开的位置:在\AtEndAfterFileList调用时的最末尾。

问题:

  • 所有宏均显示第 4 节,这是挂接到where\thenumber时的 最新扩展。\end{document}\AtEndAfterFileList
  • 所有宏都扩展为,这是连接到时 的\myproduct{tiger shampoo}最新扩展。\thetitle\end{document}\AtEndAfterFileList
  • 所有的宏都显示第 2 页,这是连接到where\thepage时 的最新扩展。\end{document}\AtEndAfterFileList
  • 所有宏都显示第 49 行,这是所挂钩的\the\inputlinenoat \end{document}where的最新扩展。\AtEndAfterFileList

请注意,如果我\input在最后一次\myproduct通话之前的某个时间点遇到了问题,我也会预料到会出现问题\currfilepath

有关的

答案1

我认为这个问题很难理解,除非人们理解它,否则它就太神秘了:)

我将尝试以建设性的方式回答这个问题。你的问题是

\g@addto@macro{\trackedmacro}{^^J==> #1 (\contextinfo)}

这不会扩展\contextinfo,所以最后你会把\contextinfo .. \contextinfo .. \contextinfo .. \contextinfo所有内容都放在里面\trackedmacro,并且它们会同时扩展(因此会扩展为同一个内容)。所以这是你的特殊问题。你需要确保它在附加到 之前得到扩展\trackedmacro

你可以这样做首先,你需要完全扩展它,所以

\protected@edef\tmp{\contextinfo}

将节省已经扩大里面的内容\tmp。现在你需要\tmp在把它放进去之前展开一次,\tracketmacro这样你就能得到整个值。这样就可以了

\expandafter\addtotrackedmacro\expandafter{\tmp}{#1}

具有适当的定义

\newcommand*\addtotrackedmacro[2]{\g@addto@macro{\trackedmacro}{^^J==> #2 (#1)}}

我并不是说这是你问题的最佳解决方案。但是从你得到的代码开始,你有一个简单而小的解决方案来解决这个问题。现在只需在你的代码中更改这一行

\xapptocmd{\myproduct}{\typeout{MacMessage: \contextinfo}\g@addto@macro{\trackedmacro}{^^J==> #1 (\contextinfo)}}{}{}

进入这个

\xapptocmd\myproduct{\typeout{MacMessage: \contextinfo}%
  \protected@edef\tmp{\contextinfo}%
  \expandafter\addtotrackedmacro\expandafter{\tmp}{#1}}{}{}
\newcommand*\addtotrackedmacro[2]{\g@addto@macro\trackedmacro{^^J==> #2 (#1)}}

就能解决这个问题。


解决该问题的另一种方法是使用\edef而不是\def代替\g@addto@macro,这样您就可以更改

\g@addto@macro{\trackedmacro}{^^J==> #1 (\contextinfo)}

\protected@xdef\trackedmacro{\unexpanded\expandafter{\trackedmacro}^^J==> #1 (\contextinfo)}

\trackedmacro这将获取(扩展一次)的当前值,然后添加您的代码。

答案2

试试这个,但我不知道这是否是正确的结果。
在我看来,\tracklistmacro应该在then内递归定义\section

\listfiles
\documentclass{article}
\usepackage{atveryend}
\usepackage{currfile}% adds \currfilepath

% Define a couple commands to track
\DeclareRobustCommand{\myapp}[1]{\textit{#1}}
\DeclareRobustCommand{\myproduct}[1]{MacGyver.\textit{#1}}
\makeatletter
\newcommand{\@myapp}[1]{#1}
\newcommand{\@myproduct}[1]{MacGyver.#1}
\makeatother

% The following is normally put into separate file as to modularize the application of patches
% Define a context macro as described
\def\trackedmacrolist{Tracked Macro List}% initialize macro
\AtEndAfterFileList{\typeout{\trackedmacrolist}}

\makeatletter
% Apply Patches
\usepackage{regexpatch}
\def\foo@@{}
\xapptocmd{\myproduct}{\g@addto@macro{\trackedmacrolist}{^^J==> #1 (\contextinfo)}}{}{}% <-- I'd rather show MacGyver.monkey shampoo, but unsure how best to implement
% Note: \typeout is always fully expanded due to \write %http://tex.stackexchange.com/a/60976/13552
\makeatother

%\usepackage{xparse}% Loaded by regexpatch
\let\oldsection\section
\makeatletter
\RenewDocumentCommand{\section}{s o m}{%
  \begingroup
  % Extract the counter representation
  \stepcounter{section}%
  \xdef\thenumber{\thesection}%
  \addtocounter{section}{-1}%
  % Temporarily change \myapp and \myproduct to be expandable and ordinary
  \let\myapp\@myapp
  \let\myproduct\@myproduct
  % Extract the title with possible \myapp and \myproduct (now ordinary/expandable)
  % Extract the title with possible \myapp and \myproduct (now ordinary/expandable)
  \protected@xdef\thetitle{#3}%
  \endgroup
  % Regular section
  % 
  \xdef\contextinfo{\thenumber:\thetitle:[\the\c@page]:\currfilepath:\the\inputlineno}%
  \IfBooleanTF{#1}
    {\oldsection*{#3}}
    {\IfValueTF{#2}
      {\oldsection[#2]{#3}}
      {\oldsection{#3}}}
   \xdef\trackedmacrolist{\trackedmacrolist}%
  }
\makeatother

\begin{document}
\section{About \myproduct{elephant shampoo}}
\meaning\trackedmacrolist
\clearpage
\section{About \myproduct{monkey shampoo}}

\clearpage
\section{About \myproduct{giraffe shampoo}}

\clearpage
\section{About \myproduct{tiger shampoo}}

\end{document}

跟踪的宏列表 ==> 大象洗发水 (1:关于 MacGyver。大象洗发水:[1]:macmadness.tex:56) ==> 猴子洗发水 (2:关于 MacGyver。猴子洗发水:[2]:macmadness.tex:59) ==> 长颈鹿洗发水 (3:关于 MacGyver。长颈鹿洗发水:[3]:macmadness.tex:62) ==> 老虎洗发水 (4:关于 MacGyver。老虎洗发水:[4]:macmadness.tex:65) )

相关内容