Are there suggestions how to convert a rather long Mathematica expression to Julia?
With Matlab I use http://library.wolfram.com/infocenter/MathSource/577/
I also would appreciate suggestions for the same problem with Sage Math
Are there suggestions how to convert a rather long Mathematica expression to Julia?
With Matlab I use http://library.wolfram.com/infocenter/MathSource/577/
I also would appreciate suggestions for the same problem with Sage Math
The closest thing to it is this
Use SymPy.jl. SymPy can parse Mathematica expressions, and SymPy.jl can convert SymPy expressions to Julia expressions. For example, if we define:
using SymPy
const sympy_parsing_mathematica = SymPy.PyCall.pyimport("sympy.parsing.mathematica")
mathematica2julia(s::AbstractString, substitutions::Pair{<:AbstractString,<:AbstractString}...) =
SymPy.lambdify_expr(sympy_parsing_mathematica["mathematica"](s, Dict(substitutions...))).args[2]
then we get:
julia> mathematica2julia("Log[Log[x]]")
:(log(log(x)))
julia> mathematica2julia("Exp[Log3[x]]", "Log3[x]"=>"log(x,3)")
:(x ^ (log(3) ^ -1))
Works charmingly well… thank you!
SymataSyntax
has not been upgraded for v1.0.
Ah, this stops working now for SymPy v1.0.10.
The updated code should be:
using SymPy
const sympy_parsing_mathematica = SymPy.PyCall.pyimport("sympy.parsing.mathematica")
mathematica2julia(s::AbstractString, substitutions::Pair{<:AbstractString,<:AbstractString}...) =
SymPy.walk_expression(sympy_parsing_mathematica."mathematica"(s, Dict(substitutions...)))
You may also find https://github.com/JuliaInterop/MathLink.jl helpful.
How to replace the unknown function?Naively the following code does not work.
mathematica2julia("(Sqrt[Pi])/(2*Gamma[23/10])","Gamma"=>"gamma")
PyError ($(Expr(:escape, :(ccall(#= /Users/gangchen/.julia/packages/PyCall/ttONZ/src/pyfncall.jl:44 =# @pysym(:PyObject_Call), PyPtr, (PyPtr, PyPtr, PyPtr), o, pyargsptr, kw))))) <class ‘ValueError’>
ValueError(“‘Gamma’ function form is invalid.”)
File “/Users/gangchen/.julia/conda/3/lib/python3.7/site-packages/sympy/parsing/mathematica.py”, line 17, in mathematica
parser = MathematicaParser(additional_translations)
File “/Users/gangchen/.julia/conda/3/lib/python3.7/site-packages/sympy/parsing/mathematica.py”, line 154, in init
d = self._compile_dictionary(additional_translations)
File “/Users/gangchen/.julia/conda/3/lib/python3.7/site-packages/sympy/parsing/mathematica.py”, line 187, in _compile_dictionary
raise ValueError(err)
The dictionary has to map a Mathematica function-call expression to a Python/SymPy function call:
julia> mathematica2julia("(Sqrt[Pi])/(2*Gamma[23/10])","Gamma[x]"=>"gamma(x)")
:(__prod__(1 / 2, pi ^ (1 / 2), gamma(23//10) ^ -1))
See the documentation for the sympy.parsing.mathematica.mathematica
function that is being called here.
Thanks. That works well
I got a Julia expression if I do this. How to turn expression that I get into a function?
you can use SyntaxTree.jl. The genfun is useful. You can also see the examples in my UseMathLink.jl
I eventually ended up using sage and copy paste to Julia since the syntax are quite similar. The only problem I found so far is that sage convert Exp(2)
from Mathematica to e^2
. But I often want it written as exp(2)
.
I am trying to run this now, but I got some errors. I tried to fix it and I got this function
using SymPy
const sympy_parsing_mathematica = SymPy.PyCall.pyimport("sympy.parsing.mathematica")
mathematica2julia(s::AbstractString, substitutions::Pair{<:AbstractString,<:AbstractString}...) =
SymPy.walk_expression(sympy_parsing_mathematica."parse_mathematica"(s))
When I now try, I get
mathematica2julia("(Sqrt[Pi])/(2*EllipticE[m])","EllipticE[x]"=>"elliptic_e(x)")
# :((1 / 2) * SymPy.__POW__(pi, 1 / 2) * SymPy.__POW__(EllipticE(m), -1))
My goal is to get
sqrt(pi) / (2*elliptic_e(m))
How can I get this?
You don’t really need the walk expression part, but you need to add the EllipticE function to help sympy out. This seems to work:
sympy_parsing_mathematica.mathematica(s, Dict("EllipticE[x]"=>"elliptic_e(x)"))
Thanks, but I don’t understand the suggestion.
Following what you wrote I tried to run:
sympy_parsing_mathematica.mathematica("(Sqrt[Pi])/(2*EllipticE[m])", Dict("EllipticE[x]"=>"elliptic_e(x)"))
I get a latex expression. But I actually want to get an expression I then can copy into a julia function like
Do you know how to do that?
Okay, the “POW” you are seeing was removed somewhat recently, and ^
should be used in the returned expression. You can update SymPy, or try passing in a dictionary holding the conversion, like SymPy.walk_expression(out, fns=Dict("Pow"=>:^))
.
Thanks again!
But I think the substitutions do not work anyway. In this example
mathematica2julia("(Sqrt[Pi])/(2*EllipticE[m])", "EllipticE[x]"=>"elliptic_e(x)")
# :((1 / 2) * SymPy.__POW__(pi, 1 / 2) * SymPy.__POW__(EllipticE(m), -1))
I get that EllipticE[m]
is not substituted by elliptic_e(m)
.
Github Copilot is quite good for these kind of tasks. I use it to convert from latex to Julia.