1

I was trying to use Jacobi elliptical function from mpmath, but getting the error for the simple code given below:

import numpy as np
import scipy.integrate as spi
from scipy import special as sp
import matplotlib.pyplot as plt
from math import sqrt, pow, log
from mpmath import ellipfun

sn = ellipfun('sn')
y=sn(0.5,-1)
print y

y1=y.real
print y1, np.arcsin(y), np.arcsin(y1)

I am getting the error even when I pass only the real part of the function sn(0.5,-1). I don't know whether I am making a mistake. Kindly help. Thanks in advance.

1
  • I need other packages for rest of my program. So I import them. Commented Jun 19, 2017 at 12:25

1 Answer 1

5

y is an mpc object, and y.real is an mpf object. numpy knows nothing about such objects, so when you call np.arcsin(y), the numpy code checks to see if the argument has an arcsin() method (that is, it looks for y.arcsin()). If it does, it will call that function to compute the arcsin. The mpc and mpf objects do not have such a method, which results in the error that you see. (It would be nice if the error message said something like "numpy does not know how to compute the arcsin of an mpf object".)

Here's the same behavior demonstrated with a different object:

In [10]: class Foo:
    ...:     pass
    ...: 

In [11]: f = Foo()

In [12]: np.arcsin(f)
---------------------------------------------------------------------------
AttributeError                            Traceback (most recent call last)
<ipython-input-12-aa4b1a80cd4e> in <module>()
----> 1 np.arcsin(f)

AttributeError: Foo instance has no attribute 'arcsin'

As pointed out in a comment by Hannebambel, you could use mpmath.asin instead of np.arcsin:

In [6]: import mpmath

In [7]: y = sn(0.5, -1)

In [8]: mpmath.asin(y)
Out[8]: mpc(real='0.52001273608158616', imag='0.0')

To use the numpy arcsin function, first convert to a plain floating point or complex by passing the mpc and mpf objects through the builtin functions complex() and float(), respectively:

In [19]: y
Out[19]: mpc(real='0.49689119041931196', imag='0.0')

In [20]: np.arcsin(float(y.real))
Out[20]: 0.52001273608158627

In [21]: np.arcsin(complex(y))
Out[21]: (0.52001273608158616+0j)

Or use math.asin instead of numpy.arcsin:

In [25]: import math

In [26]: math.asin(y.real)
Out[26]: 0.5200127360815863
Sign up to request clarification or add additional context in comments.

3 Comments

I would rather use mpmath.asin as this allows to stay within this arbitrary precision library. Returns a mpmath.ctx_mp_python.mpf object, not a float like 'math.asin'.
@Hannebambel Yes, that makes sense. I assumed Satadru has a reason for using np.arcsin, but maybe it was just lack of awareness of mpmath.asin. I have updated my answer.
Yes, I did not know about mpmath.asin. Actually I am very armature in python.

Your Answer

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

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.