summaryrefslogtreecommitdiff
path: root/Master/texmf-dist/tex/latex/probsoln/probsoln.sty
diff options
context:
space:
mode:
authorKarl Berry <karl@freefriends.org>2011-08-24 00:09:20 +0000
committerKarl Berry <karl@freefriends.org>2011-08-24 00:09:20 +0000
commit00e6529c140ad1858c21526e6f8044aabb399270 (patch)
tree39e376e2630a9135fa211e3945879224c4c8e83b /Master/texmf-dist/tex/latex/probsoln/probsoln.sty
parent9acea66f478ccf41a96c04350796f74e5e74757e (diff)
probsoln 3.01 (22aug11)
git-svn-id: svn://tug.org/texlive/trunk@23668 c570f23f-e606-0410-a88d-b1316a301751
Diffstat (limited to 'Master/texmf-dist/tex/latex/probsoln/probsoln.sty')
-rw-r--r--Master/texmf-dist/tex/latex/probsoln/probsoln.sty447
1 files changed, 308 insertions, 139 deletions
diff --git a/Master/texmf-dist/tex/latex/probsoln/probsoln.sty b/Master/texmf-dist/tex/latex/probsoln/probsoln.sty
index fe9a6d3b2b6..365b1075773 100644
--- a/Master/texmf-dist/tex/latex/probsoln/probsoln.sty
+++ b/Master/texmf-dist/tex/latex/probsoln/probsoln.sty
@@ -7,7 +7,7 @@
%% probsoln.dtx (with options: `probsoln.sty,package')
%%
%% probsoln.dtx
-%% Copyright 2008 Nicola Talbot
+%% Copyright 2011 Nicola Talbot
%%
%% This work may be distributed and/or modified under the
%% conditions of the LaTeX Project Public License, either version 1.3
@@ -21,7 +21,7 @@
%%
%% The Current Maintainer of this work is Nicola Talbot.
%%
-%% This work consists of the files probsoln.dtx and probsoln.ins and the derived files probsoln.sty, 1stprncp.tex, args.tex, easy.tex, easy2.tex, implicit.tex, mchoice.tex, newdata.tex, nosoln.tex, probspaces.tex, probspaces2.tex, sample.tex, sample2.tex, sample3.tex, sample4.tex, sample5.tex, tabmchoice.tex.
+%% This work consists of the files probsoln.dtx and probsoln.ins and the derived files probsoln.sty, sample.tex, sample2.tex, sample3.tex, sample4.tex, sample5.tex, sample6.tex, sample7.tex, prob-1stprncp.tex, prob-args.tex, prob-easy.tex, prob-easy2.tex, prob-implicit.tex, prob-mchoice.tex, prob-mixed.tex, prob-newdata.tex, prob-nosoln.tex, prob-probspaces.tex, prob-probspaces2.tex, prob-tabmchoice.tex.
%%
%% \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
@@ -47,9 +47,8 @@
%% Display the problems
%% You may need to change \theenumi back here
\NeedsTeXFormat{LaTeX2e}
-\ProvidesPackage{probsoln}[2008/08/25 v3.0 (NLCT)]
+\ProvidesPackage{probsoln}[2011/08/22 v3.01 (NLCT)]
\RequirePackage{ifthen}
-\RequirePackage{substr}
\RequirePackage{amsmath}
\newif\ifshowanswers
\showanswersfalse
@@ -57,6 +56,10 @@
\let\hideanswers\showanswersfalse
\DeclareOption{answers}{\showanswerstrue}
\DeclareOption{noanswers}{\showanswersfalse}
+\newif\ifusedefaultprobargs
+\DeclareOption{usedefaultargs}{\usedefaultprobargstrue}
+\DeclareOption{nousedefaultargs}{\usedefaultprobargsfalse}
+\usedefaultprobargsfalse
\newcommand*{\prob@showdraftlabel}[2]{}
\newcommand*{\draftproblemlabel}[2]{[#1,#2]}
\DeclareOption{draft}{%
@@ -66,10 +69,12 @@
\ProcessOptions
\newcommand*{\prob@db@default}{}
\newcommand*{\prob@databases}{default}
+\newcommand*{\prob@db@default@solutions}{}
\newcommand*{\prob@newdb}[1]{%
\@ifundefined{prob@db@#1}{%
\expandafter\gdef\csname prob@db@#1\endcsname{}%
\xdef\prob@databases{\prob@databases,#1}%
+ \expandafter\gdef\csname prob@db@#1@solutions\endcsname{}%
}{%
\PackageError{probsoln}{Data set `#1' is already defined}{}}}
\newcommand*{\prob@currentdb}{default}
@@ -127,37 +132,60 @@
\do@moveargs
}%
}
-\newcommand{\prob@newproblem}[4]{%
-\@ifundefined{prob@db@#2}{\prob@newdb{#2}}{}%
-\@ifundefined{prob@data@#2@#3}{%
-\let\@tmp=\undefined
-\newcommand\@tmp[#1]{#4}%
-\expandafter\global\expandafter\let
- \csname prob@data@#2@#3\endcsname=\@tmp
-\expandafter\xdef\csname prob@argN@#2@#3\endcsname{\number#1}%
-\let\@tmp=\undefined
-\expandafter\ifx\csname prob@db@#2\endcsname\@empty
- \expandafter\xdef\csname prob@db@#2\endcsname{#3}%
-\else
- \expandafter\xdef\csname prob@db@#2\endcsname{%
- \csname prob@db@#2\endcsname,#3}%
-\fi
-\ifnum#1>0\relax
- \@prob@do@getargs{#1}{#2}{#3}%
-\fi
- }{%
- \PackageError{probsoln}{Problem `#3' is already defined for
- data base `#2'}{Problem labels must be unique for each data base}}%
+\newcommand{\prob@newproblem}[5]{%
+ \@ifundefined{prob@db@#2}{\prob@newdb{#2}}{}%
+ \@ifundefined{prob@data@#2@#3}%
+ {%
+ \let\@tmp=\undefined
+ \newcommand\@tmp[#1]{#4}%
+ \expandafter\global\expandafter\let
+ \csname prob@data@#2@#3\endcsname=\@tmp
+ \expandafter\xdef\csname prob@argN@#2@#3\endcsname{\number#1}%
+ \let\@tmp=\undefined
+ \expandafter\ifx\csname prob@db@#2\endcsname\@empty
+ \expandafter\xdef\csname prob@db@#2\endcsname{#3}%
+ \else
+ \expandafter\xdef\csname prob@db@#2\endcsname{%
+ \csname prob@db@#2\endcsname,#3}%
+ \fi
+ \ifx\@empty#5\@empty
+ \else
+ \edef\thisprob@currentdb{#2}%
+ \edef\thisprob@currentlabel{#3}%
+ \expandafter\@setdefaultprobargs\expandafter{#5}%
+ \fi
+ }%
+ {%
+ \PackageError{probsoln}{Problem `#3' is already defined for
+ data base `#2'}{Problem labels must be unique for each data base}%
+ }%
}
\newcommand{\@prob@gobblethree}[3]{}
\newcommand{\@prob@getargs}[3]{%
\message{Problem `#3' (in data base `#2') requires #1 argument(s).^^J
-Please specify (e.g. {5}{3}):}%
+Please specify (e.g. \csname @prob@getargs@eg@\romannumeral#1\endcsname):}%
\read-1to\@tmp
\expandafter\global\expandafter\let
\csname prob@args@#2@#3\endcsname=\@tmp
}
+\def\@prob@getargs@eg@i{{12}}
+\def\@prob@getargs@eg@ii{{5}{3}}
+\def\@prob@getargs@eg@iii{{4}{5}{2}}
+\def\@prob@getargs@eg@iv{{5}{3}{10}{8}}
+\def\@prob@getargs@eg@v{{5}{3}{10}{8}{4}}
+\def\@prob@getargs@eg@vi{{5}{3}{10}{8}{4}{24}}
+\def\@prob@getargs@eg@vii{{5}{3}{10}{8}{4}{24}{32}}
+\def\@prob@getargs@eg@viii{{5}{3}{10}{8}{4}{24}{32}{9}}
+\def\@prob@getargs@eg@ix{{5}{3}{10}{8}{4}{24}{32}{9}{2}}
\let\@prob@do@getargs\@prob@gobblethree
+\newcommand*{\setprobargs}[3][default]{%
+ \expandafter\gdef\csname prob@args@#1@#2\endcsname{#3}%
+}
+\newcommand*{\@setdefaultprobargs}[1]{%
+ \ifusedefaultprobargs
+ \setprobargs[\thisprob@currentdb]{\thisprob@currentlabel}{#1}%
+ \fi
+}
\long\def\long@collect@body#1{%
\@envbody{\@xp#1\@xp{\the\@envbody}}%
\edef\process@envbody{\the\@envbody\@nx\end{\@currenvir}}%
@@ -167,9 +195,15 @@ Please specify (e.g. {5}{3}):}%
\edef\process@envbody{\@xp\@nx\csname\@currenvir\endcsname}%
\process@envbody
}
-\long\def\long@addto@envbody#1{\global\@envbody\@xp{\the\@envbody#1}}
+\long\def\long@addto@envbody#1{%
+ \toks@{#1}%
+ \edef\@psn@tmp{\the\@envbody\the\toks@}%
+ \global\@envbody\@xp{\@psn@tmp}%
+}
\long\def\long@collect@@body#1\end#2{%
- \edef\begin@stack{\long@push@begins#1\begin\end \@xp\@gobble\begin@stack}%
+ \protected@edef\begin@stack{%
+ \long@push@begins#1\begin\end \@xp\@gobble\begin@stack
+ }%
\ifx\@empty\begin@stack
\endgroup
\@checkend{#2}%
@@ -182,22 +216,60 @@ Please specify (e.g. {5}{3}):}%
\long\def\long@push@begins#1\begin#2{%
\ifx\end#2\else b\@xp\long@push@begins\fi
}
-\newenvironment{defproblem}[2][0]{%
- \def\@prob@currentargN{#1}%
+\newenvironment{defproblem}[1][0]{%
+ \edef\@prob@currentargN{\number0#1}%
+ \@defproblem@beginenv
+}{}
+
+\newcommand*{\@defproblem@beginenv}[2][]{%
+ \def\@prob@currentdefaultargs{#1}%
\def\@prob@currentlabel{#2}%
\long@collect@body\prob@do@defproblem
-}{}
+}
\newcommand{\prob@do@newproblem}[1]{%
-\prob@newproblem\@prob@currentargN\prob@currentdb
- \@prob@currentlabel{#1}}
+ \prob@newproblem\@prob@currentargN\prob@currentdb
+ \@prob@currentlabel{#1}{\@prob@currentdefaultargs}}
\let\prob@do@defproblem=\prob@do@newproblem
\newenvironment{onlysolution}{%
\long@collect@body\do@onlysolution
}{}
\newcommand{\do@onlysolution}[1]{%
-\ifshowanswers
- #1%
-\fi}
+ \ifshowanswers
+ #1%
+ \fi
+ \@ifundefined{@prob@currentlabel}
+ {}%
+ {%
+ \expandafter
+ \psn@add@unique@label
+ \csname prob@db@\prob@currentdb @solutions\endcsname{%
+ \@prob@currentlabel
+ }%
+ }%
+}
+\newcommand*{\psn@add@unique@label}[2]{%
+ \ifx#1\@empty
+ \xdef#1{#2}%
+ \else
+ \edef\@tmp@label{#2}%
+ \expandafter\DTLifinlist\expandafter{\@tmp@label}{#1}%
+ {}% ignore
+ {\xdef#1{#1,\@tmp@label}}%
+ \fi
+}
+\providecommand{\DTLifinlist}[4]{%
+ \def\@dtl@doifinlist##1,#1,##2\end@dtl@doifinlist{%
+ \def\@before{##1}%
+ \def\@after{##2}%
+ }%
+ \expandafter\@dtl@doifinlist\expandafter,#2,#1,\@nil
+ \end@dtl@doifinlist
+ \ifx\@after\@nnil
+ #4%
+ \else
+ #3%
+ \fi
+}
\newenvironment{onlyproblem}{%
\long@collect@body\do@onlyproblem
}{}
@@ -207,15 +279,20 @@ Please specify (e.g. {5}{3}):}%
#1%
\fi}
\newcommand{\useproblem}[2][default]{%
-\prob@showdraftlabel{#1}{#2}%
-\let\@next=\relax
-\@ifundefined{prob@data@#1@#2}{%
- \PackageError{probsoln}{Problem `#2' is not defined in data set
- `#1'}{}%
-}{%
- \def\@next{\csname prob@data@#1@#2\endcsname}%
-}%
-\@next}
+ \def\@prob@currentlabel{#2}%
+ \def\prob@currentdb{#1}%
+ \prob@showdraftlabel{#1}{#2}%
+ \let\@useprob@next=\relax
+ \@ifundefined{prob@data@#1@#2}%
+ {%
+ \PackageError{probsoln}%
+ {Problem `#2' is not defined in data set `#1'}{}%
+ }%
+ {%
+ \def\@useprob@next{\csname prob@data@#1@#2\endcsname}%
+ }%
+ \@useprob@next
+}
\newcommand*{\loadallproblems}[2][default]{%
\bgroup
\let\par\relax
@@ -224,8 +301,11 @@ Please specify (e.g. {5}{3}):}%
\egroup
}
\newcommand{\prob@do@selectedproblem}[1]{%
-\IfSubStringInString{,\@prob@currentlabel,}{,\prob@selectedlabels,}{%
-\prob@do@newproblem{#1}}{}%
+ \expandafter\DTLifinlist\expandafter{\@prob@currentlabel}{\prob@selectedlabels}%
+ {%
+ \prob@do@newproblem{#1}%
+ }%
+ {}%
}
\newcommand{\loadselectedproblems}[3][default]{%
\bgroup
@@ -236,6 +316,22 @@ Please specify (e.g. {5}{3}):}%
\input{#3}%
\egroup
}
+\newcommand{\prob@do@exceptedproblem}[1]{%
+ \expandafter\DTLifinlist\expandafter{\@prob@currentlabel}{\prob@selectedlabels}%
+ {}%
+ {%
+ \prob@do@newproblem{#1}%
+ }%
+}
+\newcommand{\loadexceptproblems}[3][default]{%
+\bgroup
+ \let\par\relax
+ \edef\prob@currentdb{#1}%
+ \edef\prob@selectedlabels{#2}%
+ \let\prob@do@defproblem=\prob@do@exceptedproblem
+ \input{#3}%
+\egroup
+}
\newcommand{\prob@add@currentlabel}[1]{%
\ifx\prob@selectedlabels\@empty
\xdef\prob@selectedlabels{\@prob@currentlabel}%
@@ -246,6 +342,12 @@ Please specify (e.g. {5}{3}):}%
\newif\iffirstpass
\firstpasstrue
\newcommand{\loadrandomproblems}[3][default]{%
+ \@loadrandomproblems{#1}{#2}{#3}{}%
+}
+\newcommand{\loadrandomexcept}[4][default]{%
+ \@loadrandomproblems{#1}{#2}{#3}{#4}%
+}
+\newcommand{\@loadrandomproblems}[4]{%
\bgroup
\let\par\relax
\def\prob@db@reserved{}%
@@ -256,17 +358,20 @@ Please specify (e.g. {5}{3}):}%
\input{#3}%
\@probselN=0\relax
\@for\@thislabel:=\prob@selectedlabels\do{%
- \advance\@probselN by 1\relax
- \expandafter
- \edef\csname @prob@tmp@\romannumeral\@probselN\endcsname{%
- \@thislabel}%
+ \expandafter\DTLifinlist\expandafter
+ {\@thislabel}{#4}{}%
+ {%
+ \advance\@probselN by 1\relax
+ \expandafter
+ \edef\csname @prob@tmp@\romannumeral\@probselN\endcsname{%
+ \@thislabel}%
+ }%
}%
\shuffle{@prob@tmp@}{\@probselN}%
\ifnum\@probselN<#2\relax
- \PackageError{probsoln}{%
- Can't select \number#2\space\space problem(s):^^J
- '#3' only contains \number\@probselN\space problem(s)}{%
- Only \number\@probselN\space problem(s) will be selected}%
+ \PackageWarning{probsoln}{You have requested
+ \number#2\space\space problem(s) but `#3' only contains
+ \number\@probselN\space problems. All problems will be selected}%
\else
\@probselN=#2\relax
\fi
@@ -317,6 +422,33 @@ Please specify (e.g. {5}{3}):}%
}%
}%
}
+\newcommand{\foreachsolution}[2][default]{%
+\@ifundefined{prob@db@#1}{%
+ \PackageError{probsoln}{Data base `#1' is not defined}{}%
+}{%
+ \expandafter\let\expandafter\@tmp\csname prob@db@#1@solutions\endcsname
+ \@for\thisproblemlabel:=\@tmp\do{%
+ \ifx\thisproblemlabel\@empty
+ \else
+ \expandafter\ifnum
+ \csname prob@argN@#1@\thisproblemlabel\endcsname>0\relax
+ \@ifundefined{prob@args@#1@\thisproblemlabel}{%
+ \expandafter\@prob@getargs
+ \csname prob@argN@#1@\thisproblemlabel\endcsname
+ {#1}{\thisproblemlabel}}{}%
+ \expandafter\let\expandafter\thisproblemargs
+ \csname prob@args@#1@\thisproblemlabel\endcsname
+ \else
+ \let\thisproblemargs\@empty
+ \fi
+ \expandafter\toks@\expandafter{\thisproblemargs}%
+ \edef\thisproblem{\noexpand\useproblem[#1]{\thisproblemlabel}%
+ \the\toks@}%
+ #2%
+ \fi
+ }%
+}%
+}
\newcommand{\foreachdataset}[2]{%
\@for#1:=\prob@databases\do{#2}}
\newcount\@probN \newcount\@probselN \newcount\@rndselctr
@@ -324,35 +456,50 @@ Please specify (e.g. {5}{3}):}%
\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}%
- \global\r@ndcur=1\relax
-\else
- \global\r@ndcur=#1\relax
-\fi
-\PackageInfo{probsoln}{Random Seed = \number\r@ndcur}%
+ \ifnum#1=0\relax
+ \PackageWarning{probsoln}{Can't have 0 as random seed, changing to 1}%
+ \global\r@ndcur=1\relax
+ \else
+ \global\r@ndcur=#1\relax
+ \fi
+ \PackageInfo{probsoln}{Random Seed = \number\r@ndcur}%
}
\newcommand*{\PSNgetrandseed}[1]{#1=\r@ndcur\relax}
\newcommand*{\PSNrand}{%
-\@ps@randtmp=\r@ndcur
-\multiply\@ps@randtmp by 16807\relax
-\r@ndcur=\@ps@randtmp
-\global\divide\r@ndcur by 120001\relax
-\global\multiply\r@ndcur by 120001\relax
-\advance\@ps@randtmp by -\r@ndcur
-\global\r@ndcur = \@ps@randtmp
-\ifnum\r@ndcur=0\relax
- \global\r@ndcur=1\relax
-\fi
+ \@ps@randtmp=\r@ndcur
+ \multiply\@ps@randtmp by 16811\relax
+ \r@ndcur=\@ps@randtmp
+ \global\divide\r@ndcur by 39989\relax
+ \global\multiply\r@ndcur by 39989\relax
+ \advance\@ps@randtmp by -\r@ndcur
+ \global\r@ndcur = \@ps@randtmp
+ \ifnum\r@ndcur=0\relax
+ \global\r@ndcur=1\relax
+ \fi
+}
+\newcommand*{\PSN@old@rand}{%
+ \@ps@randtmp=\r@ndcur
+ \multiply\@ps@randtmp by 16807\relax
+ \r@ndcur=\@ps@randtmp
+ \global\divide\r@ndcur by 120001\relax
+ \global\multiply\r@ndcur by 120001\relax
+ \advance\@ps@randtmp by -\r@ndcur
+ \global\r@ndcur = \@ps@randtmp
+ \ifnum\r@ndcur=0\relax
+ \global\r@ndcur=1\relax
+ \fi
+}
+\newcommand*{\PSNuseoldrandom}{%
+ \let\PSNrand\PSN@old@rand
}
\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
+ \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
@@ -368,58 +515,73 @@ Please specify (e.g. {5}{3}):}%
}
\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
-}%
+ \@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
-}}
+ {%
+ \@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
+ }%
+}
\newcommand*{\newproblem}{\@ifstar\@snewproblem\@newproblem}
-\newcommand{\@snewproblem}[3][0]{%
-\begin{defproblem}[#1]{#2}%
-#3%
-\end{defproblem}}
-\newcommand{\@newproblem}[4][0]{%
-\begin{defproblem}[#1]{#2}%
-#3%
-\begin{onlysolution}%
-\begin{solution}%
-#4%
-\end{solution}%
-\end{onlysolution}%
-\end{defproblem}}
+\newcommand{\@snewproblem}[1][0]{%
+ \def\@newprob@argN{#1}%
+ \@s@newproblem
+}%
+\newcommand{\@s@newproblem}[3][]{%
+ \begin{defproblem}[\@newprob@argN][#1]{#2}%
+ #3%
+ \end{defproblem}%
+}
+\newcommand{\@newproblem}[1][0]{%
+ \def\@newprob@argN{#1}%
+ \@ns@newproblem
+}
+\newcommand{\@ns@newproblem}[4][]{%
+ \begin{defproblem}[\@newprob@argN][#1]{#2}%
+ #3%
+ \begin{onlysolution}%
+ \begin{solution}%
+ #4%
+ \end{solution}%
+ \end{onlysolution}%
+ \end{defproblem}%
+}
\newcommand*{\selectallproblems}[1]{{\loadallproblems[#1]{#1}}%
\foreachproblem[#1]{\PSNitem\thisproblem\endPSNitem}}
\newcommand*{\selectrandomly}[2]{%
@@ -428,21 +590,28 @@ are only \number\@ps@forrand item(s) in the list}%
}
\newenvironment{PSNitem}{\item}{}
\@ifundefined{solution}{%
-\newenvironment{solution}{\par\noindent\textbf{\solutionname:}}{}%
+ \newenvironment{solution}{\par\noindent\textbf{\solutionname:}\space
+ \ignorespaces}{}%
}{}
\newcommand*{\solutionname}{Solution}
\newenvironment{textenum}{%
-\ifnum\@enumdepth>\thr@@
- \@toodeep
-\else
- \advance\@enumdepth\@ne
- \edef\@enumctr{enum\romannumeral\the\@enumdepth}%
- \let\@item\@textitem
- \def\@itemlabel{\refstepcounter{\@enumctr}%
- \csname label\@enumctr\endcsname}%
- \setcounter{\@enumctr}{0}%
-\fi\ignorespaces}{%
-\global\advance\@enumdepth\m@ne}
+ \ifnum\@enumdepth>\thr@@
+ \@toodeep
+ \else
+ \advance\@enumdepth\@ne\relax
+ \edef\@enumctr{enum\romannumeral\the\@enumdepth}%
+ \let\@item\@textitem
+ \def\@itemlabel{%
+ \refstepcounter{\@enumctr}%
+ \csname label\@enumctr\endcsname
+ }%
+ \setcounter{\@enumctr}{0}%
+ \fi
+ \ignorespaces
+}%
+{%
+ \global\advance\@enumdepth\m@ne\relax
+}
\def\@textitem[#1]{#1\space\ignorespaces}
\newcommand*{\correctitemformat}[1]{\fbox{#1}}
\newcommand*{\incorrectitemformat}[1]{%