当我编译我的文档时出现以下奇怪的错误:
! Incomplete \ifcase; all text was ignored after line 256.
<inserted text>
\fi
l.256 \foo[
0]{|>I>-:a:c.-:a:c:c b|}\\
?
这远非一个最小的工作示例,但这里有其中的相关部分:
\documentclass{article}
\usepackage{xparse}
\usepackage{tikz}
\usetikzlibrary{calc,arrows,patterns,decorations.pathmorphing,backgrounds,fadings,external}
\tikzset{external/system call={pdflatex \tikzexternalcheckshellescape -halt-on-error -interaction=batchmode -jobname "\image" "\texsource"}}
\tikzexternalize[prefix=figures/cache/] %,up to date check=md5]
% Colors
\definecolor{tape}{rgb}{.9,.9,.9}
\definecolor{transition}{rgb}{.1,.4,.9}
\definecolor{quantum}{rgb}{1,.8,.1}
\newcommand{\ta}{.8}
\newcommand{\dx}{.175}
\tikzfading[name=fade down, top color=transparent!0, bottom color=transparent!100]
\tikzfading[name=fade up, top color=transparent!100, bottom color=transparent!0]
\pgfdeclarelayer{blurb}
\pgfdeclarelayer{pipe}
\pgfdeclarelayer{tape}
\pgfdeclarelayer{quantum}
\pgfsetlayers{background,blurb,pipe,tape,quantum,main}
% Graph environments
% need to use environ package to work with externalizing tikz for caching
\usepackage{environ}
\NewEnviron{tape}[1][1]{%
%\newenvironment{tape}[1][1]{%
%expand body command exactly once, then take md5 sum from it
\tikzsetnextfilename{\pdfmdfivesum{\expandafter\detokenize\expandafter\expandafter\expandafter{\csname BODY\endcsname}}}%
\begin{tikzpicture}[
tape/.style = {fill = tape, draw = tape, line width=\dx\ts, align = center, rounded corners=.1\ts},
debug/.style = {fill = none, draw = none},
quantum/.style = {fill = quantum, draw = quantum, line width=\dx\ts, align = center, rounded corners=.1\ts},
transition/.style = {fill = transition, draw=none, line width=\dx\ts},
draw=black,
line width=.08\ts,
baseline = #1,
x=\ta\ts,y=\ts
]
%}{
\BODY
\begin{pgfonlayer}{tape}
\draw[tape] (0,0) rectangle (\thetx+\thetx*\dx-\dx,1);
\end{pgfonlayer}
\draw[debug] (current bounding box.north east) rectangle (current bounding box.south west);
\end{tikzpicture}%
}
% Tape symbol macro
\makeatletter
\newcommand\tapesymbols[1]{%
\@tapesymbols#1\@nnil
}
\def\@tapesymbols#1{%
\ifx\@nnil#1\relax\else%
\@nameuse{tapesymbols@char@#1\expandafter}%
\fi
}
\DeclareDocumentCommand \defcharcode { m O{} O{} m }{
\@namedef{tapesymbols@char@#1}#2#3{
\begin{scope}[shift={(\thetx + \thetx*\dx,0)}]
\draw[debug] (0,0) rectangle (\ta\ts,\ts);
\begin{pgfinterruptboundingbox}
#4
\end{pgfinterruptboundingbox}
\end{scope}
\stepcounter{tx}
\@tapesymbols
}%
}
\makeatother
\DeclareDocumentCommand \inputinkscape{ m O{.01} }{
\begin{scope}[x=#2\ts,y=#2\ts,yscale=-1,shift={(0,-\ts)}]%have to give explicit units here
\InputIfFileExists{./figures/#1}{}{\input{#1}}
\end{scope}
}
% transition and penalty markers
\defcharcode{>}{
\draw[transition, path fading=fade up] (-\dx,-.2) rectangle (1+\dx,.3);
\addtocounter{tx}{-1}
}
\defcharcode{<}{
\draw[transition, path fading=fade down] (-\dx,.7) rectangle (1+\dx,1.2);
\addtocounter{tx}{-1}
}
\defcharcode{-}{
\begin{pgfonlayer}{quantum}
\draw[quantum] (0,0) rectangle (\ta\ts,\ts);
\end{pgfonlayer}
\addtocounter{tx}{-1}
}
\defcharcode{,}{
\begin{pgfonlayer}{quantum}
\draw[quantum] (0,0) rectangle (2*\ta\ts+6*\dx,\ts);
\end{pgfonlayer}
\addtocounter{tx}{-1}
}
% rhombus
\newcommand{\rhombus}[1]{
\draw[#1] (.1,.5) -- (.5,.8) -- (.9,.5) -- (.5,.2) -- cycle;
}
% symbols
\defcharcode{|}{
\draw[double=tape] (.5,0) -- (.5,1);
}
\defcharcode{!}{
\draw[decorate, decoration={coil, aspect=0, amplitude=.04cm, segment length=0.07cm}] (.5,0) -- (.5,1);
}
\defcharcode{?}{
\draw[line width=1.5*\dx\ts,black] (.5,0) -- (.5,1);
}
\defcharcode{o}{
\draw[rounded corners=.2] (.1,.1) rectangle (.9,.9);
}
\defcharcode{O}[#1]{
\draw[rounded corners=.2,fill=black] (.05,.05) rectangle (.95,.95);
\ifx#1T
\node[text centered,text height=5,scale=.7,white] at (.5,.4) {\textbf{\textup{T}}};
\else\ifx#1U
\node[text centered,text height=5,scale=.7,white] at (.5,.4) {\textbf{\textup{U}}};
\else\ifx#1A
\node[text centered,text height=5,scale=.7,white] at (.5,.4) {\textbf{\textup{A}}};
\else\ifx#1H
\node[text centered,text height=5,scale=.7,white] at (.5,.4) {\textbf{\textup{H}}};
\else\ifx#1S
\node[text centered,text height=5,scale=.7,white] at (.5,.4) {\textbf{\textup{S}}};
\else
\node[text centered,text depth=1,white] at (.5,.4) {$#1$};
\fi\fi\fi\fi\fi
}
\defcharcode{.}{
\fill (.33,.5) circle [radius=.1];
\fill (1,.5) circle [radius=.1];
\fill (1.66,.5) circle [radius=.1];
\stepcounter{tx}
}
\defcharcode{G}{
\inputinkscape{ghost}
}
\defcharcode{B}{
\inputinkscape{ghostb}
}
\defcharcode{g}{
\inputinkscape{ighost}
}
\defcharcode{b}{
\inputinkscape{ighostb}
}
\defcharcode{I}{
\inputinkscape{initializer}
}
\defcharcode{+}{
\draw[fill,rounded corners=.2] (.1,0) -- (.1,1) -- (1,.5) -- cycle;
\begin{scope}[line width=1,white,line cap=round]
\draw (0.2,.5) -- (0.7,.5);
\draw (0.45,.25) -- (.45,.75);
\end{scope}
}
\defcharcode{D}{
\draw[fill,rounded corners=.2] (.1,0) -- (.1,1) -- (1,.5) -- cycle;
}
\defcharcode{X}{
\draw[rounded corners=.2] (.1,0) -- (.1,1) -- (1,.5) -- cycle;
}
\defcharcode{Y}{
\draw[rounded corners=.2] (.1,0) -- (.1,1) -- (1,.5) -- cycle;
\draw[rounded corners=.2] (.3,.3) -- (.3,.7) -- (.65,.5) -- cycle;
}
\defcharcode{Z}{
\draw[rounded corners=.2] (.9,0) -- (0,.5) -- (.9,1) -- cycle;
}
\defcharcode{C}{
\draw[fill, rounded corners=.2] (.9,0) -- (0,.5) -- (.9,1) -- cycle;
}
\defcharcode{:}[#1]{
\ifx#1T
\node[text centered,text height=5,scale=.7] at (.5,.35) {\textbf{\textup{T}}};
\else\ifx#1U
\node[text centered,text height=5,scale=.7] at (.5,.35) {\textbf{\textup{U}}};
\else\ifx#1A
\node[text centered,text height=5,scale=.7] at (.5,.35) {\textbf{\textup{A}}};
\else\ifx#1H
\node[text centered,text height=5,scale=.7] at (.5,.35) {\textbf{\textup{H}}};
\else\ifx#1S
\node[text centered,text height=5,scale=.7] at (.5,.35) {\textbf{\textup{S}}};
\else
\node[text centered,text height=5] at (.5,.4) {$#1$};
\fi\fi\fi\fi\fi
}
\defcharcode{;}[#1]{
\node[text centered,text height=5,text depth=-0.2] at (.6,.4) {$\dot{#1}$};
}
\defcharcode{"}[#1]{
\node[text centered,text height=5,text depth=-0.2] at (.6,.4) {$\ddot{#1}$};
}
\defcharcode{*}[#1]{
\node[text centered,text height=5,text depth=-0.2] at (.6,.4) {$\vec{#1}$};
}
\defcharcode{@}[#1]{
\draw[fill = black] (0,0) -- (0,1) -- (.6,1) -- (1,.5) -- (.6,0) -- cycle;
\ifx#1r
\rhombus{fill=white,draw=none}
\else\ifx#1T
\node[text centered,text height=5,scale=.7,white] at (.4,.4) {\textbf{\textup{T}}};
\else\ifx#1U
\node[text centered,text height=5,scale=.7,white] at (.4,.4) {\textbf{\textup{U}}};
\else\ifx#1A
\node[text centered,text height=5,scale=.7,white] at (.4,.4) {\textbf{\textup{A}}};
\else\ifx#1H
\node[text centered,text height=5,scale=.7,white] at (.4,.4) {\textbf{\textup{H}}};
\else\ifx#1S
\node[text centered,text height=5,scale=.7,white] at (.4,.4) {\textbf{\textup{S}}};
\else
\node[text centered,text height=5,white] at (.4,.4) {$#1$};
\fi\fi\fi\fi\fi\fi
}
\defcharcode{r}{
\rhombus{}
}
\defcharcode{R}{
\rhombus{fill=black}
}
\defcharcode{w}{
\draw (.1,.6) -- (.5,.9) -- (.9,.6);
\draw (.1,.4) -- (.5,.1) -- (.9,.4);
}
% tape macro
\newlength{\ts}
\newcounter{tx}
\DeclareDocumentCommand \foo { O{0} m } {%
\settoheight{\ts}{Z}%
\setlength{\ts}{1.2\ts}%
\setcounter{tx}{0}%
\begin{tape}
\draw[debug] (-#1-#1*\dx-\dx,0) -- (0,1);
\tapesymbols{#2}
\end{tape}%
}
\newenvironment{rules}{%
\renewcommand{\arraystretch}{0.8}%
\begin{tabular}[t]{@{}l@{}}
}{
\end{tabular}%
}
\newcommand{\rvdots}{\multicolumn{1}{c}{\vdots}}
\begin{document}
\begin{rules}
\foo[0]{|>I>-:a:c.-:a:c:c b|}\\
\foo[1]{<-:a<>I>:c}\\
\foo[2]{<:c<I}\\
\rvdots\\
\foo[6]{:c>I>:cb|}\\
\foo[7]{<:c<>I>b|}\\
\foo[0]{|-:a:c.-:a:c:c<o<B|}
\end{rules}
\end{document}
我认为问题是由\DeclareDocumentCommand
(采用可选参数)和rules
环境的结合引起的。
关于如何修复此问题同时保持相同功能,有什么建议吗?
笔记:我的文档以前编译得很好,但在我更新解析包裹最近。
答案1
\foo
是不可扩展的(由于[...]
参数),所以尝试\DeclareExpandableDocumentCommand
,但我想,可能有比使用\foo
这种方式更好的方法。
\documentclass{article}
\usepackage{xparse}
\newenvironment{rules}{%
\tabular{l}
}{
\endtabular%
}
\DeclareExpandableDocumentCommand\foo{ O{0} m } {%
}
\begin{document}
\begin{rules}
\foo[0]{}
\end{rules}
\end{document}