\endnote-argument 中练习后提示的扩展

\endnote-argument 中练习后提示的扩展

我们用于练习的乳胶模板的一个理想特性是以某种方式给出提示,让学生可以选择在没有提示的情况下尝试解决练习(即,不在问题表述的正下方)。

endnotes(或者说较新的enotez),似乎是一个很好的起点。但是,我希望每个尾注的标记都指向给出提示的子问题。我的想法是使用从派生的计数器自动标记所有子问题\thesubproblem,从而重建正确的标签,而不必手动将标签提供给\hint我想要的 -command(参见下面的代码)。不幸的是,我无法做到:

  • 扩展论证中的引用\endnote
  • 喂养任何引用到可选参数(负责标记)。然而,这是次要的,因为通过改变样式并删除标记,我可以将引用放在提示主体的开头。

我看过几个 tex.sx 问题(如何扩展一个环境中的几个参数?何时使用 \edef、\noexpand 和 \expandafter?等),但没有成功。

此外,我想利用enotez提供的拆分功能,最好是诱使它认为新问题属于新部分(下面我会使用\section*{}我想要删除的 来做到这一点)。我尝试过增加计数器等,但这没有用,而且我的expl3-fu 还不足以解析enotez.sty实际正在做的事情。

这是我的示例代码:

\documentclass{article}
\usepackage[english]{babel}

\usepackage{etoolbox}
\usepackage{enotez}
\usepackage[colorlinks]{hyperref}

\makeatletter
\setenotez{
    list-name=Hints,
    list-style=section,
    mark-cs=\@gobble,
    split=section,
    split-title={Hints for Problem <ref>}
}
\makeatother

\DeclareInstance{enotez-list}{custom}{list}{number = #1:}

\newcounter{exsheet}
\newcounter{problem}[exsheet]

\newcommand{\exsheet}[1]
{\setcounter{exsheet}{#1}
\begin{center}  {\Large Homework Problem Sheet #1} \end{center}
}

\setlength{\parindent}{0pt}
\makeatletter
\renewcommand{\theproblem}{\arabic{exsheet}.\arabic{problem}}
\newcommand{\problem}[2][]{%
    % details see tex.stackexchange.com/q/31780
    \@startsection{problem}{1}{\z@}{-3.25ex\@plus -1ex \@minus -.2ex}{1.5ex \@plus .2ex}%
    {\large\bfseries Problem~}[\ifstrempty{#1}{#2}{#1}]{#2}}
\let\problemmark\@gobble

\newcounter{subproblem}[problem]
\renewcommand{\thesubproblem}{(\arabic{exsheet}.\arabic{problem}\alph{subproblem})}
\newcommand{\thesp}{\arabic{exsheet}.\arabic{problem}.\arabic{subproblem}}
\newcommand*{\subproblem}{\@startsection{subproblem}{2}{0em}{1ex}{0pt}{\bfseries}{}%
    \label{sp.\thesp}}
\let\subproblemmark\@gobble
\makeatother

% % % % % % Help needed here: % % % % % % %
%\newcommand{\hint}[#1]{\endnote[...expansion magic...\ref{sp.\thsp}]{#1}}

\let\thesection\theproblem

\begin{document}

\exsheet{1}

\problem{Test}
\subproblem Text
\subproblem Text\endnote[(1.1b)]{Hint} % call should just be \hint{Hint}
\subproblem Text 
\subproblem Text\endnote[(1.1d)]{Hint} %\ref{sp.\thesp} works outside

\section*{Section for splitting endnotes -- shouldn't be here}
\problem{Test}
\subproblem Text\endnote[(1.2a)]{Hint}
\subproblem Text
\subproblem Text
\subproblem Text\endnote[(1.2d)]{Hint}

\vfill % would normally be \newpage
\printendnotes[custom]
\end{document}

答案1

下面的代码通过 LaTeX 的构建机制构建提示列表toclof并且lot不再使用enotez。它依赖于hyperref正在加载的包,因此列表中的提示链接回相应的子问题。

提示以description列表形式打印,\subsection*其中以 s 作为标题。文档主体

\problem{Test}
\subproblem Text
\subproblem Text\hint{Hint one}
\subproblem Text
\subproblem Text\hint{Hint two}

\problem{Also a test}
\subproblem Text
\subproblem Text
\subproblem Text
\subproblem Text

\problem{Another test}
\subproblem Text\hint{Hint three}
\subproblem Text
\subproblem Text
\subproblem Text\hint{Hint four}

\listofhints

给出

在此处输入图片描述

我在代码中添加了大量注释,希望能够解释所有事情的作用。\null\clearpage\clearpage\null行只是为了确保链接跳转到正确的位置。

\documentclass{article}
\usepackage[english]{babel}

\usepackage{etoolbox}
\usepackage[colorlinks]{hyperref}

\makeatletter
% exercise sheet:
\newcounter{exsheet}
\newcommand{\exsheet}[1]{%
  \setcounter{exsheet}{#1}%
  \begin{center}
    \Large Homework Problem Sheet~\theexsheet
  \end{center}%
}

% problems:
\newcounter{problem}[exsheet]
\renewcommand*\theproblem{\theexsheet.\arabic{problem}}
\newcommand\problem[2][]{%
  % details see tex.stackexchange.com/q/31780
  \@startsection{problem}
    {1}{\z@}{-3.25ex\@plus -1ex \@minus -.2ex}{1.5ex \@plus .2ex}%
    {\large\bfseries Problem~}[\ifstrempty{#1}{#2}{#1}]{#2}%
}
\let\problemmark\@gobble
% avoid hyperrefs bookmark level warning:
\providecommand*\toclevel@problem{0}

% subproblems:
\newcounter{subproblem}[problem]
\renewcommand*\thesubproblem{(\theproblem\alph{subproblem})}
\newcommand*\subproblem{%
  \@startsection{subproblem}
    {2}{0em}{1ex}{0pt}
    {\bfseries}{}%
}
\let\subproblemmark\@gobble
% avoid hyperrefs bookmark level warning:
\providecommand*\toclevel@subproblem{1}

% hints:
% the following code relies on `hyperref' being loaded
%   => \contentsline then has 4 arguments!

\newcounter{hints}
\newrobustcmd\hint[1]{%
  % count the number of hints:
  \stepcounter{hints}%
  % write hint to auxiliary file:
  \addtocontents{hints}{%
    \hintscontentsline
      {subproblem.\theHsubproblem}  % the current subproblem hyperlink destination
      {\thesubproblem}              % the current subproblem number
      {\unexpanded{\unexpanded{#1}}}% the actual hint
      {\arabic{problem}}            % the value of the current problem number
      {\theproblem}%                % the current problem number
  }%
}

\newrobustcmd\hintscontentsline[5]{%
  \contentsline{hints}
    {#2}                        % first argument to \l@hints 
    {\hint@item{#2}{#3}{#4}{#5}}% second argument to \l@hints
    {#1}%                       % hyperlink name
}

\newrobustcmd*\listofhints{%
  \section*{Hints}
  \begingroup
    % get the list of hints:
    \@starttoc{hints}
    \hints@empty{\@latex@warning{Empty list of hints}}%
  \endgroup
}

\let\hints@empty\@firstofone

% \l@hints gets fed by \contentsline
% #1: second argument of \contentsline
% #2: third argument of \contentsline
% => we build \hint@item with five arguments here, the first of \l@hints being
%    the last to \hint@item
\newcommand\l@hints[2]{%
  #2{#1}%
}

\newcounter{problemhints}
\newcounter{hintinlist}
% \hint@item does the actual writing of the hints:
% #1: formatted subproblem number
% #2: hint text
% #3: problem number
% #4: formatted problem number
% #5: subproblem link
\newrobustcmd\hint@item[5]{%
  % \Hy@tocdestname (part of argument #5) needs to survive when the group is
  % closed, else the first link of a problem will lead to a wrong destination:
  \xdef\Hy@tocdestname{\Hy@tocdestname}%
  % check if the hints for a new problem start:
  \ifnumcomp{\value{problemhints}}<{#3}
    {%
      % if this is nit the first problem end the description list:
      \ifnumequal{#3}{1}{}{\end{description}}%
      \subsection*{Hints for problem~#4}
      % start a new description list:
      \begin{description}
    }{}%
  \item[#5] #2%
  % remember to which problem this hint belongs to:
  \setcounter{problemhints}{#3}%
  % check if this is the last hint and if so end the description list:
  \stepcounter{hintinlist}%
  \ifnumequal{\value{hints}}{\value{hintinlist}}
    {%
      \end{description}
      % disable the warning -- the list isn't empty any more:
      \global\let\hints@empty\@gobble
    }{}%
}

\makeatother

\setlength{\parindent}{0pt}

\begin{document}

\null\clearpage

\exsheet{1}

\problem{Test}
\subproblem Text
\subproblem Text\hint{Hint one}
\subproblem Text
\subproblem Text\hint{Hint two}

\problem{Also a test}
\subproblem Text
\subproblem Text
\subproblem Text
\subproblem Text

\problem{Another test}
\subproblem Text\hint{Hint three}
\subproblem Text
\subproblem Text
\subproblem Text\hint{Hint four}

\listofhints

\clearpage\null

\end{document}

相关内容