我需要创建一个环境(我们称之为randomizer
),随机改变其行的顺序,它可能包含任何文本或乳胶命令(假设而不验证它们不会跨行)。
例如,我有几个tex
文件,每个文件包含一个问题,我想生成一组按随机顺序排列的问题。然后我会使用
\begin{randomizer}
\input{problem1}
\input{problem2}
\input{problem3}
\input{problem4}
\end{randomizer}
我还希望能够控制随机过程,通过为生成器指定种子数。
答案1
以下是基于 RANOMIZE-IN-PLACE 程序的解决方案临床研究与培训中心.该过程定义为
n = A.length
for i=1 to n
swap A[i] with A[random(i,n)]
(CLRS 不喜欢end for
,所以我们也不使用它)。
Donald Arseneau使用的 TeX 代码random.tex
(应该在您的发行版中)。此代码放入了 10 个宏\csname num0\endcsname
,,\csname num1\endcsname
...一些数字 0..9 的随机排列(我使用宏而不是计数器来保存后者)。您可以使用此代码编写类似等的内容\expandafter\input{file\csname num0\endcsname}
。\expandafter\input{file\csname num1\endcsname}
\documentclass{article}
\input{random}
\begin{document}
\newcount\number
\newcount\randomnum
% Put 0..9 into \num0..\num9
\number=0
\loop\ifnum\the\number<10\relax
\expandafter\edef\csname num\the\number\endcsname{\the\number}
\advance\number by 1
\repeat
% Randomize
\number=0
\loop\ifnum\the\number<10\relax
\setrannum{\randomnum}{\the\number}{9} % Random number between \number and 9
\edef\tmpnum{\csname num\the\number\endcsname}
\expandafter\edef\csname num\the\number\endcsname{\csname
num\the\randomnum\endcsname}
\expandafter\edef\csname num\the\randomnum\endcsname{\tmpnum}
\advance\number by 1
\repeat
% Print the results:
\number=0
\loop\ifnum\the\number<10\relax
Macro \textbackslash num\the\number\space contains \expandafter\csname
num\the\number\endcsname
\advance\number by 1\relax\par
\repeat
% To input in random order files file0.tex, file1.tex, file2.tex,...
% use instead
% \number=0
% \loop\ifnum\the\number<10\relax
% \expandafter\input{file\csname num\the\number\endcsname}
% \advance\number by 1\relax
% \repeat
\end{document}
请参阅random.tex
有关为生成器播种的文档。
输出示例:
Macro \num0 contains 7
Macro \num1 contains 1
Macro \num2 contains 9
Macro \num3 contains 3
Macro \num4 contains 6
Macro \num5 contains 8
Macro \num6 contains 2
Macro \num7 contains 5
Macro \num8 contains 4
Macro \num9 contains 0
答案2
如果有luatex
,也可以使用 lua。这使用与 Boris 的答案相同的改组方法,但在 lua 中。lualatex
使用以下文件调用:
\documentclass{article}
\usepackage{luacode}
\newcommand\SeedRnd[1][os.time()]{\directlua{rndseed = #1; math.randomseed(rndseed)}}
\newcommand\RndSeed{\directlua{tex.print(rndseed)}}
\SeedRnd %Takes an optional parameter if you want a specific random seed
\newcommand\RndOrderInput[1]{%
\luaexec{
local table = {#1}
function shuffle(t)
local n = \#t
while n > 1 do
local k = math.random(n)
t[n], t[k] = t[k], t[n]
n = n - 1
end
return t
end
for k,v in pairs(shuffle(table)) do tex.print("\string\\input{" .. v .. "}") end
}}
\begin{document}
Random seed: \RndSeed %so you will be able to recreate this order.
\RndOrderLoad{'file1', 'file2', 'file3', 'file4'}
\end{document}
请注意,文件名必须写为lua字符串,即'file1'
或"file1"
,而不仅仅是file1
。