簡體   English   中英

將python列表作為'float *'或'int *'傳遞給C / C ++

[英]Pass python list to C/C++ as 'float*' or 'int*'

C / C ++

void func(float* xyz1, float* xyz2,int n){
     //do something
     for(int i=0; i<n;i++){
        printf("%f %f\n",xyz1[i],xyz2[i]);
     }
}

蟒蛇

import numpy as np
n = 1000000
xyz1 = np.random.random((n,)).tolist()
xyz2 = np.random.random((n,)).tolist()

#pass above array to the C/C++ code for further processing.
func(xyz1,xyz2,n) # <-- the call to the c/c++ code

我見過使用更高級數據結構(如C ++ array調用C ++代碼的示例。 但是,我只想使用基本數據類型傳遞它,如intfloat *

使用PyBind11或python的內置C類型的任何簡單方法嗎?

你可以用ctypes實現這一點。 首先使用C Api創建共享對象。 ctypes不支持C ++,但只支持C.這意味着你可以在源代碼中使用c ++,但是你必須提供一個沒有C ++語言功能的C接口,比如函數重載或名稱修改。 因此,函數定義用extern "C"標記。

然后在python中加載共享對象。 設置參數類型和結果類型。 最后你可以調用你的函數。 這是一個例子:

import ctypes
import numpy as np

n = 1000000
xyz1 = np.random.random((n,)).tolist()
xyz2 = np.random.random((n,)).tolist()

#pass above array to the C/C++ code for further processing.
Func = ctypes.CDLL("path/to/libFunc.so")
Func.func.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.c_int]
res = Func.func(xyz1,xyz2,n) # <-- the call to the c/c++ code

我沒有測試它,所以可能有一些錯誤,但我認為這個想法應該是清楚的。 這是我測試的一個例子:

的CMakeLists.txt:

cmake_minimum_required (VERSION 3.5.1) 
project (DotProduct) 
set(CMAKE_CXX_STANDARD 14) 
set(CMAKE_BUILD_TYPE Debug) 

add_library(DotProduct SHARED src/DotProduct.cpp src/DotProduct.h)

DotProduct.h:

extern "C" double dotProduct(double* l, double* r, unsigned int len);

DotProduct.cpp:

#include "DotProduct.h" 

double dotProduct(double *l, double *r, unsigned int len) { 
    double sum(0); 

    while (len--) { 
        sum += l[len] * r[len]; 
    } 
    return sum; 
}

main.py:

import ctypes

def dot_product(v1, v2):    
    l = len(v1)    
    if l != len(v2):        
        return 0    
    vec1 = (ctypes.c_double * l)(*v1)    
    vec2 = (ctypes.c_double * l)(*v2)    
    Dot_Product = ctypes.CDLL("build/lib/libDotProduct.so")      
    Dot_Product.dotProduct.argtypes = [ctypes.POINTER(ctypes.c_double), ctypes.POINTER(ctypes.c_double), ctypes.c_uint]    
    Dot_Product.dotProduct.restype = ctypes.c_double
    return Dot_Product.dotProduct(vec1, vec2, l)

vec1 = [2, 2]
vec2 = [2, 3]
print("{} * {} = {}".format(vec1, vec2, dot_product(vec1, vec2)))

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM