【问题标题】:Calling PARI/GP from Python从 Python 调用 PARI/GP
【发布时间】:2023-04-09 05:21:01
【问题描述】:

我想从 Python 调用 PARI/GP 仅计算我定义的不同 ns 的函数 nextprime(n)。不幸的是,我无法安装pari-python,所以我想我会在Python 中通过os.system 使用命令行调用它。但是,我在手册页中看不到如何让 PARI/GP 在非交互模式下运行。有没有办法做到这一点?

【问题讨论】:

    标签: python linux pari-gp


    【解决方案1】:

    您可以像这样使用-q 标志将输入通过管道传输到 gp 的标准输入:

    senderle:~ $ echo "print(isprime(5))" | gp -q
    1
    

    但是,创建一个简单的 python 扩展,允许您将字符串传递给 pari 的内部解析器并返回结果(作为字符串)并不难。这是我前段时间写的一个基本版本,以便我可以从 python 调用 pari 的 APRT test 实现。您可以进一步扩展它以进行适当的转换等。

    //pariparse.c
    
    #include<Python.h>
    #include<pari/pari.h>
    
    static PyObject * pariparse_run(PyObject *self, PyObject *args) {
        pari_init(40000000, 2);
        const char *pari_code;
        char *outstr;
    
        if (!PyArg_ParseTuple(args, "s", &pari_code)) { return NULL; }
        outstr = GENtostr(gp_read_str(pari_code));
        pari_close();
        return Py_BuildValue("s", outstr);
    }
    
    static PyMethodDef PariparseMethods[] = {
        {"run", pariparse_run, METH_VARARGS, "Run a pari command."},
        {NULL, NULL, 0, NULL}
    };
    
    PyMODINIT_FUNC initpariparse(void) {
        (void) Py_InitModule("pariparse", PariparseMethods);
    }
    

    还有设置文件:

    #setup.py
    
    from distutils.core import setup, Extension
    
    module1 = Extension('pariparse',
                        include_dirs = ['/usr/include', '/usr/local/include'],
                        libraries = ['pari'],
                        library_dirs = ['/usr/lib', '/usr/local/lib'],
                        sources = ['pariparse.c'])
    
    setup (name = 'pariparse',
           version = '0.01a',
           description = 'A super tiny python-pari interface',
           ext_modules = [module1])
    

    然后只需键入 python setup.py build 即可构建扩展。然后你可以这样称呼它:

    >>> pariparse.run('nextprime(5280)')
    '5281'
    

    我刚刚对此进行了测试,它使用通过 homebrew 提供的最新版本的 pari 为我编译(在 OS X 上)。 YMMV!

    【解决方案2】:

    您可能想尝试使用Sage 数学工具。 Sage 使用 Python 将各种数学库(包括 PARI)粘合在一起。一些数学库很好地集成了,另一些则使用 hacks(将字符串传递到库中,然后解析字符串结果),但在所有情况下,其他人为您完成了集成工作,您可以使用它。

    您可以设置自己的 Sage 系统,也可以获取免费帐户并在华盛顿大学的服务器上试用 Sage。

    【讨论】:

      【解决方案3】:

      我不认为调用os.system 是一个好主意,除非你有一个可靠的C 库支持它时快速而肮脏的解决方法。从 Python 调用 C 函数非常容易;这里有两个调用 nextprime 的函数。一种是使用long 整数(尽管有名称,但在这里意味着您使用的是小整数);另一种是使用string 类型(用于更长的整数)。

      首先检查您是否安装了libpari。下面的解决方案适用于 Linux,并假定您的库名为 libpari.so。在 Windows 下,它可能会被称为 .dll 后缀。如果第一次尝试找不到 DLL 文件,您可能需要输入完整的路径:

      import ctypes
      
      # load the library
      pari=ctypes.cdll.LoadLibrary("libpari.so")
      
      # set the right return type of the functions
      pari.stoi.restype = ctypes.POINTER(ctypes.c_long)
      pari.nextprime.restype = ctypes.POINTER(ctypes.c_long)
      pari.strtoGENstr.restype = ctypes.POINTER(ctypes.c_long)
      pari.geval.restype = ctypes.POINTER(ctypes.c_long)
      pari.itostr.restype = ctypes.c_char_p
      
      # initialize the library 
      pari.pari_init(2**19,0)
      
      def nextprime(v):
        g = pari.nextprime(pari.stoi(ctypes.c_long(v)))
        return pari.itos(g)
      
      def nextprime2(v):
        g = pari.nextprime(pari.geval(pari.strtoGENstr(str(v))))
        return int(pari.itostr(g))
      
      print( nextprime(456) )
      print( nextprime2(456) )
      

      【讨论】:

        猜你喜欢
        • 2020-07-02
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-08-23
        • 2014-03-10
        • 2020-07-06
        • 2013-01-25
        • 1970-01-01
        相关资源
        最近更新 更多