[C++-sig] Moving "decorator" into C++ part of module

Albert Strasheim fullung at gmail.com
Mon May 21 15:14:05 CEST 2007


Hello all

I have a class with various methods that return uBLAS matrices. I've 
wrapped various instantiations of these matrices with:

template<typename T>
struct matrix_wrapper
{
    static void wrap(const char* python_name)
    {
        py::class_<T, boost::noncopyable>(python_name, py::no_init)
            .add_property("__array_struct__", array_struct__)
            ;
    }

    static void cleanup(void* obj) {
        PyArrayInterface* ai = (PyArrayInterface*) obj;
        delete [] ai->shape;
        delete [] ai->strides;
        delete ai;
    }

    static PyObject* array_struct__(T const& self)
    {
        // http://numpy.scipy.org/array_interface.shtml
        PyArrayInterface* ai = new PyArrayInterface;
        // ... more code here ...
        ai->data = (void*) self.data().begin();
        return PyCObject_FromVoidPtr(ai, cleanup);
    }
}

In Python this allows me to do:

foo = WrappedClass()
cmatrix = foo.somefunc()
numpyarr = numpy.asarray(cmatrix)

without a copy of cmatrix's contents having to be made. Now I'd just 
like to get rid of the asarray bit so that it looks like my wrapped 
functions return NumPy arrays. In Python I can "decorate" this function 
like so:

def return_asarray(func):
    from numpy import asarray
    def call(*args, **kwargs):
        return asarray(func(*args, **kwargs))
    return call
WrappedClass.somefunc = return_asarray(WrappedClass.somefunc)

but I would like to move this "decoration" into the C++ code, so that 
my module doesn't need to have the extra Python bits.

Any thoughts on how this could be done? I looked at the documentation 
for class_, but nothing jumped out at me.

Regards,

Albert



More information about the Cplusplus-sig mailing list