ldexp 和 frexp 在 python 中如何工作?

发布于 2024-08-12 18:35:00 字数 89 浏览 9 评论 0原文

python frexp 和 ldexp 函数将浮点数拆分为尾数和指数。 有谁知道这个过程是否公开了实际的浮点结构,或者是否需要 python 进行昂贵的对数调用?

The python frexp and ldexp functions splits floats into mantissa and exponent.
Do anybody know if this process exposes the actual float structure, or if it requires python to do expensive logarithmic calls?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

怀中猫帐中妖 2024-08-19 18:35:00

Python 2.6的math.frexp只是直接调用底层C库frexp。我们必须假设 C 库只是直接使用浮点表示的部分,而不是计算是否可用(IEEE 754)。

static PyObject *
math_frexp(PyObject *self, PyObject *arg)
{
        int i;
        double x = PyFloat_AsDouble(arg);
        if (x == -1.0 && PyErr_Occurred())
                return NULL;
        /* deal with special cases directly, to sidestep platform
           differences */
        if (Py_IS_NAN(x) || Py_IS_INFINITY(x) || !x) {
                i = 0;
        }
        else {  
                PyFPE_START_PROTECT("in math_frexp", return 0);
                x = frexp(x, &i);
                PyFPE_END_PROTECT(x);
        }
        return Py_BuildValue("(di)", x, i);
}

PyDoc_STRVAR(math_frexp_doc,
"frexp(x)\n"
"\n"
"Return the mantissa and exponent of x, as pair (m, e).\n"
"m is a float and e is an int, such that x = m * 2.**e.\n"
"If x is 0, m and e are both 0.  Else 0.5 <= abs(m) < 1.0.");

Python 2.6's math.frexp just calls the underlying C library frexp directly. We must assume that the C library simply uses the float representation's parts directly instead of calculating if avaliable (IEEE 754).

static PyObject *
math_frexp(PyObject *self, PyObject *arg)
{
        int i;
        double x = PyFloat_AsDouble(arg);
        if (x == -1.0 && PyErr_Occurred())
                return NULL;
        /* deal with special cases directly, to sidestep platform
           differences */
        if (Py_IS_NAN(x) || Py_IS_INFINITY(x) || !x) {
                i = 0;
        }
        else {  
                PyFPE_START_PROTECT("in math_frexp", return 0);
                x = frexp(x, &i);
                PyFPE_END_PROTECT(x);
        }
        return Py_BuildValue("(di)", x, i);
}

PyDoc_STRVAR(math_frexp_doc,
"frexp(x)\n"
"\n"
"Return the mantissa and exponent of x, as pair (m, e).\n"
"m is a float and e is an int, such that x = m * 2.**e.\n"
"If x is 0, m and e are both 0.  Else 0.5 <= abs(m) < 1.0.");
我是男神闪亮亮 2024-08-19 18:35:00

至于速度,这里有一个快速比较

$ python -m timeit -c 'from math import frexp' 'frexp(1.1)'
100000 loops, best of 3: 3.7 usec per loop

$ python -m timeit -c 'from math import log' 'log(1.1)'
100000 loops, best of 3: 3.7 usec per loop

$ python -m timeit -c 'from math import ldexp' 'ldexp(1.1,2)'
100000 loops, best of 3: 3.5 usec per loop

因此,在 python 中,frexplogldexp 之间没有太多可检测的差异的速度。但不确定这会告诉您有关实施的任何信息!

As for speed, here is a quick comparison

$ python -m timeit -c 'from math import frexp' 'frexp(1.1)'
100000 loops, best of 3: 3.7 usec per loop

$ python -m timeit -c 'from math import log' 'log(1.1)'
100000 loops, best of 3: 3.7 usec per loop

$ python -m timeit -c 'from math import ldexp' 'ldexp(1.1,2)'
100000 loops, best of 3: 3.5 usec per loop

So there isn't a lot of difference detectable in python between frexp, log and ldexp in terms of speed. Not sure that tells you anything about the implementation though!

魂ガ小子 2024-08-19 18:35:00

这是一个您可以轻松回答的问题:

$ python
>>> import math
>>> help(math.frexp)
Help on built-in function frexp in module math:

注意内置。它是用 C 语言

>>> import urllib
>>> help(urllib.urlopen)
Help on function urlopen in module urllib:

编写的。这里没有内置。它是用 Python 编写的。

This is a question you can easily answer yourself:

$ python
>>> import math
>>> help(math.frexp)
Help on built-in function frexp in module math:

Notice the built-in. It's in C.

>>> import urllib
>>> help(urllib.urlopen)
Help on function urlopen in module urllib:

No built-in here. It's in Python.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文