随机列表,不编译

随机列表,不编译

我正在尝试创建一个可以生成复三项式的宏。

我编写的代码在 80% 的情况下都能按预期编译,但在 20% 的情况下会给出一大堆错误消息。你可以在此 ShareLaTeX 链接。如果您多次按下“重新编译”,您会发现它有时会编译,有时则不会。

错误包括:

  • 缺失数字视为零
  • 非法计量单位
  • 额外\其他
  • 缺少结束 \csname
  • 额外的 \endcsname
  • 未定义的控制序列
  • 失控的论点

以下是其中前几张图片:在此处输入图片描述

即在 15% 的时间内无法编译,一大堆事情会同时出错。

我的代码有什么问题?我猜想这与随机数/项目/列表未正确编码有关,但我不确定。

\documentclass{article}

\usepackage[margin=1cm]{geometry}
\usepackage{ifthen}
\usepackage{pgf}
\usepackage{pgffor}

\setlength{\parindent}{0pt}

\pagestyle{empty}

\pgfmathsetseed{\number\pdfrandomseed}

\newcommand{\InitVariablesCTPP}
{% 
 % I want the equation to be in the form (ax+b)(cx+d)=Ax^2+Bx+C.
 %but I want there to be NO common factors.
 %So, these lists mean that if, say, c=2, then d is selected randomly from 1,3,5, or 7.... at least that was the intention.
 \pgfmathdeclarerandomlist{IfOne}{{1}{2}{3}{4}{5}{6}{7}}
 \pgfmathdeclarerandomlist{IfTwo}{{1}{3}{5}{7}}
 \pgfmathdeclarerandomlist{IfThree}{{1}{2}{4}{5}{7}}
 \pgfmathdeclarerandomlist{IfFour}{{1}{3}{5}{7}}
 \pgfmathdeclarerandomlist{IfFive}{{1}{2}{3}{4}{6}{7}}

 \pgfmathsetmacro{\a}{int(random(1,5))}
 \ifcase\a\relax%
  \or \pgfmathrandomitem{\b}{IfOne}
  \or \pgfmathrandomitem{\b}{IfTwo}
  \or \pgfmathrandomitem{\b}{IfThree}
  \or \pgfmathrandomitem{\b}{IfFour}
  \or \pgfmathrandomitem{\b}{IfFive} \fi

 \pgfmathsetmacro{\c}{int(random(2,5))}
 \ifcase\c\relax%
   \or \pgfmathrandomitem{\d}{}
   \or \pgfmathrandomitem{\d}{IfTwo}
   \or \pgfmathrandomitem{\d}{IfThree}
   \or \pgfmathrandomitem{\d}{IfFour}
   \or \pgfmathrandomitem{\d}{IfFive}
 \fi

 \pgfmathsetmacro{\A}{int(\a*\c)}
 \pgfmathsetmacro{\B}{int(\a*\d+\b*\c)}
 \pgfmathsetmacro{\C}{int(\b*\d)}
}

\newcommand{\ManyCTPP}[1]
 {%
  \foreach \x in {1,2,3,...,#1}
  {
   \InitVariablesCTPP
    a=\a\\
    b=\b\\
    c=\c\\
    d=\d\\
    A=\A =\a * \c \\
    B=\B =\a * \d + \b * \c\\
    C=\C =\b * \d\\

\(({\a}x+{\b})({\c}x+{\d})={\A}x^2+{\B}x+{\C}\)
\\

\vspace{1cm}}
 }

\begin{document}

\section{Complex Trinomials}

\ManyCTPP{5}

\end{document}

答案1

什么出现会发生这种情况,您正在选择两个随机列表元素\b\d,当您要使用它们时,随机列表的最后一个“索引”用于和\b\d这是有问题的,因为,例如,如果\d正在使用列表项编号 6 并且\b是列表中的一个项目,IfTwo那么您会得到一个missing number,因为IfTwo没有项目 6。

解决该问题的一种方法是强制 \b,并\d在定义时使用类似以下内容进行扩展:

\xdef\b{\b}

您的代码还存在一些其他问题:

  • 用于\a, \b, \c, \d, \A, \B, \C, \x宏/变量名称并不是一个好主意,因为其中一些与 latex 使用的内部宏相冲突
  • 正如 David 在评论中指出的那样,这\pgfmathrandomitem{\d}{}行是错误的。应该是\pgfmathrandomitem{\d}{IfOne}。(好吧,因为\c介于之间2,并且5此代码永远不会执行...)
  • 你只需要定义一次随机列表,因此你应该\pgfmathdeclarerandomlist从 Init 宏中删除这些行
  • 除了使用之外,\pgfmathsetmacro{\a}{int(random(1,5))}您还可以使用\pgfmathrandominteger{\a}{1}{5}
  • \foreach \x in {1,2,3,...,#1}不是写\foreach \x in {1,...,#1}
  • \\是一个糟糕的结束方式...

考虑到这些要点,您的代码将变为:

\documentclass{article}

\usepackage[margin=1cm]{geometry}
\usepackage{ifthen}
\usepackage{pgf}
\usepackage{pgffor}

\setlength{\parindent}{0pt}

\pagestyle{empty}

\pgfmathsetseed{\number\pdfrandomseed}

 % I want the equation to be in the form (ax+b)(cx+d)=Ax^2+Bx+C.
 %but I want there to be NO common factors.
 %So, these lists mean that if, say, c=2, then d is selected randomly from 1,3,5, or 7.... at least that was the intention.
 \pgfmathdeclarerandomlist{IfOne}{{1}{2}{3}{4}{5}{6}{7}}
 \pgfmathdeclarerandomlist{IfTwo}{{1}{3}{5}{7}}
 \pgfmathdeclarerandomlist{IfThree}{{1}{2}{4}{5}{7}}
 \pgfmathdeclarerandomlist{IfFour}{{1}{3}{5}{7}}
 \pgfmathdeclarerandomlist{IfFive}{{1}{2}{3}{4}{6}{7}}

\newcommand{\InitVariablesCTPP}{
 \pgfmathrandominteger{\avar}{1}{5}
 \ifcase\avar\relax%
  \or \pgfmathrandomitem{\bvar}{IfOne}
  \or \pgfmathrandomitem{\bvar}{IfTwo}
  \or \pgfmathrandomitem{\bvar}{IfThree}
  \or \pgfmathrandomitem{\bvar}{IfFour}
  \or \pgfmathrandomitem{\bvar}{IfFive}
 \fi
 \xdef\bvar{\bvar}

 \pgfmathrandominteger{\cvar}{2}{5}
 \ifcase\cvar\relax%
   \or \pgfmathrandomitem{\dvar}{IfOne}
   \or \pgfmathrandomitem{\dvar}{IfTwo}
   \or \pgfmathrandomitem{\dvar}{IfThree}
   \or \pgfmathrandomitem{\dvar}{IfFour}
   \or \pgfmathrandomitem{\dvar}{IfFive}
 \fi
 \xdef\dvar{\dvar}

 \pgfmathsetmacro{\Avar}{int(\avar*\cvar)}
 \pgfmathsetmacro{\Bvar}{int(\avar*\dvar+\bvar*\cvar)}
 \pgfmathsetmacro{\Cvar}{int(\bvar*\dvar)}
}

\newcommand{\ManyCTPP}[1]
 {%
  \foreach \x in {1,...,#1}
  {
   \InitVariablesCTPP
    a=\avar\\
    b=\bvar\\
    c=\cvar\\
    d=\dvar\\
    A=\Avar =\avar * \cvar\relax \\
    B=\Bvar =\avar * \dvar + \bvar * \cvar\relax\\
    C=\Cvar =\bvar * \dvar\relax\\

\(({\avar}x+{\bvar})({\cvar}x+{\dvar})={\Avar}x^2+{\Bvar}x+{\Cvar}\)
\\

\vspace{1cm}}
 }

\begin{document}

\section{Complex Trinomials}

\ManyCTPP{5}

\end{document}

上面的代码确实解决了问题,但是我对问题所在的看法却有点可疑,因为如果我是对的,那么下面的代码有时会导致错误,但它总是可以编译而没有任何问题:

\documentclass{article}
\usepackage{pgf}
\usepackage{pgffor}

\pgfmathdeclarerandomlist{one}{{1}{2}{3}{4}{5}{6}{7}{8}{9}}
\pgfmathdeclarerandomlist{two}{{1}{2}{3}{4}}
\pgfmathdeclarerandomlist{three}{{1}{2}{3}{4}{5}{6}}

\begin{document}

% test case
\foreach \n in {1,...,100} {
    \pgfmathrandomitem{\oneval}{one}
    \pgfmathrandomitem{\twoval}{two}
    \pgfmathrandomitem{\threeval}{three}
    \pgfmathparse{int(\oneval*\threeval+\oneval)}
    \n: \pgfmathresult
}

\end{document}

我应该小心地将 OP 代码减少到 MWE,但我还有工作要做......

相关内容