setting a typemap correctly for SWIG for using a specific method

54 Views Asked by At

I have tried to redo what is shown here but there is s.t not working and I can't see what.

We have a C++ class ('Point') that contains this method:

int Point::myfunc(int a, std::vector<float> *b) 
    {
         for (short int i = 0; i <= 10; i = i + 1)
            b->push_back(static_cast<float>(a * i));
        return 0;
    }

I have this interface file ".i" for SWIG:

%module Point
%{
#include "Point.h"
%}
%include <std_string.i>
// Define typemaps for std::vector<float>*
%typemap(in) std::vector<float>* (std::vector<float> tmp) {
  $1 = &tmp;
}
%typemap(argout) std::vector<float>* {
  // Nothing needed here; the vector is modified in-place.
}
%include "Point.h"

I generate the Python module (swig -c++ -python -Wall Point.i) but when I use it like this:

a_list= [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
b=A.myfunc(3,a_list)
print (b)

I obtain '0' for b (I was expecting a modified list). Could you please tell me what am I doing wrong ? thanks in advance.

1

There are 1 best solutions below

0
Criminal_Affair_At_SO On

How is the vector modified in-place? You create a new variable called tmp and you assign $1 to its address. This assigns a new value to the argument, which is essentially a local variable.

Do not reinvent the wheel, there is something very similar in the examples using SWIG builtins, you don't have to create new typemaps:

%module Point

%include stl.i

// We need to tell SWIG that we are instantiating std::vector for float
%template(FloatVector) std::vector<float>;

// There is a standard INOUT SWIG typemap for doing what you need
%apply std::vector<float> *INOUT { std::vector<float> *b };

%inline %{

#include <vector>

int myfunc(int a, std::vector<float> *b) 
    {
         for (short int i = 0; i <= 10; i = i + 1)
            b->push_back(static_cast<float>(a * i));
        return 0;
    }
    
%}