%% %% This is file `probsoln.sty', %% generated with the docstrip utility. %% %% The original source files were: %% %% probsoln.dtx (with options: `probsoln.sty,package') %% Copyright (C) 2006 Nicola Talbot, all rights reserved. %% If you modify this file, you must change its name first. %% You are NOT ALLOWED to distribute this file alone. You are NOT %% ALLOWED to take money for the distribution or use of either this %% file or a changed version, except for a nominal charge for copying %% etc. %% \CharacterTable %% {Upper-case \A\B\C\D\E\F\G\H\I\J\K\L\M\N\O\P\Q\R\S\T\U\V\W\X\Y\Z %% Lower-case \a\b\c\d\e\f\g\h\i\j\k\l\m\n\o\p\q\r\s\t\u\v\w\x\y\z %% Digits \0\1\2\3\4\5\6\7\8\9 %% Exclamation \! Double quote \" Hash (number) \# %% Dollar \$ Percent \% Ampersand \& %% Acute accent \' Left paren \( Right paren \) %% Asterisk \* Plus \+ Comma \, %% Minus \- Point \. Solidus \/ %% Colon \: Semicolon \; Less than \< %% Equals \= Greater than \> Question mark \? %% Commercial at \@ Left bracket \[ Backslash \\ %% Right bracket \] Circumflex \^ Underscore \_ %% Grave accent \` Left brace \{ Vertical bar \| %% Right brace \} Tilde \~} \NeedsTeXFormat{LaTeX2e} \ProvidesPackage{probsoln}[2006/03/02 v2.02 Problems and their Solutions Package (NLCT)] \RequirePackage{ifthen} \provideboolean{showanswers} \newcommand{\showanswers}{\showanswerstrue} \newcommand{\hideanswers}{\showanswersfalse} \DeclareOption{answers}{\showanswerstrue} \DeclareOption{noanswers}{\showanswersfalse} \ExecuteOptions{noanswers} \ProcessOptions \newif\ifselectrandom \selectrandomfalse \newif\iffirstpass \newif\ifselected \newcommand{\solutionname}{Solution} \newcommand{\newproblem}[4][0]{% \ifselectrandom \iffirstpass \global\advance\@probN by 1 \expandafter\gdef\csname @problabel\romannumeral\@probN\endcsname{#2}% \else \checkselected{#2}% \ifselected \@ifundefined{@prob@#2}{% \ifnum#1=0 \expandafter\gdef\csname @prob@#2\endcsname{% #3 \ifshowanswers\begin{solution}#4\end{solution}\fi}% \expandafter\gdef\csname @prob@#2@arg\endcsname{\relax}% \else \message{Problem #2 requires #1 argument(s), please specify (e.g. {5}{3}):}% \read-1to\@tmp \expandafter\xdef\csname @prob@#2@arg\endcsname{\@tmp}% \expandafter\global\expandafter\newcommand\csname @prob@#2\endcsname[#1]{% #3 \ifshowanswers\solution #4\fi}% \fi }{% \PackageError{probsoln}{Label #2 already used}% {Each problem must have a unique label identifier}% }% \fi \fi \else \@ifundefined{@prob@#2}{% \expandafter\global\expandafter\newcommand\csname @prob@#2\endcsname[#1]{% #3 \ifshowanswers\begin{solution}#4\end{solution}\fi}% }{% \PackageError{probsoln}{Label #2 already used}% {Each problem must have a unique label identifier}% } \fi } \newcommand{\useproblem}[1]{% \@ifundefined{@prob@#1}{% \PackageError{probsoln}{Label #1 undefined}% {Can't find problem defined with label identifier '#1'}% }{\csname @prob@#1\endcsname}% } \newcount\@probN \newcount\@probselN \newcount\@rndselctr \newcount\r@ndcur \newcount\@ps@randtmp \r@ndcur=1\relax \newcommand{\PSNrandseed}[1]{% \ifnum#1=0\relax \PackageWarning{probsoln}{Can't have 0 as random seed, changing to 1}% \r@ndcur=1\relax \else \r@ndcur=#1\relax \fi \PackageInfo{probsoln}{Random Seed = \the\r@ndcur}% } \newcommand{\PSNrand}{% \@ps@randtmp=\r@ndcur \multiply\@ps@randtmp by 16807\relax \r@ndcur=\@ps@randtmp \divide\r@ndcur by 120001\relax \multiply\r@ndcur by 120001\relax \advance\@ps@randtmp by -\r@ndcur \r@ndcur = \@ps@randtmp \ifnum\r@ndcur=0\relax\r@ndcur=1\fi } \newcommand{\PSNrandom}[2]{% \PSNrand #1=\r@ndcur \@ps@randtmp=\r@ndcur \divide\@ps@randtmp by #2\relax \multiply\@ps@randtmp by #2\relax \advance#1 by -\@ps@randtmp \advance#1 by 1\relax } \newcommand{\random}[3]{% \ifnum#2=1\relax \PSNrandom{\value{#1}}{#3}% \else \@rndselctr=#3% \advance\@rndselctr by -#2\relax \advance\@rndselctr by 1\relax \PSNrandom{\value{#1}}{\@rndselctr}% \addtocounter{#1}{#2}% \addtocounter{#1}{-1}% \fi } \newcommand*{\selectallproblems}[1]{% \global\@probN=0\relax \selectrandomtrue \firstpasstrue \input{#1}% \firstpassfalse \selectrandomfalse \input{#1}% \global\@rndselctr=1\relax \whiledo{\@rndselctr < \@probN \TE@or \@rndselctr = \@probN}{% \edef\@tmp{\csname @problabel\romannumeral\@rndselctr\endcsname}% \edef\@probargs{{\@tmp}\csname @prob@\@tmp @arg\endcsname}% \PSNitem \expandafter\useproblem\@probargs \endPSNitem \global\advance\@rndselctr by 1\relax }} \newcommand{\selectrandomly}[2]{% \global\@probselN=#2\relax \global\@probN=0\relax \selectrandomtrue \firstpasstrue \input{#1}% \ifnum\@probselN>\@probN \PackageError{probsoln}{Requested number too large}% {You have asked for \the\@probselN \space problems, but there are only \the\@probN \space problems defined in the file #1. I will only select \the\@probN \space problems.}% \global\@probselN=\@probN \fi \shuffle{@problabel}{\@probN}% \firstpassfalse \input{#1}% \selectrandomfalse \global\@rndselctr=1\relax \whiledo{\@rndselctr < \@probselN \TE@or \@rndselctr = \@probselN}{% \edef\@tmp{\csname @problabel\romannumeral\@rndselctr\endcsname}% \edef\@probargs{{\@tmp}\csname @prob@\@tmp @arg\endcsname}% \PSNitem \expandafter\useproblem\@probargs \endPSNitem \global\advance\@rndselctr by 1\relax }% } \newcommand{\PSNitem}{\item} \@ifundefined{endPSNitem}{\def\endPSNitem{}}{% \PackageError{probsoln}{\string\endPSitem\ already defined}{}} \newenvironment{solution}{\paragraph{\solutionname:}}{} \newcount\@ckselctr \newcommand{\checkselected}[1]{% \selectedfalse \@ckselctr=1\relax \whiledo{\@ckselctr < \@probselN \TE@or \@ckselctr = \@probselN}{% \ifthenelse{\equal{#1}{\csname @problabel\romannumeral\@ckselctr\endcsname}}% {\global\selectedtrue \global\@ckselctr=\@probselN}{}% \advance\@ckselctr by 1\relax }% } \newcount\@shfctr \newcount\@shfA \newcount\@shfB \newcommand{\shuffle}[2]{% \@shfctr=1\relax \whiledo{\@shfctr < 101}{% \PSNrandom{\@shfA}{#2}\PSNrandom{\@shfB}{#2}% \ifnum\@shfA=\@shfB \else \edef\@@tmpA{\csname#1\romannumeral\@shfA\endcsname}% \let\@tmpA=\@@tmpA \edef\@@tmpB{\csname#1\romannumeral\@shfB\endcsname}% \let\@tmpB=\@@tmpB \expandafter\xdef\csname#1\romannumeral\@shfA\endcsname{\@tmpB}% \expandafter\xdef\csname#1\romannumeral\@shfB\endcsname{\@tmpA}% \fi \advance\@shfctr by 1\relax }% } \newcount\@ps@forrand \newcommand{\doforrandN}[4]{% {\@ps@forrand=0\relax \@for#2:=#3\do{% \advance\@ps@forrand by 1\relax \expandafter\edef\csname @doforrandN@\romannumeral\@ps@forrand\endcsname{#2}}% \ifnum\@ps@forrand<#1\relax \PackageError{probsoln}{Can't randomly select \number#1 item(s)}{You have requested \number#1 item(s), but there are only \number\@ps@forrand item(s) in the list}% \else \shuffle{@doforrandN@}{\@ps@forrand}% \ifnum#1>0\relax \@ps@forrand=0\relax \loop \advance\@ps@forrand by 1\relax \edef#2{\csname @doforrandN@\romannumeral\@ps@forrand\endcsname}% #4% \ifnum\@ps@forrand<#1\relax \repeat \fi \fi }} \endinput %% %% End of file `probsoln.sty'.