6
$\begingroup$

For example, equation Sin[10*x]-Log[x]==0 can't be solved by NSolve. Mathematica returns message "NSolve::nsmet". How can I get messages in my c# program?

IKernelLink kl = MathLinkFactory.CreateKernelLink();
kl.WaitAndDiscardAnswer();
kl.ComplexType = typeof(Complex);
kl.Evaluate("x/.NSolve[" + equation + ",x]");
kl.WaitForAnswer();
Complex[] res = (Complex [])kl.GetComplexArray();
//some code
kl.Close();
$\endgroup$
2
  • $\begingroup$ I believe the kernel will return a MessagePacket $\endgroup$
    – Szabolcs
    Nov 30, 2013 at 17:59
  • $\begingroup$ But how can I get this MessagePacket in my program? I tried to do this via MessageArrived event. $\endgroup$
    – user10884
    Nov 30, 2013 at 18:26

2 Answers 2

7
$\begingroup$

The "messages" handled by the MessageArrived event are MathLink messages (like interrupt requests), not Mathematica warning messages. Mathematica messages are delivered as part of the stream of packets. To get them in your program, use the PacketArrived event.

Here is an example. Note that messages come as a MessagePacket followed by a TextPacket, and for many uses all you want is the TextPacket, which contains the full text of the message.

IKernelLink kl = MathLinkFactory.CreateKernelLink();
kl.WaitAndDiscardAnswer();

// Added:
kl.PacketArrived += new PacketHandler(myPacketHandler);

kl.ComplexType = typeof(Complex);
kl.Evaluate("x/.NSolve[" + equation + ",x]");
kl.WaitForAnswer();
Complex[] res = (Complex [])kl.GetComplexArray();
//some code
kl.Close();

elsewhere:

private static bool lastPktWasMsg = false;

private static bool myPacketHandler(IKernelLink ml, PacketType pkt) {
    switch (pkt) {
        case PacketType.Text:
            if (lastPktWasMsg)
                Console.WriteLine(ml.GetStringCRLF());
            break;
        default:
            break;
    }
    lastPktWasMsg = pkt == PacketType.Message;
    return true;
}
$\endgroup$
2
$\begingroup$

You can also use the MathKernel object to do your computations, which has more overhead, but has more power and convenience also. Your code would look like this:

Wolfram.NETLink.MathKernel kernel = new Wolfram.NETLink.MathKernel();
kernel.Compute("x/.NSolve[" + equation + ",x]");

My favorite properties of MathKernel are

1) The computation result, stored in the object kernel.Result. This is an object, and you will generally want to cast it to a string in order to get the text result you seek. A good practice for doing this is to wrap your Mathematica command in "ToString[ ... , InputForm]", so that it will be nicely formatted.

2) The string array kernel.Messages, which is exactly what you were asking for. For successful computations, this array is generally length 0.

3) The image array kernel.Graphics, which will return any graphics results from commands, e.g. Plot.

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.