Per parecchio casi (ad esempio int *n
) sarebbe sufficiente scrivere:
%apply int *OUTPUT { int *n };
che utilizza alcuni typemaps predefinite SWIG fornisce per parametri di output. (C'è anche INOUT e INPUT che sono simili).
In questo caso, tuttavia, non corrispondiamo a nessuno dei casi predefiniti, quindi è necessario eseguire manualmente la stessa operazione. In pratica sono due typemaps per argomento: una typemap di input che crea qualcosa di temporaneo per la chiamata alla funzione effettiva e utilizza quello invece di qualche input reale e un argout che effettua il marshalling del risultato dal temporaneo a Python. Nel caso di Python ha senso usare una tupla per restituire più argomenti.
Un esempio:
%module test
%typemap(in,numinputs=0) int& n (int temp) "$1 = &temp;"
%typemap(in,numinputs=0) char **data (char *temp) "$1 = &temp;"
%typemap(argout) char **data {
%append_output(PyString_FromString(*$1));
}
%typemap(argout) int& n {
%append_output(PyInt_FromLong(*$1));
}
%inline %{
void foo(int& n, char **data) {
static char str[] = "Hello world";
*data = str;
n = sizeof str;
}
%}
Punti da notare:
Le variabili temporanee (int temp
, char *temp
) automaticamente ottenere rinominato che ferma il nome scontro apparente. %append_output
è una macro SWIG che si espande per aggiungere qualcosa alla parte posteriore della tupla $result
in Python. Se la tua funzione foo
fosse allocata dinamicamente alla memoria, dovrai gestirla. La typemap freearg è spesso utile se la typemap in deve allocare dinamicamente la memoria.
Questo era sufficiente per permettermi di compilare ed eseguire le cose come:
import test
len,str = test.foo()
print len
print str