Reputation: 336
I am using SWIG (v3) to wrap C++ code to Python 3. In C++, I have a class MyClass
which inherits from std::vector
. I want to wrap this in Python, such that the resulting Python class MyClass
is a subclass of the standard Python list
class. Is this possible?
Here is an example:
example.h
#include <vector>
#include <iostream>
using namespace std;
// List class
class MyList : public vector<int>
{
public:
// Init
MyList() : vector<int>() {
this->insert(this->begin(),2);
this->insert(this->begin(),1);
}
// Toy insert function
void toy_insert()
{
this->insert(this->begin(),0);
}
};
example.cpp
#include "example.h"
example.i
%module example
%{
#include "example.h"
%}
%include "std_vector.i"
using namespace std;
%template(MyVector) std::vector<int>; // Nothing known about base class 'vector< int >' if we remove std:: here
%typemap(out) MyList* {
int size = (*$1).size();
$result = PyList_New(size);
for (int i=0; i<size; i++) {
PyList_SetItem($result, i, PyInt_FromLong((*$1)[i]));
}
};
// List class
class MyList : public std::vector<int> // Nothing known about base class 'vector< int >' if we remove std:: here
{
public:
MyList();
void toy_insert();
};
run_example.py
import example
my_list = example.MyList()
print(my_list)
The print command returns <example.MyList; proxy of [1, 2] >
, but this is not what I want. Ideally this should just return [1,2]
, but then I would still be able to call:
my_list.toy_insert()
print(my_list)
which should return [0,1,2]
.
Thanks for your help
Upvotes: 0
Views: 140
Reputation: 178409
As mentioned in my comment, you can override the display of a SWIG type. Here's a rough example:
%module x
%{
#include "example.h"
%}
%include <windows.i>
%include <std_vector.i>
%template(MyVector) std::vector<int>;
%include "example.h"
%extend MyList {
const char*__repr__()
{
// I was lazy.
return "fancy representation";
}
}
Output:
>>> import x
>>> t=x.MyList()
>>> t
fancy representation
>>> t[0]
1
>>> t[1]
2
>>> t.toy_insert()
>>> t[0]
0
>>> t[1]
1
>>> t[2]
2
Upvotes: 2