python - 在从 Python 调用的 C 函数中使用 PyFloat_FromDouble 时获得错误结果

标签 python c arrays

我正在学习如何通过制作包装器从 Python 调用 C 函数。我的最终目标是将 Python 中声明的巨大复杂数组传递给我的 C 函数,并返回其他巨大复杂数组。

我从一个简单的示例开始,以了解从 Python 调用 C 函数的基础知识。我定义了一个函数,该函数读取 double 组(任何大小)并返回所有值的总和。这是我的wrapperTest.c代码:

#include <Python.h>

static PyObject *sumArray(PyObject * self, PyObject * args){
    PyObject *ret;

    PyObject* myTuple;
    if(!PyArg_ParseTuple(args, "O", &myTuple)) return NULL;

    printf("PyTuple_Size=%ld\n", PyTuple_Size(myTuple));

    double *my_array;
    my_array=(double*)malloc(sizeof(double)*PyTuple_Size(myTuple));

    int tupleSize;
    tupleSize=PyTuple_Size(myTuple);

    int i;
    PyObject* tupleItem;
    for(i=0; i<tupleSize; i++){
        tupleItem=PyTuple_GetItem(myTuple, i);

        if(!PyFloat_Check(tupleItem)){
            printf("Error: tuple contains a non-float value");
            exit(1);
        }
        my_array[i]=PyFloat_AsDouble(tupleItem);
        printf("my_array[%d]=%lf\n", i, my_array[i]);
    }

    double result;
    result=0.;
    for(i=0; i<tupleSize; i++){
        result+=my_array[i];
    }
    printf("result=%lf\n", result);

    ret=PyFloat_FromDouble(result);

    free(my_array);

    return ret;
}

static PyMethodDef wrapperTest_funcs[] = {
    {"sumArray", (PyCFunction)sumArray,
        METH_VARARGS, ""},
    {NULL}
};

void initwrapperTest(void)
{
    Py_InitModule3("wrapperTest", wrapperTest_funcs,
                   "Extension module example!");
}

我可以通过运行脚本 setup.py 成功编译扩展

from distutils.core import setup, Extension
setup(name='wrapperTest', version='1.0',  \
      ext_modules=[Extension('wrapperTest', ['wrapperTest.c'])])

使用命令“python setup.py install”。此外,我可以在运行 Python 时导入扩展并执行该函数。但是,我无法从定义的函数中始终获得正确的结果。例如,如果我尝试传递数组 a=(1.2, 2.4),这就是我得到的:

>>> import wrapperTest
>>> a=(1.2, 2.4)
>>> b=wrapperTest.sumArray(a)
PyTuple_Size=2
my_array[0]=1.200000
my_array[1]=2.400000
result=3.600000
>>> b 
3.5999999999999996

显然正确的结果是3.6(C语言编写的函数打印的结果),但Python中最终得到的结果是3.5999999999999996。当然,它非常接近正确的结果,但又不一样。我错过了什么?

最佳答案

我认为 printf 输出的默认精度是 6 位小数。

是否只是您的 printf 函数将答案四舍五入为 3.600000 并且 python 的打印更加准确?

关于python - 在从 Python 调用的 C 函数中使用 PyFloat_FromDouble 时获得错误结果,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30866183/

相关文章:

python - 如何从 JSON 文件中删除键/对象?

python - 如何使用 Python 迁移将 Heroku Django 应用程序的新模型表添加到远程 Heroku Postgres?

c - 在线编译时出现段错误

java - 创建 int 数组的字符串数组时出现问题

arrays - 更快的整数 num2str?

python - xgboost.plot_tree 显示 - 空字符/框/ block 作为标签

python - 我可以使用 Django 风格的 order_by() 代替 QuerySet 对现有模型对象列表进行排序吗?

c - Google Protobuf-c 重复字符串

c - 如何检查我的字节标志,验证特定位是 1 还是 0?

javascript - axios 和响应数据集拆分到多个数组