(MathLink) 正确处理从属内核生成的消息
当使用从属内核处理 MathLink
时,我在正确解析 TextPacket
时遇到问题。特别是当这样的数据包对应于从属内核生成的Message
时,我根本不明白如何正确处理它。我需要在评估笔记本中打印这样的消息,就好像它们是由主内核生成的一样(但有一些标记以表明它来自从属内核)。我需要将与 Message
对应的 TextPacket
与仅 Print[]
命令分开。后者我也需要正确解析,将它们打印在评估笔记本中,并带有一点标记,表明它来自从属内核。
以下是所发生情况的示例:
link = LinkLaunch[First[$CommandLine] <> " -mathlink"]
Print@LinkRead[link]
LinkWrite[link,
Unevaluated[EnterExpressionPacket[Print[a]; 1/0; Print[b]]]]
While[Not@MatchQ[packet = LinkRead[link], InputNamePacket[_]],
Print[packet]]
默认情况下,Message
通过 MathLink
的形式:
TextPacket[ 1
Power::infy: Infinite expression - encountered.
0]
它看起来很丑。我发现让它变得更好的唯一方法是在从属内核中进行评估,
$MessagePrePrint = InputForm;
但我认为应该有更直接的解决方案。特别是在以这种方式处理时,我得到了带有 HoldForm
的 TextPacket
:
TextPacket[Power::infy: Infinite expression HoldForm[0^(-1)] encountered.]
我不知道如何将此类字符串转换为适合作为 Message 打印的形式
。
PS这个问题来自那个问题。
When working through MathLink
with slave kernel I have a problem with correct parsing TextPacket
s. In particular when such packet corresponds to a Message
generated by the slave kernel I do not understand how to handle it correctly at all. I need such Messages
to be printed in the evaluation notebook as if they were generated by master kernel (but with some mark to make clear that it comes from the slave). And I need to separate TextPacket
s corresponding to Message
s from just to Print[]
commands. The latter I need to parse correctly too, printing them in the evaluation notebook with a little mark that it is from the slave kernel.
Here is an example of what happens:
link = LinkLaunch[First[$CommandLine] <> " -mathlink"]
Print@LinkRead[link]
LinkWrite[link,
Unevaluated[EnterExpressionPacket[Print[a]; 1/0; Print[b]]]]
While[Not@MatchQ[packet = LinkRead[link], InputNamePacket[_]],
Print[packet]]
The Message
by default comes through MathLink
in the form:
TextPacket[ 1
Power::infy: Infinite expression - encountered.
0]
It looks ugly. The only way to make it better I have found is to evaluate in the slave kernel
$MessagePrePrint = InputForm;
But I think there should be more straightforward solution. In particular when dealing this way I get TextPacket
s with HoldForm
s inside:
TextPacket[Power::infy: Infinite expression HoldForm[0^(-1)] encountered.]
I do not know how to convert such string into a form appropriate for printing as a Message
.
P.S. This question comes from that question.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
我想分享 Todd Gayley(Wolfram Research)针对给定问题提出的一个很好的技巧。也许对某人有用,对我也有用。这个技巧以相当优雅的方式解决了所讨论的问题。
高级方法:所有内容都打印在 StandardForm 中
为了在
StandardForm
中返回除输出之外的所有内容,我们可以重新定义变量$Pre
和$Post
以特殊方式从属内核(应在从属内核中评估以下代码):I would like to share a nice hack proposed by Todd Gayley (Wolfram Research) in connection with the given question. Perhaps for somebody it will be useful as also for me. This hack solves the problem in question in rather elegant way.
Advanced approach: everything is printed in the StandardForm
For having everything except output returned in
StandardForm
we could redefine variables$Pre
and$Post
in the slave kernel in a special way (the following code should be evaluated in the slave kernel):该表达式始终以 HoldForm 形式出现,但对于默认的 $MessagePrePrint 则不是
呈现。尝试评估
实现所需行为的一种方法是实现您自己的框渲染器。要查看渲染器必须处理的内容,请
在从属设备中进行设置。就像这样:
The expression comes in HoldForm always, but with the default $MessagePrePrint it is not
rendered. Try evaluating
One way to achieve your desired behavior would be to implement your own box renderer. To see that the renderer has to process, set
in the slave. Like so: