Skip to main content

programming - How to use Mathematica functions in Python programs?


I'd like to know how can I call Mathematica functions from Python.


I appreciate a example, for example, using the Mathematica function Prime.


I had search about MathLink but how to use it in Python is a little obscure to me.


I tried to use a Mathematica-Python library called pyml but I hadn't no sucess, maybe because this lib looks very old (in tutorial says Mathematica 2 or 3).


So, someone knows a good way to write python programs who uses Mathematica functions and can give me an example?


Old Edit:


Maybe this edit can help someone who wants to use mathlinks directly.


To another solution, please see the answer accepted.


Using the Wolfram/Mathematica/8.0/SystemFiles/Links/Python I could had sucess in compiling the module changing some things in setup.py.



My architechture is x86-64.


1-Change the mathematicaversion to 8.0.


2-Changing the lib name ML32i3 to ML64i3.


3-Copying the file Wolfram/Mathematica/8.0/SystemFiles/Libraries/Linux-x86-64/libML64i3.so to the path pointed in setup.py library_dirs = ["/usr/local/Wolfram/Mathematica/" + mathematicaversion + "/SystemFiles/Links/MathLink/DeveloperKit/Linux/CompilerAdditions"].


5-Compiling the source with sudo python setup.py build.


6-Installing the lib with sudo python setup.py install


4-Editing the file /etc/ld.so.conf and putting the line include /usr/local/lib.


5-Creating a directory in /usr/local/lib/python2.6/dist-packages/mathlink with the lib libML64i3.so.


6-Running sudo ldconfig


I had tested the scripts guifrontend.py with python guifrontend.py -linkname "math -mathlink" -linkmode launch and textfrontend.py with python textfrontend.py -linkname "math -mathlink" -linkmode launch and worked fine.



Looks like I almost. But the script


>>> from mathlink import *
>>> import exceptions,sys, re, os
>>> from types import ListType
>>> mathematicaversion = "8.0"
>>> os.environ["PATH"] = "/usr/local/Wolfram/Mathematica/" + mathematicaversion + ":/usr/local/bin:/usr/bin:/bin"
>>> e = env()
>>> sys.argv=['textfrontend.py', '-linkname', 'math -mathlink', '-linkmode', 'launch']
>>> kernel = e.openargv(sys.argv)
>>> kernel.connect()

>>> kernel.ready()
0
>>> kernel.putfunction("Prime",1)
>>> kernel.putinteger(10)
>>> kernel.flush()
>>> kernel.ready()
0
>>> kernel.nextpacket()
8
>>> packetdescriptiondictionary[3]

'ReturnPacket'
>>> kernel.getinteger()
Traceback (most recent call last):
File "", line 1, in
mathlink.error: MLGet out of sequence.

breaks in the last command and I don't know why. How can I fix this?



Answer



This solution can work with several programming languages. Check this GitHub repository of mine.


See this link.



I have found a solution. Works fine to me.


Steps:


1-Create a script named runMath with the content:


#!/usr/bin/env wolframscript
# for certain older versions of Mathematica replace 'wolframscript' by
# 'MathematicaScript -script' in the shebang line

value=ToExpression[$ScriptCommandLine[[2]]];

(*The next line prints the script name.*)

(*Print[$ScriptCommandLine[[1]]];*)

Print[value];

2-I gave execution privilege to the file.


sudo chmod +x runMath

3-Moved the file to the execution path


sudo mv runMath /usr/local/bin/


4-Created a new script called run with the content:


#!/usr/bin/python
from subprocess import *
from sys import *

command='/usr/local/bin/runMath'
parameter=argv[1]

call([command,parameter])


5-Moved to the execution path


sudo mv run /usr/local/bin

6-Finally, tested it:


$run Prime[100]
541

$run 'Sum[2x-1,{x,1,k}]'
k^2


$run Integrate[Log[x],x]
-x + x*Log[x]

$run 'Zeta[2]'
Pi^2/6

You can use with ou without '. The ' are needed to command with spaces.


$run 'f[n_] := f[n] = f[n - 1] + f[n - 2]; f[1] = f[2] = 1; Table[f[n],{n,5}]'
{1, 1, 2, 3, 5}


Happy!


Comments

Popular posts from this blog

mathematical optimization - Minimizing using indices, error: Part::pkspec1: The expression cannot be used as a part specification

I want to use Minimize where the variables to minimize are indices pointing into an array. Here a MWE that hopefully shows what my problem is. vars = u@# & /@ Range[3]; cons = Flatten@ { Table[(u[j] != #) & /@ vars[[j + 1 ;; -1]], {j, 1, 3 - 1}], 1 vec1 = {1, 2, 3}; vec2 = {1, 2, 3}; Minimize[{Total@((vec1[[#]] - vec2[[u[#]]])^2 & /@ Range[1, 3]), cons}, vars, Integers] The error I get: Part::pkspec1: The expression u[1] cannot be used as a part specification. >> Answer Ok, it seems that one can get around Mathematica trying to evaluate vec2[[u[1]]] too early by using the function Indexed[vec2,u[1]] . The working MWE would then look like the following: vars = u@# & /@ Range[3]; cons = Flatten@{ Table[(u[j] != #) & /@ vars[[j + 1 ;; -1]], {j, 1, 3 - 1}], 1 vec1 = {1, 2, 3}; vec2 = {1, 2, 3}; NMinimize[ {Total@((vec1[[#]] - Indexed[vec2, u[#]])^2 & /@ R...

functions - Get leading series expansion term?

Given a function f[x] , I would like to have a function leadingSeries that returns just the leading term in the series around x=0 . For example: leadingSeries[(1/x + 2)/(4 + 1/x^2 + x)] x and leadingSeries[(1/x + 2 + (1 - 1/x^3)/4)/(4 + x)] -(1/(16 x^3)) Is there such a function in Mathematica? Or maybe one can implement it efficiently? EDIT I finally went with the following implementation, based on Carl Woll 's answer: lds[ex_,x_]:=( (ex/.x->(x+O[x]^2))/.SeriesData[U_,Z_,L_List,Mi_,Ma_,De_]:>SeriesData[U,Z,{L[[1]]},Mi,Mi+1,De]//Quiet//Normal) The advantage is, that this one also properly works with functions whose leading term is a constant: lds[Exp[x],x] 1 Answer Update 1 Updated to eliminate SeriesData and to not return additional terms Perhaps you could use: leadingSeries[expr_, x_] := Normal[expr /. x->(x+O[x]^2) /. a_List :> Take[a, 1]] Then for your examples: leadingSeries[(1/x + 2)/(4 + 1/x^2 + x), x] leadingSeries[Exp[x], x] leadingSeries[(1/x + 2 + (1 - 1/x...

What is and isn't a valid variable specification for Manipulate?

I have an expression whose terms have arguments (representing subscripts), like this: myExpr = A[0] + V[1,T] I would like to put it inside a Manipulate to see its value as I move around the parameters. (The goal is eventually to plot it wrt one of the variables inside.) However, Mathematica complains when I set V[1,T] as a manipulated variable: Manipulate[Evaluate[myExpr], {A[0], 0, 1}, {V[1, T], 0, 1}] (*Manipulate::vsform: Manipulate argument {V[1,T],0,1} does not have the correct form for a variable specification. >> *) As a workaround, if I get rid of the symbol T inside the argument, it works fine: Manipulate[ Evaluate[myExpr /. T -> 15], {A[0], 0, 1}, {V[1, 15], 0, 1}] Why this behavior? Can anyone point me to the documentation that says what counts as a valid variable? And is there a way to get Manpiulate to accept an expression with a symbolic argument as a variable? Investigations I've done so far: I tried using variableQ from this answer , but it says V[1...