![](/img/trans.png)
[英]Trouble using Python ctypes to run C dll function (array output with unknown size)
[英]Wrap C Function returning array of unknown size using ctypes python
我試圖使用ctypes包裝一個C函數,該函數返回未知大小的字符數組。 該函數來自gdal c api ,但我的問題並不特定於該函數。
我想知道是否存在解構返回未知大小的char **數組對象的函數輸出的一般方法。 在ctypes中,這將是POINTER(c_char_p * X)
,其中X未知。
# Define the function wrapper.
f = ctypes.CDLL('libgdal.so.20').GDALGetMetadata
MAX_OUTPUT_LENGTH = 10
f.restype = ctypes.POINTER(ctypes.c_char_p * MAX_OUTPUT_LENGTH)
f.argtypes = [ctypes.c_void_p, ctypes.c_char_p]
# Example call (the second argument can be null).
result = []
counter = 0
output = f(ptr, None).contents[counter]
while output:
result.append(output)
counter += 1
output = f(ptr, None).contents[counter]
output
是結果數組,而ptr
是指向打開的GDALRaster的ctypes指針。 對此的局限性在於,在調用該函數之前,我必須構造一個具有固定長度的數組。 我可以猜測實際情況下的最大長度是多少,只需使用即可。 但這是任意的,我想知道是否存在一種無需指定數組長度即可獲取數組指針的方法。 換一種說法:
有沒有一種方法可以執行與上面的示例類似的操作,但不指定任意的最大長度?
事實證明,如果函數輸出是一個以null終止的字符數組,則只需將指針傳遞給c_char_p
對象, 而無需將長度指定為restype參數。 然后循環遍歷結果,直到找到null元素為止,該元素指示數組的結尾。
因此,以下內容很適合我的用例:
# Define the function wrapper, the restype can simply be a
# pointer to c_char_p (without length!).
f = ctypes.CDLL('libgdal.so.20').GDALGetMetadata
f.restype = ctypes.POINTER(ctypes.c_char_p)
f.argtypes = [ctypes.c_void_p, ctypes.c_char_p]
# Prepare python result array.
result = []
# Call C function.
output = f(ptr, None)
# Ensure that output is not a null pointer.
if output:
# Get first item from array.
counter = 0
item = output[counter]
# Get more items, until the array accessor returns null.
# The function output (at least in my use case) is a null
# terminated char array.
while item:
result.append(item)
counter += 1
item = output[counter]
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.