__init__ 来自 ctypes 构造函数

__init__ from ctypes constructor

我有一个 C 结构和一个构造函数

typedef struct {
    uint32_t index;
    int32_t line;
    int16_t column;
} Position;

Position positionCreate() {
    Position position;
    position.index = 0;
    position.line = -1;
    position.column = -1;
    return position;
}

有一个 Python class 等价物

from ctypes import *


library = cdll.LoadLibrary('./libposition.so')


class Position(Structure):

    _fields_ = [
        ('index', c_uint32),
        ('line', c_int32),
        ('column', c_int16),
    ]

当我“手动”初始化 class 时:

constructor = library.positionCreate
constructor.restype = Position
position = constructor()
print(position.index, position.line, position.column)

我得到了想要的输出:

0, -1, -1

但是我想使用这个构造函数:

class Position(Structure):

    _fields_ = [
        ('index', c_uint32),
        ('line', c_int32),
        ('column', c_int16),
    ]

    def __init__(self):

        # Or words to this effect
        self = library.positionCreate()

当我尝试这个时:

position = Position()
print(position.index, position.line, position.column)

我不再得到正确的输出:

0, 0, 0

我认为我的 self = positionCreate() 语法是错误的,但我不知道什么是正确的。

self 不能这样分配。你需要的是 __new__,它可以 return 一个你想要的 class 的实例:

test.c

#include <stdint.h>

#ifdef _WIN32
#   define API __declspec(dllexport)
#else
#   define API
#endif

typedef struct {
    uint32_t index;
    int32_t line;
    int16_t column;
} Position;

API Position positionCreate() {
    Position position;
    position.index = 0;
    position.line = -1;
    position.column = -1;
    return position;
}

test.py

from ctypes import *

class Position(Structure):

    _fields_ = [('index', c_uint32),
                ('line', c_int32),
                ('column', c_int16)]

    def __new__(cls):
        return dll.positionCreate()

dll = CDLL('./test')
dll.positionCreate.argtypes = ()
dll.positionCreate.restype = Position

position = Position()
print(position.index, position.line, position.column)

输出:

0 -1 -1