2013-03-03 39 views
8

Tôi có một hàm C++ trong đó hai đối số được đưa ra làm ví dụ sau.Làm cách nào để nhận các đối số tham chiếu và con trỏ trong Python + SWIG?

void func(int& n, char** data) 
{ 
    *data = other_func1(); // returns a char array 
    n = other_func2(); // returns the length of the array 
} 

Tôi có thể dễ dàng sử dụng hàm này trong C hoặc C++, nhưng tôi không biết làm thế nào tôi có thể gọi nó từ mô-đun Python được tạo bằng SWIG. Tôi cho rằng tôi sẽ phải viết một hàm C++ khác trả về, ví dụ, std :: pair. Nhưng nếu có thể, tôi muốn biết một cách giải quyết ở phía Python. Bất cứ ai có thể giúp đỡ?

Trả lời

8

Đối với khá nhiều trường hợp (ví dụ int *n) nó sẽ là đủ để viết:

%apply int *OUTPUT { int *n }; 

trong đó sử dụng một số typemaps mặc định mà SWIG cung cấp cho các thông số đầu ra. (Cũng có INOUT và INPUT tương tự).

Trong trường hợp này mặc dù chúng tôi không hoàn toàn khớp với bất kỳ trường hợp được xác định trước nào, vì vậy chúng tôi cần thực hiện tương tự theo cách thủ công. Đó là cơ bản hai typemaps cho mỗi đối số - một typemap đầu vào mà tạo ra một cái gì đó tạm thời cho các cuộc gọi chức năng thực tế và sử dụng mà thay vì một số đầu vào thực sự và một argout marshals kết quả trở lại từ tạm thời để Python. Trong trường hợp của Python nó có ý nghĩa để sử dụng một tuple để trả về nhiều đối số.

Một ví dụ:

%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; 
    } 
%} 

điểm cần lưu ý:

Các biến tạm thời (int temp, char *temp) tự động được đổi tên mà dừng lại tên đụng độ rõ ràng. %append_output là một macro SWIG mở rộng để thêm một cái gì đó vào mặt sau của các $result tuple bằng Python. Nếu chức năng của bạn foo được cấp phát bộ nhớ động, bạn cần phải xử lý điều đó. Các typemap freearg thường hữu ích nếu trong typemap cần phải tự động cấp phát bộ nhớ.

Đây là đủ để cho phép tôi để biên dịch và chạy nó thích:

import test 

len,str = test.foo() 

print len 
print str 
Các vấn đề liên quan