开发者

How do I connect a Python and a C program?

I have a python-based program that reads serial data off an a port connected to an rs232 cable. I want to pass the data I get he开发者_如何学Gore to a C-program that will handle the computation-intensive side of things. I have been checking up the net and all I've found are linux-based.


My suggestion would be the inline function from the instant module, though that only works if you can do everything you need to in a single c function. You just pass it a c function and it compiles a c extension at runtime.

    from instant import inline
    sieve_code = """
    PyObject* prime_list(int max) {
        PyObject *list = PyList_New(0);
        int *numbers, *end, *n; 
        numbers = (int *) calloc(sizeof(int), max);
        end = numbers + max;

        numbers[2] = 2;
        for (int i = 3; i < max; i += 2) { numbers[i] = i; }
        for (int i = 3; i < sqrt(max); i++) {
            if (numbers[i] != 0) {
                for (int j = i + i; j < max; j += i) { numbers[j] = 0; }
            }
        }
        for (n = numbers; n < end; n++) { 
            if (*n != 0) { PyList_Append(list, PyInt_FromLong(*n)); }
        }
        free(numbers);
        return list;
    }
    """
    sieve = inline(sieve_code)


There a number of ways to do this.

  1. The rawest, simplest way is to use the Python C API and write a wrapper for your C library which can be called from Python. This ties your module to CPython.

  2. The second way is to use ctypes which is an FFI for Python that allows you to load and call functions in C libraries directly. In theory, this should work across Python implementations.

  3. A third way is to use Pyrex or it's next generation version Cython which allows you to annotate your Python code with type information that the compiler can convert into compiled code. It can be used to write wrappers too. AFAIK, It's tied to CPython.

  4. Yet another way is to use SWIG which is a tool that generates glue code that helps you wrap C libraries for use from Python. It's basically the first approach with a helper tool.

  5. Another way is to use Boost Python API which is an object oriented wrapper over the raw Python C API.

All of the above let you do your work in the same process.

If that's not a constraint, like Digital Ross suggested, you can simply spawn a subprocess and hand over arguments (either as command line ones or via it's standard input) and have an external process do the work for you.


Use a pipe and popen

The easiest way to deal with this is probably to just use popen(3). The popen function is available in both Python and C and will connect a program of either language with the other using a pipe.

>>> import subprocess
>>> print args
['/bin/vikings', '-input', 'eggs.txt', '-output', 'spam spam.txt', '-cmd', "echo '$MONEY'"]
>>> p = subprocess.Popen(args)

Once you have the pipe, you should probably send yaml or json through it, though I've never tried to read either in C. If it's really a simple stream, just parse it yourself. If you like XML, I suppose that's available as well.


How many bits per second are you getting across this RS-232 cable? Have you test results that show that Python won't do the crunchy bits fast enough? If the C program is yet to be written, consider the possibility of writing the computation-intensive side of things in Python, with easy fallback to Cython in the event that Python isn't fast enough.


Indeed this question does not have much to do with C++. Having said that, you can try SWIG - it's multi-platform and allows functional calls from Python to C/C++.


I would use a standard form of IPC like a socket.

A good start would be Beej's Guide.

Also, don't tag the question with c++ if you are specifically using c. c and c++ are different languages.


I'd use ctypes: http://python.net/crew/theller/ctypes/tutorial.html
It allows you to call c (and c++) code from python.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜