在试卷中包含可选答案

在试卷中包含可选答案

我想在试卷中包含答案,这样试卷就可以以两种不同的方式编写:带答案和不带答案。英国大学(或至少其中一些大学)通常采用这种方式,使用包comment,如下所示:

\documentclass{article}
\usepackage{comment}
\excludecomment{answer}
\newcommand{\showanswers}{\renewenvironment{answer}{\begin{answershown}}{\end{answershown}}}
\newenvironment{answershown}{\textbf{Answer:} }{}
% \showanswers  % comment out to hide the answer
\begin{document}
  Is the following command correct?
  \begin{verbatim}
    public class
  \end{verbatim}
  \begin{answer} % do not indent!
    The following command is not correct:
    \begin{verbatim}
      public class
    \end{verbatim}
  \end{answer} % do not indent!
\end{document}

\showanswer是论文的干净版本(没有答案)和包含答案的版本之间的切换。缺点是该comment包不允许缩进(这很重要,因为它清楚地显示了论文的结构,可能很复杂),因此编译上面的源代码会产生错误消息:

Runaway argument?
! File ended while scanning use of \next.
<inserted text>
                \par
<*> ./mwe.tex

?

为了允许缩进,我可以使用environ包:

\documentclass{article}
\usepackage{environ}
\NewEnviron{answer}{}
\newcommand{\showanswers}{\RenewEnviron{answer}{\textbf{Answer:} \BODY}}
\showanswers  % comment out to hide the answer
\begin{document}
  Is the following command correct?
  \begin{verbatim}
    public class
  \end{verbatim}
  \begin{answer}
    The following command is not correct:
    \begin{verbatim}
      public class
    \end{verbatim}
  \end{answer}
\end{document}

但答案environ并不像,编译后者的源代码会产生:verbatim

Runaway argument?
 public class \end {verbatim}\env@ignore  The following command is no\ETC.
! File ended while scanning use of \@xverbatim.
<inserted text>
                \par
<*> ./mwe.tex

?

有没有办法同时实现缩进和verbatim(在答案中)?

答案1

好的,有几种可能的解决方案。(您可以使用前两种方案中的任一种)

我将它们重写成单独的问题(未来的读者更有可能搜索这些术语)。


我如何定义“注释”环境以便环境分隔符可以缩进?

简单,使用verbatim包。

\usepackage{verbatim}
\let\answer=\comment
\let\endanswer=\endcomment

参考:重新定义环境,使其成为另一个环境的同义词

请注意,实际上可以使用comment制表符来缩进包定义的环境,只有空格会失效。

或者:


我如何重新定义environ包所定义的环境,以便它允许在其主体中使用 catcode 更改命令(例如)\verb\begin{verbatim}

包定义的环境没有什么特别的environ。您仍然可以\renewenvironment照常使用它来重新定义它。

\usepackage{environ}
\NewEnviron{answer}{}

\newcommand{\showanswers}{\renewenvironment{answer}{\begin{answershown}}{\end{answershown}}}
\newenvironment{answershown}{\textbf{Answer:} }{}

并不是说你需要这个,但可以作为参考:

我怎么能够定义带有包的环境environ,使得它允许在其主体中执行 catcode 更改命令?

你不能。还有其他选择,例如 savebox 或scontentspackage。

参考:环境中的 \BODY 中的逐字内容

答案2

似乎lstlistingverbatim与 catcode 一起玩,不能真正在环境中使用,至少当我们想不显示它们时。我不确定这是否是最好的解决方案,但你可以在环境之前使用包realboxes和命令将代码保存在框中\Sbox{\mylstbox}{your content}(确保使用创建框\newsavebox{\mylstbox}),然后在环境中通过重新使用它\usebox{\mylstbox}。它适用于verbatimlstlisting

模式考试:

在此处输入图片描述

模式答案:

在此处输入图片描述

顺便说一句,我认为 tcolorbox 也有一个用于答案的模块,您可能会喜欢它(并且我猜这个解决方案也适用于 tcolorbox 模式)。

%%% Comment/uncomment, or compile with:
%%%
%%% pdflatex -jobname=exam_answers "\def\showanswers{} \input{exam.tex}" && pdflatex -jobname=exam_no_answers "\input{exam.tex}"
%%%
%%% to produce automatically two versions without changing the file.
% \def\showanswers{}
\documentclass{article}
\usepackage{listings}
\usepackage{realboxes} % https://tex.stackexchange.com/questions/29971/why-can-lstlisting-not-be-saved-in-a-command
\usepackage{changepage} % For adjustwidth and indentation
\NewDocumentEnvironment{answer}{+b}{
  \ifdefined\showanswers
  \textbf{Answer}:

  \begin{adjustwidth}{1cm}{0cm} % Indent
    #1
  \end{adjustwidth}
  \else\fi}{}
\newsavebox{\mylstbox}

\begin{document}

\noindent Is the following command correct?
\begin{lstlisting}
  public class
\end{lstlisting}
\Sbox{\mylstbox}{%
\begin{lstlisting}
public class {
  hello
}
\end{lstlisting}
}
\begin{answer}
  The following command is not correct:

  \usebox{\mylstbox}
\end{answer} % do not indent!
\end{document}

相关内容