2011-03-02 40 views
4

上的文檔pageGeneral::stop我們讀到:更改常規的行爲::停止,主循環

的 指示的消息已經在一個單一的生成 第三次後產生此消息 評價

消息被抑制 以防止冗長或重複的 郵件長計算。

我的問題是,通過MathLink工作時,我通過每一個點作爲一個單一的評價等General::stop永遠不會出現。

例如,如果我定義:

link = LinkLaunch[First[$CommandLine] <> " -mathlink"] 
f[z_?NumericQ] := ([email protected][link]; 
    LinkWrite[link, 
    Unevaluated[ 
    EnterExpressionPacket[NIntegrate[Sin[1/x], {x, .001, z}]]]]; 
    While[Head[packet = LinkRead[link]] =!= OutputNamePacket, 
    Print[packet]]; [email protected][link]); 
Plot[f[z], {z, 1, 10}, PlotPoints -> 6, MaxRecursion -> 0] 

我得到許多Message包爲f[z]許多評估。當然,我想要在生成相同的消息3次後,在從內核中停止消息生成了General::stop。有沒有辦法做到這一點?

在文檔頁面$MessageList我們讀到

隨着標準數學主 循環,$ MessageList中的重置爲{}當 特定輸入 線的處理完成。

而且tutorial/Messages在頁面上,我們讀到:

在你做的每一個計算, 數學維護一個列表 產生的所有消息的 $ MessageList中。 在標準Mathematica會話, 這個列表被清除後產生輸出每行 。

可能是這是爲什麼General::stop沒有出現?如果確實有什麼方法可以控制主循環的這一方面?有沒有辦法創建這樣一個非標準的Mathematica會話?

編輯: 看來我的假設是正確的。如果我們將所有的消息後清除$MessageList,然後General::stop從未出現:

Unprotect[$MessageList] 
Do[$MessageList = {}; 1/0, {10}] 

所以問題仍然存在:如何禁用自動生成輸出後清零$MessageList

+0

是將MessageList [n]的有用嗎? – 2011-03-02 17:08:00

+0

@Brett問題的根源在於從內核認爲所有的評估都是分開的,並在每個評估之後清除'$ MessageList'。它可以很容易地模擬: 'Unprotect [$ MessageList]; 做[$ MessageList = {}; 1/0,{20}]'。 這段代碼不會停止生成相同的消息,並且'General :: stop'永遠不會出現。 – 2011-03-02 17:12:14

+0

在頁面'教程/ Messages'我們讀到: 「在你做的每一個計算,*數學* 維護一個列表'所有 所產生的消息的$ MessageList' 在一個標準的*數學*會話。 在生成每行輸出後,該列表被清除 。「 這給了我一個希望,即有一種方法可以創建一個非標準的 * Mathematica *會話,其中在生成每行輸出後,$ MessageList不會被清除。 – 2011-03-02 17:15:19

回答

0

我已經找到了解決辦法。它再次利用elegant hack by Todd Gayley。這是(當然,它必須在從內核評估):

$globalMessageList = {}; 
Unprotect[Message]; 
Message[args___] := 
    Block[{$inMsg = True, $MessageList = $globalMessageList}, 
    Message[args]; 
    $globalMessageList = $MessageList; 
    ] /; ! TrueQ[$inMsg]; 
Protect[Message]; 

一個通過檢查的$Line當前值,並將它與先前的值進行比較,可以完全模擬在從內核信息的標準行爲:

If[TrueQ[$Line > lastLine], 
LinkWrite[$kern, 
    Unevaluated[ExpressionPacket[$globalMessageList = {};]]]; 
LinkRead[$kern]]; lastLine = $Line; 

:)

1

有可能是更好的解決方案,但這似乎工作。據我所知,所有重要的是你有一些持續變量在奴隸內核積累消息。

link = LinkLaunch[First[$CommandLine] <> " -mathlink"] 
f[z_?NumericQ] := 
([email protected][link]; 
LinkWrite[link, Unevaluated[EnterExpressionPacket[ 
    If[! ValueQ[oldMessageList], oldMessageList = {}]; 
    Block[{$MessageList = oldMessageList}, 
    Module[{result}, 
    oldMessageList = 
    Join[oldMessageList, (result = 
     NIntegrate[Sin[1/x], {x, .001, z}]; $MessageList)]; 
    result 
    ]]]]]; 
While[Head[packet = LinkRead[link]] =!= OutputNamePacket, 
Print[packet]]; [email protected][link]); 

Plot[f[z], {z, 1, 10}, PlotPoints -> 6, MaxRecursion -> 0] 

HTH