我试图找出Message
行为的逻辑。
考虑以下评估:
On[]
Sin[1,1]
评估完上述内容后,您将获得大约830(!)Messages
(在 Mathematica 7中)。
所有这些Messages
在制作过程中出现:
Sin::argx: Sin called with 2 arguments; 1 argument is expected. >>
(这是一个但最后Message
)。
最后Message
Message::trace: Message[Sin::argx,Sin,2] --> Null. >>
对应于完成内部 Mathematica 的Message
函数的工作。大多数其他Messages
来自对$NewMessage
和$MessagePrePrint
的评估。
我的问题是:
1)为什么没有Message
代的无限循环?如果调用Message[Sin::argx,Sin,2]
产生超过830个其他Messages
,为什么每个Messages
都不会产生相似数量的Message
?如何模拟这种行为(通过编写Message
的模拟?)
2)在跟踪模式中调用它时,是否可以强制Messages
不产生任何额外的On[]
(我的意思是评估{{1}}后的模式)?
答案 0 :(得分:0)
我不明白为什么有必要使用On
打开所有邮件。你不仅可以激活你需要的子集。 “更多信息”部分中On
的参考页面列出了您可能会发现有用的各种类别。如果您选择按照规定继续操作,则可以在On[]
之后立即关闭跟踪消息来禁止跟踪消息:
On[]; Off[General::trace];
Sin[1, 1]
这只输出两条消息。因此,您看到的830条消息是::跟踪消息,并且源于执行一些不一定与消息相关的顶级代码,可能是排版...
答案 1 :(得分:0)
似乎我找到了一种方法来实现内置函数Message
我想要的东西:
Unprotect[Message];
Message[_, HoldForm[Block[List[$MyMagicalTag$, ___], _]], _] := Null;
Message[args___] /;
Block[{$MyMagicalTag$, Message}, Not@TrueQ[inMsg]] :=
Block[{$MyMagicalTag$, inMsg = True, lastargs = HoldComplete[args]},
Message[args]];
Message[args___] /;
Block[{$MyMagicalTag$,
Message}, (inMsg && (HoldComplete[args] =!= lastargs))] := Null;
Protect[Message];
现在事情按预期工作:
In[6]:= On[]
In[7]:= Sin[1,1]//AbsoluteTiming
During evaluation of In[7]:= Message::trace: Message[Sin::argx,Sin,2] --> Block[{$MyMagicalTag$,inMsg=True,lastargs=HoldComplete[Sin::argx,Sin,2]},Message[Sin::argx,Sin,2]]. >>
During evaluation of In[7]:= Sin::argx: Sin called with 2 arguments; 1 argument is expected. >>
During evaluation of In[7]:= AbsoluteTiming::trace: AbsoluteTiming[Sin[1,1]] --> {0.1502160,Sin[1,1]}. >>
Out[7]= {0.1502160,Sin[1,1]}
上面唯一的问题是,从时间上看,CPU负载仍然很高。
其他测试案例也能正常运作:
In[8]:= 1+1//AbsoluteTiming
During evaluation of In[8]:= Plus::trace: 1+1 --> 2. >>
During evaluation of In[8]:= AbsoluteTiming::trace: AbsoluteTiming[1+1] --> {0.0400576,2}. >>
Out[8]= {0.0400576,2}
感谢Mr.Wizard的help。