Rob*_*t H 6 wolfram-mathematica
当我评估一个单元格中的函数时,Mathematica说
ToExpression::notstrbox: {At Line = 6, the input was:,$Failed,InString[6]}
is not a string or a box. ToExpression can only interpret strings or boxes
as Mathematica input. >>
细胞右边缘变红.
如何找到错误位置?
实际上,内核总是将输入字符串中的第一个语法错误的位置发送到FrontEnd(如果此输入字符串包含错误).可以使用以下MathLink代码演示:
In[32]:= link = LinkLaunch[First[$CommandLine] <> " -mathlink"];
LinkRead[link];
LinkWrite[link, EnterTextPacket["2+"]]
LinkRead[link]
LinkRead[link]
LinkRead[link]
Out[35]= MessagePacket[Syntax, "sntxi"]
Out[36]= TextPacket["Syntax::sntxi: Incomplete expression; more input is needed.
"]
Out[37]= SyntaxPacket[5]
Run Code Online (Sandbox Code Playgroud)
SyntaxPacket根据文档,"表示在输入行中检测到语法错误的位置"中的整数.最初令人困惑的是,在输入行" 2+" 的情况下,这个位置显然超出了输入行的末尾.但实际上这个位置似乎是InputForm输入线的计数,在这种情况下是:" 2+\n\n".
我们可以通过以下$SyntaxHandler定义检查它的工作原理:
In[41]:= link = LinkLaunch[First[$CommandLine] <> " -mathlink"];
LinkRead[link]
LinkWrite[link,
EnterTextPacket[
"$SyntaxHandler=
Function[{str,pos},
Print["Input string: ",ToString[str,InputForm]];
Print["Position of syntax error: ",pos];
$Failed
];
"]]
LinkRead[link]
LinkWrite[link, EnterTextPacket["2+"]]
While[Head[packet = LinkRead[link]] =!= InputNamePacket,
Print[packet]]; Print[packet]
Out[42]= InputNamePacket["In[1]:= "]
Out[44]= InputNamePacket["In[2]:= "]
During evaluation of In[41]:= MessagePacket[Syntax,sntxi]
During evaluation of In[41]:= TextPacket[Syntax::sntxi: Incomplete expression; more input is needed.
]
During evaluation of In[41]:= TextPacket[Input string: "2+\n\n"
]
During evaluation of In[41]:= TextPacket[Position of syntax error: 6
]
During evaluation of In[41]:= SyntaxPacket[5]
During evaluation of In[41]:= InputNamePacket[In[2]:= ]
Run Code Online (Sandbox Code Playgroud)
人们可以看到报同样的语法错误的位置之间的矛盾SyntaxPacket,并通过$SyntaxHandler.但似乎有可能理解它们如何计算位置:InputForm输入线的使用和输入线的编号为0 之前的位置,$SyntaxHandler以及编号为1的位置SyntaxPacket.通过这种方式,我们可以定义$SyntaxHandler获取输入字符串内部语法错误位置的精确可视化表示(输入Cell必须具有"RawInputForm"样式),如下所示:
$SyntaxHandler =
Function[{str, pos},
Print["Input string: ", ToString[str, InputForm], "\n",
"Position of syntax error: ", pos, "\n",
StringInsert[ToString[str, InputForm],
ToString[Style["\[DownArrowBar]", Red, Background -> Yellow],
StandardForm], pos + 2]]; $Failed];
Run Code Online (Sandbox Code Playgroud)
我会再次强调输入单元格必须具有"RawInputForm"样式!可以通过创建普通的空输入单元然后通过Cell -> Convert To菜单中的适当命令将其转换为"RawInputForm"单元来创建这样的单元.
让我们看看它是如何工作的:

$SyntaxHandler当输入以a的形式发送到内核时,我们必须使用"RawInputForm"单元格的原因可能就是应用String,而不是Boxes像默认StandardForm输入单元格那样.
你ToExpression在用字符串打电话给自己吗?该函数SyntaxLength将在应用于字符串时为您提供第一个语法错误的字符偏移量,例如:
In[26]:= SyntaxLength["2+"]
Out[26]= 4
In[27]:= SyntaxLength["x[1]+x[2]]"]
Out[27]= 9
Run Code Online (Sandbox Code Playgroud)
请注意,如文档中所示,当SyntaxLength返回超出输入字符串末尾的位置时,这意味着表达式到目前为止在语法上是正确的,但不完整.否则,SyntaxLength有效地返回第一个语法错误的位置.
如果您没有明确地调用ToExpression某些内容,则可能有助于查看相关单元格.