Типы Python и C-структуры
В коде C определены несколько новых типов. Большинство из них доступны из Python, но некоторые не экспонируются из-за ограниченного использования. Каждый новый тип Python имеет связанную PyObject* со внутренней структурой, включающей указатель на «таблицу методов», которая определяет поведение нового объекта в Python. Когда вы получаете объект Python в коде C, вы всегда получаете указатель на структуру PyObject. Поскольку структура PyObject очень общая и определяет только PyObject_HEAD, сама по себе она не очень интересна. Однако разные объекты содержат больше деталей после PyObject_HEAD (но вам нужно привести к нужному типу, чтобы получить к ним доступ — или использовать функции-аксессоры или макросы).
Определенные новые типы Python
Типы Python функционально эквивалентны классам в Python в C. Создавая новый тип Python, вы делаете доступным новый объект для Python. Объект ndarray является примером нового типа, определенного в C. Новые типы определяются в C двумя основными шагами:
- создание C-структуры (обычно с именем
Py{Name}Object), которая бинарно совместима со структуройPyObject, но содержит дополнительную информацию, необходимую для этого конкретного объекта; - заполнение таблицы
PyTypeObject(на которую указывает член ob_type структурыPyObject) указателями на функции, которые реализуют желаемое поведение для типа.
Вместо специальных имён методов, которые определяют поведение для классов Python, есть «таблицы функций», которые указывают на функции, реализующие желаемые результаты. Начиная с Python 2.2, сам PyTypeObject стал динамичным, что позволяет типам C быть «подтипами» других типов C в C и подклассами в Python. Дочерние типы наследуют атрибуты и методы от своих родительских типов.
Есть два основных новых типа: ndarray ( PyArray_Type ) и ufunc ( PyUFunc_Type ). Дополнительные типы играют вспомогательную роль: PyArrayIter_Type, PyArrayMultiIter_Type и PyArrayDescr_Type . Тип PyArrayIter_Type предназначен для плоского итератора для ndarray (объекта, возвращаемого при получении атрибута flat). Тип PyArrayMultiIter_Type — это тип объекта, возвращаемого при вызове broadcast. Он обрабатывает итерацию и широковещательную передачу по набору вложенных последовательностей. Также PyArrayDescr_Type — это тип описателя типа данных, чьи экземпляры описывают данные, а PyArray_DTypeMeta — это метакласс для описателей типов данных. Есть также новые скалярные типы массивов, которые являются новыми скалярами Python, соответствующими каждому из основных типов данных, доступных для массивов. Дополнительные типы являются плацехолдерами, которые позволяют скалярам массивов соответствовать иерархии реальных типов Python. Наконец, экземпляры PyArray_DTypeMeta, соответствующие встроенным типам данных NumPy, также доступны.
PyArray_Type и PyArrayObject
- PyTypeObjectPyArray_Type
-
Тип Python массива ndarray —
PyArray_Type. В C, каждый ndarray является указателем на структуруPyArrayObject. Член ob_type этой структуры содержит указатель на типPyArray_Type.
- typePyArrayObject
- typeNPY_AO
-
Структура
PyArrayObjectC содержит всю необходимую информацию для массива. Все экземпляры ndarray (и его подклассов) будут иметь эту структуру. Для совместимости в будущем члены этой структуры обычно следует обращаться с помощью предоставленных макросов. Если вам нужно более короткое имя, вы можете использоватьNPY_AO(устарело), которое определено как эквивалентноеPyArrayObject. Прямой доступ к полям структуры устарел. Используйте вместо этого формуPyArray_*(arr). Начиная с NumPy 1.20, размер этой структуры не считается частью NumPy ABI (см. примечание в конце списка членов).typedef struct PyArrayObject { PyObject_HEAD char *data; int nd; npy_intp *dimensions; npy_intp *strides; PyObject *base; PyArray_Descr *descr; int flags; PyObject *weakreflist; /* version dependent private members */ } PyArrayObject;PyObject_HEAD-
Это необходимо для всех объектов Python. Она состоит (по крайней мере) из счётчика ссылок (
ob_refcnt) и указателя на тип объекта (ob_type). (Другие элементы могут присутствовать, если Python был скомпилирован со специальными опциями. См. Include/object.h в исходном дереве Python для получения дополнительной информации). Член ob_type указывает на объект типа Python.
- char*data
-
Доступно через
PyArray_DATA, этот член — указатель на первый элемент массива. Этот указатель можно (и обычно следует) перевести к типу данных массива.
- intnd
-
Целое число, указывающее на количество измерений для этого массива. Когда nd равен 0, массив иногда называют массивом ранга 0. Такие массивы имеют неопределённые размеры и шаги и недоступны. Макрос
PyArray_NDIM, определённый вndarraytypes.h, указывает на этот член.NPY_MAXDIMSопределён как константа времени компиляции, ограничивающая количество измерений. Это число составляет 64 с NumPy 2 и было 32 до этого. Однако в будущем мы можем захотеть снять эти ограничения, поэтому лучше явно проверять размерность для кода, который полагается на такое верхнее ограничение.
- npy_intp*dimensions
-
Массив целых чисел, предоставляющий форму в каждом измерении, пока nd \(\geq\) 1. Целое число всегда достаточно велико для хранения указателя на платформе, поэтому размер измерения ограничен только памятью. Макрос
PyArray_DIMSсвязан с этим членом.
- npy_intp*strides
-
Массив целых чисел, предоставляющий для каждого измерения число байтов, которое необходимо пропустить, чтобы перейти к следующему элементу в этом измерении. Связанный с макросом
PyArray_STRIDES.
- PyObject*base
-
Указанный
PyArray_BASE, этот член используется для хранения указателя на другой объект Python, связанный с этим массивом. Есть два случая использования:- Если этот массив не владеет своей памятью, то base указывает на объект Python, который им владеет (возможно, другой объект массива)
- Если для этого массива установлен флаг
NPY_ARRAY_WRITEBACKIFCOPY, то этот массив является рабочей копией «неправильного» массива.
При вызове
PyArray_ResolveWritebackIfCopy, массив, на который указывает base, будет обновлён содержимым этого массива.
- PyArray_Descr*descr
-
Указатель на объект описания типа данных (см. ниже). Объект описания типа данных — это экземпляр нового встроенного типа, который позволяет описывать память в общем виде. Для каждого поддерживаемого типа данных есть структура описателя. Эта структура описателя содержит полезную информацию о типе, а также указатель на таблицу указателей функций для реализации определённого функционала. Как следует из названия, она связана с макросом
PyArray_DESCR.
- intflags
-
Указанный макросом
PyArray_FLAGS, этот член представляет флаги, указывающие, как интерпретировать память, на которую указывает data. Возможные флаги —NPY_ARRAY_C_CONTIGUOUS,NPY_ARRAY_F_CONTIGUOUS,NPY_ARRAY_OWNDATA,NPY_ARRAY_ALIGNED,NPY_ARRAY_WRITEABLE,NPY_ARRAY_WRITEBACKIFCOPY.
- PyObject*weakreflist
-
Этот член позволяет объектам массива иметь слабые ссылки (используя модуль weakref).
Примечание
Дополнительные члены считаются закрытыми и зависят от версии. Если размер структуры важен для вашего кода, необходимо соблюдать особую осторожность. Возможным случаем использования, когда это актуально, является наследование в C. Если ваш код полагается на
sizeof(PyArrayObject)для постоянства, вы должны добавить следующую проверку во время импорта:if (sizeof(PyArrayObject) < PyArray_Type.tp_basicsize) { PyErr_SetString(PyExc_ImportError, "Binary incompatibility with NumPy, must recompile/update X."); return NULL; }Для того чтобы ваш код не приходилось компилировать для конкретной версии NumPy, можно добавить константу, оставив место для изменений в NumPy. Решение, гарантированно совместимое с любой будущей версией NumPy, требует использования вычисления смещения и размера выделения во время выполнения.
Тип PyArray_Type реализует многие функции Python objects, включая интерфейсы tp_as_number, tp_as_sequence, tp_as_mapping и tp_as_buffer. Также используется rich comparison наряду с поиском атрибутов нового стиля для членов (tp_members) и свойств (tp_getset). Тип PyArray_Type также может быть подтипизирован.
Подсказка
Методы tp_as_number используют общий подход для вызова любой функции, зарегистрированной для обработки операции. При импорте _multiarray_umath module, он устанавливает числовые операции для всех массивов соответствующим ufunc. Этот выбор можно изменить с помощью PyUFunc_ReplaceLoopBySignature. Методы tp_str и tp_repr также могут быть изменены с помощью PyArray_SetStringFunction.
PyGenericArrType_Type
- PyTypeObjectPyGenericArrType_Type
-
Тип
PyGenericArrType_Type— это определение PyTypeObject, которое создаёт тип Pythonnumpy.generic.
PyArrayDescr_Type и PyArray_Descr
- PyTypeObjectPyArrayDescr_Type
-
Тип
PyArrayDescr_Type— встроенный тип объектов описателей типов данных, используемых для описания интерпретации байтов, составляющих массив. Существует 21 статически определённый объектPyArray_Descrдля встроенных типов данных. Хотя они участвуют в подсчёте ссылок, их счётчик ссылок никогда не должен достигать нуля. Также поддерживается динамическая таблица объектовPyArray_Descrпользовательского определения. После «регистрации» объекта описателя типа данных он также никогда не должен быть удалён. ФункцияPyArray_DescrFromType(…) может быть использована для извлечения объектаPyArray_Descrиз перечисления номера типа (встроенного или пользовательского).
- typePyArray_DescrProto
-
Идентичная структура
PyArray_Descr. Эта структура используется для статического определения прототипа для регистрации нового устаревшего DType с помощьюPyArray_RegisterDataType.Подробности см. в примечании к
PyArray_RegisterDataType.
- typePyArray_Descr
-
Структура
PyArray_Descrлежит в основеPyArrayDescr_Type. Хотя она описана здесь для полноты, её следует рассматривать как внутреннюю для NumPy и манипулировать ею с помощью функций и макросовPyArrayDescr_*илиPyDataType*. Размер этой структуры может меняться в разных версиях NumPy. Для обеспечения совместимости:- Никогда не объявляйте экземпляр структуры без указателя.
- Никогда не выполняйте арифметические операции с указателями.
- Никогда не используйте
sizeof(PyArray_Descr)
У неё следующая структура:
typedef struct { PyObject_HEAD PyTypeObject *typeobj; char kind; char type; char byteorder; char _former_flags; // unused field int type_num; /* * Definitions after this one must be accessed through accessor * functions (see below) when compiling with NumPy 1.x support. */ npy_uint64 flags; npy_intp elsize; npy_intp alignment; NpyAuxData *c_metadata; npy_hash_t hash; void *reserved_null[2]; // unused field, must be NULLed. } PyArray_Descr;Некоторые dtypes имеют дополнительные члены, доступные через
PyDataType_NAMES,PyDataType_FIELDS,PyDataType_SUBARRAY, а в некоторых случаях (случаях)PyDataType_C_METADATA.- PyTypeObject*typeobj
-
Указатель на typeobject, который является соответствующим типом Python для элементов этого массива. Для встроенных типов он указывает на соответствующий скаляр массива. Для пользовательских типов он должен указывать на объект пользовательского типа. Этот объект типа может либо наследоваться от скаляров массивов, либо нет. Если он не наследуется от скаляров массивов, то флаги
NPY_USE_GETITEMиNPY_USE_SETITEMдолжны быть установлены в членеflags.
- charkind
-
Символьный код, указывающий тип массива (используя обозначение типа строки интерфейса массива). ‘b’ — булево, ‘i’ — целое со знаком, ‘u’ — целое без знака, ‘f’ — с плавающей запятой, ‘c’ — комплексное с плавающей запятой, ‘S’ — байты с нулевым окончанием 8 бит, ‘U’ — строка unicode 32 бит/символ, ‘V’ — произвольный.
- chartype
-
Традиционный символьный код, указывающий тип данных.
- charbyteorder
-
Символ, указывающий порядок байтов: ‘>’ (big-endian), ‘<’ (little- endian), ‘=’ (родной), ‘|’ (неважно, игнорировать). Все встроенные типы данных имеют порядок байтов ‘=’.
- npy_uint64flags
-
Флаг типа данных, определяющий, демонстрирует ли тип данных поведение типа массива объектов. Каждый бит в этом члене является флагом, названным как:
- inttype_num
-
Число, уникально идентифицирующее тип данных. Для новых типов данных это число назначается при регистрации типа данных.
- npy_intpelsize
-
Для типов данных, которые всегда имеют одинаковый размер (например, long), это значение размера типа данных. Для гибких типов данных, где разные массивы могут иметь различный размер элемента, это значение должно быть 0.
См.
PyDataType_ELSIZEиPyDataType_SET_ELSIZEдля способа доступа к этому полю в совместимом с NumPy 1.x формате.
- npy_intpalignment
-
Число, предоставляющее информацию об выравнивании для данного типа данных. Конкретно, оно показывает, как далеко от начала двухелементной структуры (первый элемент которой —
char), компилятор помещает элемент этого типа:offsetof(struct {char c; type v;}, v)См.
PyDataType_ALIGNMENTдля способа доступа к этому полю в совместимом с NumPy 1.x формате.
- PyObject*metadata
-
Метаданные об этом dtype.
- NpyAuxData*c_metadata
-
Метаданные, специфичные для реализации dtype на C. Добавлен в NumPy 1.7.0.
- typenpy_hash_t
- npy_hash_t*hash
-
Используется для кеширования значений хэша.
- NPY_ITEM_REFCOUNT
-
Указывает, что элементы этого типа данных должны быть подсчитаны ссылок (с помощью
Py_INCREFиPy_DECREF).
- NPY_ITEM_HASOBJECT
-
То же самое, что и
NPY_ITEM_REFCOUNT.
- NPY_LIST_PICKLE
-
Указывает, что массивы этого типа данных должны быть преобразованы в список перед сериализацией.
- NPY_ITEM_IS_POINTER
-
Указывает, что элемент является указателем на другой тип данных.
- NPY_NEEDS_INIT
-
Указывает, что память для этого типа данных должна быть инициализирована (установлена в 0) при создании.
- NPY_NEEDS_PYAPI
-
Указывает, что для этого типа данных требуется Python C-API во время доступа (поэтому не отпускайте GIL, если доступ к массиву понадобится).
- NPY_USE_GETITEM
-
При доступе к массиву используйте указатель функции
f->getitemвместо стандартного преобразования в скаляр массива. Необходимо использовать, если вы не определяете скаляр массива для данного типа данных.
- NPY_USE_SETITEM
-
При создании массива 0-мерного размера из скаляра массива используйте
f->setitem, а не стандартную копию из скаляра массива. Необходимо использовать, если вы не определяете скаляр массива для данного типа данных.
- NPY_FROM_FIELDS
-
Биты, унаследованные от родительского типа данных, если эти биты установлены в любом поле типа данных. В настоящее время (
NPY_NEEDS_INIT|NPY_LIST_PICKLE|NPY_ITEM_REFCOUNT|NPY_NEEDS_PYAPI).
- NPY_OBJECT_DTYPE_FLAGS
-
Биты, установленные для типа данных объекта: (
NPY_LIST_PICKLE|NPY_USE_GETITEM|NPY_ITEM_IS_POINTER|NPY_ITEM_REFCOUNT|NPY_NEEDS_INIT|NPY_NEEDS_PYAPI).
- intPyDataType_FLAGCHK(PyArray_Descr*dtype, intflags)
-
Возвращает true, если все заданные флаги установлены для объекта типа данных.
- intPyDataType_REFCHK(PyArray_Descr*dtype)
-
Эквивалентно
PyDataType_FLAGCHK(dtype,NPY_ITEM_REFCOUNT).
PyArray_ArrFuncs
- PyArray_ArrFuncs*PyDataType_GetArrFuncs(PyArray_Descr*dtype)
-
Получить устаревший
PyArray_ArrFuncsтипа данных (не может завершиться ошибкой).Добавлено в версии NumPy: 2.0 Эта функция была добавлена в обратной совместимости и обратной переносимости в NumPy 2.0 (см.
npy_2_compat.h). Любой код, который ранее обращается к слоту->fобъектаPyArray_Descr, теперь должен использовать эту функцию и перенести её для компиляции с 1.x. (Заголовокnpy_2_compat.hможно получить для этой цели.)
- типPyArray_ArrFuncs
-
Функции, реализующие внутренние функции. Не все эти указатели на функции должны быть определены для данного типа. Требуемые члены —
nonzero,copyswap,copyswapn,setitem,getitem, иcast. Предполагается, что они не являютсяNULLиNULLзаписями, которые приведут к аварийному завершению программы. Другие функции могут бытьNULL, что просто означает уменьшение функциональности для этого типа данных. (Также функция nonzero будет заполнена по умолчанию, если онаNULLпри регистрации пользовательского типа данных).typedef struct { PyArray_VectorUnaryFunc *cast[NPY_NTYPES_LEGACY]; PyArray_GetItemFunc *getitem; PyArray_SetItemFunc *setitem; PyArray_CopySwapNFunc *copyswapn; PyArray_CopySwapFunc *copyswap; PyArray_CompareFunc *compare; PyArray_ArgFunc *argmax; PyArray_DotFunc *dotfunc; PyArray_ScanFunc *scanfunc; PyArray_FromStrFunc *fromstr; PyArray_NonzeroFunc *nonzero; PyArray_FillFunc *fill; PyArray_FillWithScalarFunc *fillwithscalar; PyArray_SortFunc *sort[NPY_NSORTS]; PyArray_ArgSortFunc *argsort[NPY_NSORTS]; PyObject *castdict; PyArray_ScalarKindFunc *scalarkind; int **cancastscalarkindto; int *cancastto; void *_unused1; void *_unused2; void *_unused3; PyArray_ArgFunc *argmin; } PyArray_ArrFuncs;В описании указателей на функции используется понятие «правильного сегмента». Правильный сегмент — это сегмент, который выровнен и представлен в родном байтовом порядке для типа данных. Функции
nonzero,copyswap,copyswapn,getitem, иsetitemмогут (и должны) обрабатывать некорректные массивы. Другие функции требуют правильных сегментов памяти.Примечание
Функции в основном являются устаревшим API, однако некоторые из них всё ещё используются. Начиная с NumPy 2.x, они доступны только через
PyDataType_GetArrFuncs(см. функцию для получения более подробной информации). Перед использованием любой функции, определённой в структуре, необходимо проверить, является ли онаNULL. В целом, функцииgetitem,setitem,copyswap, иcopyswapnможно ожидать, что они будут определены, но все функции, ожидается, будут заменены на более новые API. Например,PyArray_Pack— это более мощная версияsetitem, которая, например, правильно обрабатывает преобразования.- voidcast(void*from, void*to, npy_intpn, void*fromarr, void*toarr)
-
Массив указателей на функции для преобразования из текущего типа во все другие встроенные типы. Каждая функция преобразует непрерывный, выровненный и неперевернутый буфер, на который указывает from, в непрерывный, выровненный и неперевернутый буфер, на который указывает to. Количество элементов для преобразования задаётся n, а аргументы fromarr и toarr интерпретируются как PyArrayObjects для гибких массивов, чтобы получить информацию о размере элемента.
- PyObject*getitem(void*data, void*arr)
-
Указатель на функцию, которая возвращает стандартный объект Python из одного элемента объекта массива arr, на который указывает data. Эта функция должна корректно обрабатывать «неправильные» (невыровненные и/или перевернутые) массивы.
- intsetitem(PyObject*item, void*data, void*arr)
-
Указатель на функцию, которая устанавливает объект Python item в массив arr в позиции, на которую указывает data. Эта функция обрабатывает «неправильные» массивы. При успешном выполнении возвращается ноль, в противном случае — минус один (и устанавливается ошибка Python).
- voidcopyswapn(void*dest, npy_intpdstride, void*src, npy_intpsstride, npy_intpn, intswap, void*arr)
- voidcopyswap(void*dest, void*src, intswap, void*arr)
-
Эти члены являются указателями на функции для копирования данных из src в dest и перестановки байтов, если указано. Значение arr используется только для гибких (
NPY_STRING,NPY_UNICODE, иNPY_VOID) массивов (и получено изarr->descr->elsize). Вторая функция копирует одно значение, в то время как первая проходит циклом по n значениям с предоставленными шагами. Эти функции могут обрабатывать некорректные данные src. Если src равен NULL, то копирование не выполняется. Если swap равен 0, то перестановка байтов не происходит. Предполагается, что dest и src не перекрываются. Если они перекрываются, то сначала используйтеmemmove(…), а затемcopyswap(n)сsrcравным NULL.
- intcompare(constvoid*d1, constvoid*d2, void*arr)
-
Указатель на функцию, которая сравнивает два элемента массива,
arr, на которые указываютd1иd2. Эта функция требует выровненных и неперевернутых массивов. Возвращаемое значение равно 1, если *d1> *d2, 0, если *d1== *d2, и -1, если *d1< *d2. Объект массиваarrиспользуется для получения информации о размере элемента и информации о полях для гибких массивов.
- intargmax(void*data, npy_intpn, npy_intp*max_ind, void*arr)
-
Указатель на функцию, которая получает индекс наибольшего из
nэлементов вarr, начиная с элемента, на который указываетdata. Эта функция требует, чтобы сегмент памяти был непрерывным и правильным. Возвращаемое значение всегда равно 0. Индекс наибольшего элемента возвращается вmax_ind.
- voiddotfunc(void*ip1, npy_intpis1, void*ip2, npy_intpis2, void*op, npy_intpn, void*arr)
-
Указатель на функцию, которая перемножает две
n-длинные последовательности, складывает их и помещает результат в элемент, на который указываетopмассиваarr. Начало двух последовательностей указывается по адресамip1иip2. Для перехода к следующему элементу в каждой последовательности требуется скачок вis1иis2байтах соответственно. Эта функция требует выровненной (хотя и необязательно непрерывной) памяти.
- voidcast(void*from, void*to, npy_intpn, void*fromarr, void*toarr)
- intscanfunc(FILE*fd, void*ip, void*arr)
-
Указатель на функцию, которая считывает (в стиле scanf) один элемент соответствующего типа из дескриптора файла
fdв память массива, на которую указываетip. Массив предполагается корректным. Последний аргументarr— массив, в который выполняется считывание. Возвращает количество успешно присвоенных аргументов (может быть нулём, если произошла неудача сопоставления до присвоения первого аргумента), или EOF, если ошибка ввода произошла до присвоения первого аргумента. Эта функция должна вызываться без удержания блокировки Python GIL, и должна захватить её для обработки ошибок.
- intfromstr(char*str, void*ip, char**endptr, void*arr)
-
Указатель на функцию, которая преобразует строку, на которую указывает
str, в один элемент соответствующего типа и помещает его в место памяти, на которое указываетip. После завершения преобразования,*endptrуказывает на остаток строки. Последний аргументarr— массив, на который указывает ip (необходим для типов данных с переменным размером). Возвращает 0 при успехе или -1 при ошибке. Требуется корректный массив. Эта функция должна вызываться без удержания блокировки Python GIL, и должна захватить её для обработки ошибок.
- npy_boolnonzero(void*data, void*arr)
-
Указатель на функцию, которая возвращает ИСТИНА, если элемент
arr, на который указываетdata, не равен нулю. Эта функция может работать с некорректными массивами.
- voidfill(void*data, npy_intplength, void*arr)
-
Указатель на функцию, которая заполняет непрерывный массив заданной длины данными. Два первых элемента массива должны быть уже заполнены. Из этих двух значений будет вычислен дельта, и значения с элемента 3 до конца будут вычисляться путем многократного добавления этого вычисленного дельта. Буфер данных должен быть корректным.
- voidfillwithscalar(void*buffer, npy_intplength, void*value, void*arr)
-
Указатель на функцию, которая заполняет непрерывный
bufferзаданнойlengthодним скалярным значениемvalue, адрес которого задан. Последний аргумент — массив, необходимый для получения размера элемента для массивов с переменной длиной.
- intsort(void*start, npy_intplength, void*arr)
-
Массив указателей на функции для конкретных алгоритмов сортировки. Конкретный алгоритм сортировки выбирается с помощью ключа (на данный момент
NPY_QUICKSORT,NPY_HEAPSORTиNPY_MERGESORTопределены). Эти сортировки выполняются на месте, предполагая непрерывные и выровненные данные.
- intargsort(void*start, npy_intp*result, npy_intplength, void*arr)
-
Массив указателей на функции сортировки для этого типа данных. Доступны те же алгоритмы сортировки, что и для sort. Индексы, производящие сортировку, возвращаются в
result(который должен быть инициализирован индексами от 0 доlength-1включительно).
- PyObject*castdict
-
Либо
NULL, либо словарь, содержащий функции низкоуровневого преобразования для типов данных, определённых пользователем. Каждая функция обернута в PyCapsule* и индексируется по номеру типа данных.
- NPY_SCALARKINDscalarkind(PyArrayObject*arr)
-
Функция для определения, как должны интерпретироваться скаляры этого типа. Аргументом является
NULLили 0-мерный массив, содержащий данные (если это необходимо для определения типа скаляра). Возвращаемое значение должно быть типаNPY_SCALARKIND.
- int**cancastscalarkindto
-
Либо
NULL, либо массив указателейNPY_NSCALARKINDS. Эти указатели должны быть либоNULL, либо указателем на массив целых чисел (завершённыйNPY_NOTYPE), указывающий на типы данных, к которым скаляр этого типа указанного вида может быть безопасно преобразован (обычно это означает без потери точности).
- int*cancastto
-
Либо
NULL, либо массив целых чисел (завершённыйNPY_NOTYPE), указывающий на типы данных, к которым этот тип данных может быть безопасно преобразован (обычно это означает без потери точности).
- intargmin(void*data, npy_intpn, npy_intp*min_ind, void*arr)
-
Указатель на функцию, которая получает индекс наименьшего из
nэлементов вarr, начиная с элемента, на который указываетdata. Эта функция требует, чтобы сегмент памяти был непрерывным и корректным. Возвращаемое значение всегда 0. Индекс наименьшего элемента возвращается вmin_ind.
- intscanfunc(FILE*fd, void*ip, void*arr)
PyArrayMethod_Context и PyArrayMethod_Spec
- типPyArrayMethodObject_tag
-
Непрозрачная структура, используемая для представления метода «self» в циклах ArrayMethod.
- типPyArrayMethod_Context
-
Структура, передаваемая в циклы ArrayMethod для предоставления контекста для выполнения цикла.
typedef struct { PyObject *caller; struct PyArrayMethodObject_tag *method; PyArray_Descr *const *descriptors; } PyArrayMethod_Context- PyObject*caller
-
Вызывающий объект, обычно ufunc, который вызвал цикл. Может быть
NULLв случае вызова не из ufunc (например, при преобразованиях).
- structPyArrayMethodObject_tag*method
-
Метод «self». В настоящее время этот объект является непрозрачным указателем.
- PyArray_Descr**descriptors
-
Массив описателей для цикла ufunc, заполняемый
resolve_descriptors. Длина массива равнаnin+nout.
- PyObject*caller
- типPyArrayMethod_Spec
-
Структура, используемая для регистрации ArrayMethod в NumPy. Мы используем механизм слотов, используемый ограниченным API Python. Смотрите определения слотов ниже.
typedef struct { const char *name; int nin, nout; NPY_CASTING casting; NPY_ARRAYMETHOD_FLAGS flags; PyArray_DTypeMeta **dtypes; PyType_Slot *slots; } PyArrayMethod_Spec;- constchar*name
-
Имя цикла.
- intnin
-
Количество входных операндов
- intnout
-
Количество выходных операндов.
- NPY_CASTINGcasting
-
Используется для указания степени разрешительности операции преобразования. Например, если операция преобразования в одних случаях может быть безопасной, а в других – нет, то
NPY_UNSAFE_CASTINGдолжно быть установлено. Не используется для циклов ufunc, но должно быть задано.
- NPY_ARRAYMETHOD_FLAGSflags
-
Флаги, установленные для метода.
- PyArray_DTypeMeta**dtypes
-
Типы данных (DTypes) для цикла. Должны составлять
nin+noutв длину.
- PyType_Slot*slots
-
Массив слотов для метода. Идентификаторы слотов должны быть одним из значений ниже.
- constchar*name
PyArray_DTypeMeta и PyArrayDTypeMeta_Spec
- PyTypeObjectPyArrayDTypeMeta_Type
-
Объект типа Python, соответствующий
PyArray_DTypeMeta.
- typePyArray_DTypeMeta
-
В значительной степени нечитаемый структуру, представляющую классы DType. Каждый экземпляр определяет метакласс для одного типа данных NumPy. Типы данных могут быть непараметрическими или параметрическими. Для непараметрических типов класс DType имеет взаимно однозначное соответствие с экземпляром описателя, созданным из класса DType. Параметрические типы могут соответствовать множеству различных экземпляров dtype в зависимости от выбранных параметров. Этот тип доступен в общедоступном заголовке
numpy/dtype_api.h. В настоящее время использование этой структуры не поддерживается в ограниченном API CPython, поэтому, еслиPy_LIMITED_APIустановлено, этот тип является псевдонимом дляPyTypeObject.typedef struct { PyHeapTypeObject super; PyArray_Descr *singleton; int type_num; PyTypeObject *scalar_type; npy_uint64 flags; void *dt_slots; void *reserved[3]; } PyArray_DTypeMeta- PyHeapTypeObjectsuper
-
Базовый класс, предоставляющий средства взаимодействия с API объектов Python. Члены этой структуры устанавливаются для заполнения функций, реализующих API
PyTypeObject(например,tp_new).
- PyArray_Descr*singleton
-
Экземпляр описателя, подходящий для использования в качестве описателя-синглетона для типа данных. Это полезно для непараметрических типов, представляющих простые типы данных, где существует только один логический экземпляр описателя для всех данных типа. Может быть NULL, если экземпляр-синглетон не подходит.
- inttype_num
-
Соответствует номеру типа для устаревших типов данных. Типы данных, определенные за пределами NumPy и, возможно, будущие типы данных, поставляемые с NumPy, будут иметь
type_num, установленным в -1, поэтому на этом не следует полагаться для различения типов данных.
- PyTypeObject*scalar_type
-
Тип скалярных экземпляров для этого типа данных.
- npy_uint64flags
-
Флаги могут быть установлены, чтобы указать NumPy, что этот тип данных имеет необязательное поведение. См. Флаги для списка допустимых значений флагов.
- void*dt_slots
-
Нечитаемый указатель на частную структуру, содержащую реализации функций в API DType. Это заполняется из члена
slotsэкземпляраPyArrayDTypeMeta_Specиспользуемого для инициализации DType.
- PyHeapTypeObjectsuper
- typePyArrayDTypeMeta_Spec
-
Структура, используемая для инициализации нового DType с помощью функции
PyArrayInitDTypeMeta_FromSpec.typedef struct { PyTypeObject *typeobj; int flags; PyArrayMethod_Spec **casts; PyType_Slot *slots; PyTypeObject *baseclass; }- PyTypeObject*typeobj
-
Либо
NULL, либо тип Python-скаляра, связанного с DType. Скалярное индексирование в массив возвращает элемент с этим типом.
- intflags
-
Статические флаги для класса DType, указывающие, является ли DType параметрическим, абстрактным или представляет числовые данные. Последнее является необязательным, но полезно для указания в коде, обрабатывающем DType, являются ли данные числами (целыми, вещественными или другими числовыми типами) или чем-то другим (например, строкой, единицей или датой).
- PyArrayMethod_Spec**casts;
-
Массив, завершаемый
NULL, спецификаций PyArrayMethod для преобразований, определенных DType.
- PyType_Slot*slots;
-
Массив, завершаемый
NULL, спецификаций слотов для реализации функций в API DType. Идентификаторы слотов должны быть одним из идентификаторов слотов DType, перечисленных в Идентификаторы слотов и типы функций API.
- PyTypeObject*typeobj
Экспонированные классы DTypes (PyArray_DTypeMeta объекты)
Для использования с промоутерами NumPy экспонирует ряд Dtypes, следуя шаблону PyArray_<Name>DType, соответствующему тем, которые находятся в np.dtypes.
Кроме того, три DType, PyArray_PyLongDType, PyArray_PyFloatDType, PyArray_PyComplexDType соответствуют значениям Python-скаляров. Они не могут быть использованы во всех местах, но, например, позволяют производить общие операции dtype и реализовывать продвижение с их помощью может быть необходимым.
Кроме того, определены следующие абстрактные DTypes, которые охватывают как встроенные NumPy, так и Python, и пользователи, в принципе, могут наследоваться от них (это не наследует никакой специфичной для DType функциональности): * PyArray_IntAbstractDType * PyArray_FloatAbstractDType * PyArray_ComplexAbstractDType
Предупреждение
Начиная с NumPy 2.0, единственное допустимое использование этих DTypes — регистрация промоутера для удобства, например, для сопоставления «любых целых чисел» (и проверки подклассов). Из-за этого они не экспонируются в Python.
PyUFunc_Type и PyUFuncObject
- PyTypeObjectPyUFunc_Type
-
Объект ufunc реализуется созданием
PyUFunc_Type. Это очень простой тип, реализующий только базовые функции getattribute, печати и имеющий поведение вызова, которое позволяет этим объектам действовать как функциям. Основная идея ufunc заключается в хранении ссылки на быстрые одномерные (векторные) циклы для каждого типа данных, поддерживающего операцию. Все эти одномерные циклы имеют одинаковую сигнатуру и являются ключевыми для создания нового ufunc. Они вызываются общим кодом цикла по мере необходимости для реализации N-мерной функции. Также определены некоторые общие одномерные циклы для массивов с плавающей запятой и комплексными числами с плавающей запятой, которые позволяют определять ufunc с использованием одной скалярной функции (например, atanh).
- typePyUFuncObject
-
Ядро ufunc — это
PyUFuncObject, содержащий всю необходимую информацию для вызова подлежащих C-кодовых циклов, выполняющих фактические операции. Хотя он описан здесь для полноты, следует рассматривать его как внутренний для NumPy и манипулировать им с помощьюPyUFunc_*функций. Размер этой структуры может изменяться в разных версиях NumPy. Для обеспечения совместимости:- Никогда не объявляйте экземпляр структуры без указателя
- Никогда не выполняйте арифметику указателей
- Никогда не используйте
sizeof(PyUFuncObject)
Его структура выглядит следующим образом:
typedef struct { PyObject_HEAD int nin; int nout; int nargs; int identity; PyUFuncGenericFunction *functions; void **data; int ntypes; int reserved1; const char *name; char *types; const char *doc; void *ptr; PyObject *obj; PyObject *userloops; int core_enabled; int core_num_dim_ix; int *core_num_dims; int *core_dim_ixs; int *core_offsets; char *core_signature; PyUFunc_TypeResolutionFunc *type_resolver; void *reserved2; void *reserved3; npy_uint32 *op_flags; npy_uint32 *iter_flags; /* new in API version 0x0000000D */ npy_intp *core_dim_sizes; npy_uint32 *core_dim_flags; PyObject *identity_value; /* Further private slots (size depends on the NumPy version) */ } PyUFuncObject;- intnin
-
Количество входных аргументов.
- intnout
-
Количество выходных аргументов.
- intnargs
-
Общее количество аргументов (nin + nout). Это значение должно быть меньше
NPY_MAXARGS.
- intidentity
-
Может быть
PyUFunc_One,PyUFunc_Zero,PyUFunc_MinusOne,PyUFunc_None,PyUFunc_ReorderableNoneилиPyUFunc_IdentityValue, чтобы указать единицу для данной операции. Используется только для вызова типа reduce на пустом массиве.
- voidfunctions(char**args, npy_intp*dims, npy_intp*steps, void*extradata)
-
Массив указателей на функции — по одному для каждого типа данных, поддерживаемого ufunc. Это векторный цикл, вызываемый для реализации подлежащей функции dims [0] раз. Первый аргумент, args, — массив из nargs указателей на данные. Сначала идут указатели на данные входных аргументов, а затем — указатели на данные выходных аргументов. Количество байтов, которое нужно пропустить, чтобы перейти к следующему элементу в последовательности, определяется соответствующим элементом массива steps. Последний аргумент позволяет циклу получать дополнительную информацию. Это обычно используется, чтобы один общий векторный цикл мог использоваться для нескольких функций. В этом случае фактическая скалярная функция для вызова передаётся в extradata. Размер этого массива указателей на функции равен ntypes.
- void**data
-
Дополнительные данные, которые передаются в 1-мерные векторные циклы или
NULLесли дополнительные данные не нужны. Этот массив C должен иметь такой же размер (т.е. ntypes), как и массив функций.NULLиспользуется, если дополнительные данные не нужны. Несколько вызовов C-API для UFuncs — это просто 1-мерные векторные циклы, которые используют эти дополнительные данные для получения указателя на фактическую вызываемую функцию.
- intntypes
-
Количество поддерживаемых типов данных для ufunc. Это число определяет количество различных 1-мерных циклов (встроенных типов данных), доступных для использования.
- char*name
-
Строковое имя для ufunc. Используется для динамического создания атрибута __doc__ для ufunc.
- char*types
-
Массив из \(nargs \times ntypes\) 8-битных номеров типов, содержащий сигнатуру типа для функции для каждого из поддерживаемых (встроенных) типов данных. Для каждой из ntypes функций соответствующий набор чисел типов в этом массиве показывает, как аргумент args должен интерпретироваться в 1-мерном векторном цикле. Эти числа типов не обязательно должны быть одинаковыми, и поддерживаются ufunc с смешанными типами.
- char*doc
-
Документация для ufunc. Не должна содержать сигнатуру функции, так как она генерируется динамически при получении __doc__.
- void*ptr
-
Любая динамически выделенная память. В настоящее время используется для динамических ufunc, созданных из python-функции, для хранения места для членов типа, данных и имени.
- PyObject*obj
-
Для ufunc, динамически созданных из python-функций, этот член содержит ссылку на подлежащую python-функцию.
- PyObject*userloops
-
Словарь пользовательских 1-мерных векторных циклов (хранящихся как указатели CObject) для пользовательских типов. Пользователь может зарегистрировать цикл для любого пользовательского типа. Он извлекается по номеру типа. Номера типов, определённые пользователем, всегда больше, чем
NPY_USERDEF.
- intcore_enabled
-
0 для скалярных ufunc; 1 для обобщённых ufunc
- intcore_num_dim_ix
-
Количество различных имён размерностей ядра в сигнатуре
- int*core_num_dims
-
Количество размерностей ядра каждого аргумента
- int*core_dim_ixs
-
Индексы размерностей в уплощённой форме; индексы аргумента
kхранятся вcore_dim_ixs[core_offsets[k] : core_offsets[k] + core_numdims[k]]
- int*core_offsets
-
Позиция 1-й размерности ядра каждого аргумента в
core_dim_ixs, эквивалентно cumsum(core_num_dims)
- char*core_signature
-
Строка сигнатуры ядра
- PyUFunc_TypeResolutionFunc*type_resolver
-
Функция, которая разрешает типы и заполняет массив типами данных для входных и выходных аргументов
- typePyUFunc_TypeResolutionFunc
-
Тип указателя на функцию для
type_resolver
- typePyUFunc_TypeResolutionFunc
- npy_uint32op_flags
-
Переопределяет стандартные флаги операндов для каждого операнда ufunc.
- npy_uint32iter_flags
-
Переопределяет стандартные флаги nditer для ufunc.
Добавлена в версию API 0x0000000D
- npy_intp*core_dim_sizes
-
Для каждого отдельного ядра измерения, возможный размер замороженный, если
UFUNC_CORE_DIM_SIZE_INFERREDравен0
- npy_uint32*core_dim_flags
-
Для каждого отдельного ядра измерения, набор флагов (
UFUNC_CORE_DIM_CAN_IGNOREиUFUNC_CORE_DIM_SIZE_INFERRED)
- PyObject*identity_value
-
Тождество для сокращения, когда
PyUFuncObject.identityравноPyUFunc_IdentityValue.
- npy_intp*core_dim_sizes
- UFUNC_CORE_DIM_CAN_IGNORE
-
если имя измерения заканчивается на
?
- UFUNC_CORE_DIM_SIZE_INFERRED
-
если размер измерения будет определяться из операндов, а не из замороженного определения.
PyArrayIter_Type и PyArrayIterObject
- PyTypeObjectPyArrayIter_Type
-
Это объект итератора, который упрощает циклирование по N-мерному массиву. Он возвращается атрибутом flat объекта ndarray. Он также широко используется во внутренней реализации для циклирования по N-мерному массиву. Интерфейс tp_as_mapping реализован для индексирования объекта итератора (с использованием 1-мерного индексирования), а некоторые методы реализованы через таблицу tp_methods. Этот объект реализует метод next и может использоваться везде, где в Python можно использовать итератор.
- типPyArrayIterObject
-
C-структура, соответствующая объекту
PyArrayIter_Type, — этоPyArrayIterObject.PyArrayIterObjectиспользуется для отслеживания указателя в N-мерном массиве. Он содержит связанную информацию, используемую для быстрого прохода по массиву. Указатель можно скорректировать тремя основными способами: 1) перейти к «следующей» позиции в массиве в стиле C, непрерывном порядке, 2) перейти к произвольной N-мерной координате в массиве и 3) перейти к произвольному одномерному индексу в массиве. Члены структурыPyArrayIterObjectиспользуются в этих вычислениях. Объекты итератора хранят свои собственные информацию о размерности и шагах массива. Это можно изменять по мере необходимости для «вещания» или для циклирования только по определённым измерениям.typedef struct { PyObject_HEAD int nd_m1; npy_intp index; npy_intp size; npy_intp coordinates[NPY_MAXDIMS_LEGACY_ITERS]; npy_intp dims_m1[NPY_MAXDIMS_LEGACY_ITERS]; npy_intp strides[NPY_MAXDIMS_LEGACY_ITERS]; npy_intp backstrides[NPY_MAXDIMS_LEGACY_ITERS]; npy_intp factors[NPY_MAXDIMS_LEGACY_ITERS]; PyArrayObject *ao; char *dataptr; npy_bool contiguous; } PyArrayIterObject;- intnd_m1
-
\(N-1\), где \(N\) — число измерений в базовом массиве.
- npy_intpindex
-
Текущий одномерный индекс в массиве.
- npy_intpsize
-
Полный размер базового массива.
- npy_intp*coordinates
-
N-мерный индекс в массиве.
- npy_intp*dims_m1
-
Размер массива минус 1 в каждом измерении.
- npy_intp*strides
-
Шаги массива. Сколько байт нужно перейти к следующему элементу в каждом измерении.
- npy_intp*backstrides
-
Сколько байт нужно перейти от конца измерения к его началу. Обратите внимание, что
backstrides[k] == strides[k] * dims_m1[k], но оно хранится здесь для оптимизации.
- npy_intp*factors
-
Этот массив используется для вычисления N-мерного индекса из одномерного индекса. Он содержит необходимые произведения измерений.
- PyArrayObject*ao
-
Указатель на базовый ndarray, который этот итератор представлял.
- char*dataptr
-
Этот член указывает на элемент в ndarray, указанный индексом.
- npy_boolcontiguous
-
Флаг true, если базовый массив является
NPY_ARRAY_C_CONTIGUOUS. Используется для упрощения вычислений, когда это возможно.
- intnd_m1
Более подробное описание использования итератора массива на уровне C приведено в последующих разделах. Как правило, вам не нужно беспокоиться о внутренней структуре объекта итератора, и с ним взаимодействуют с помощью макросов PyArray_ITER_NEXT (it), PyArray_ITER_GOTO (it, dest) или PyArray_ITER_GOTO1D (it, index). Все эти макросы требуют аргумента it, являющегося PyArrayIterObject*.
PyArrayMultiIter_Type и PyArrayMultiIterObject
- PyTypeObjectPyArrayMultiIter_Type
-
Этот тип предоставляет итератор, который обобщает концепцию транспонирования. Он позволяет транспонировать \(N\) массивов вместе, так что цикл продвигается по транспонированному массиву в стиле C-contiguous. Соответствующая структура C —
PyArrayMultiIterObject, расположение памяти которой должно начинаться с любого объекта, obj, переданного в функциюPyArray_Broadcast(obj). Транспонирование выполняется путем корректировки итераторов массивов, так что каждый итератор представляет транспонированную форму и размер, но его шаги корректируются таким образом, чтобы на каждой итерации использовался правильный элемент из массива.
- typePyArrayMultiIterObject
-
typedef struct { PyObject_HEAD int numiter; npy_intp size; npy_intp index; int nd; npy_intp dimensions[NPY_MAXDIMS_LEGACY_ITERS]; PyArrayIterObject *iters[]; } PyArrayMultiIterObject;- intnumiter
-
Количество массивов, которые необходимо транспонировать до одинаковой формы.
- npy_intpsize
-
Общий размер транспонированного массива.
- npy_intpindex
-
Текущий (1-мерный) индекс в транспонированном результате.
- intnd
-
Количество измерений в транспонированном результате.
- npy_intp*dimensions
-
Форма транспонированного результата (используются только
ndслоты).
- PyArrayIterObject**iters
-
Массив объектов-итераторов, содержащих итераторы для транспонируемых массивов. По возвращении итераторы корректируются для транспонирования.
- intnumiter
PyArrayNeighborhoodIter_Type и PyArrayNeighborhoodIterObject
- PyTypeObjectPyArrayNeighborhoodIter_Type
-
Это объект-итератор, который упрощает циклирование по N-мерному окрестности.
- typePyArrayNeighborhoodIterObject
-
Структура C, соответствующая объекту
PyArrayNeighborhoodIter_Type, — этоPyArrayNeighborhoodIterObject.typedef struct { PyObject_HEAD int nd_m1; npy_intp index, size; npy_intp coordinates[NPY_MAXDIMS_LEGACY_ITERS] npy_intp dims_m1[NPY_MAXDIMS_LEGACY_ITERS]; npy_intp strides[NPY_MAXDIMS_LEGACY_ITERS]; npy_intp backstrides[NPY_MAXDIMS_LEGACY_ITERS]; npy_intp factors[NPY_MAXDIMS_LEGACY_ITERS]; PyArrayObject *ao; char *dataptr; npy_bool contiguous; npy_intp bounds[NPY_MAXDIMS_LEGACY_ITERS][2]; npy_intp limits[NPY_MAXDIMS_LEGACY_ITERS][2]; npy_intp limits_sizes[NPY_MAXDIMS_LEGACY_ITERS]; npy_iter_get_dataptr_t translate; npy_intp nd; npy_intp dimensions[NPY_MAXDIMS_LEGACY_ITERS]; PyArrayIterObject* _internal_iter; char* constant; int mode; } PyArrayNeighborhoodIterObject;
Типы массивов скаляров
Для каждого из встроенных типов данных, которые могут присутствовать в массиве, существует тип Python. Большинство из них являются простыми оболочками над соответствующим типом данных в C. Имена типов в C — Py{TYPE}ArrType_Type где {TYPE} может быть
Bool, Byte, Short, Int, Long, LongLong, UByte, UShort, UInt, ULong, ULongLong, Half, Float, Double, LongDouble, CFloat, CDouble, CLongDouble, String, Unicode, Void, Datetime, Timedelta и Object.
Эти имена типов являются частью C-API и поэтому могут быть созданы в коде расширения на C. Также есть PyIntpArrType_Type и PyUIntpArrType_Type, которые являются простыми заменителями одного из целочисленных типов, способного хранить указатель на платформе. Структура этих скалярных объектов не доступна коду на C. Функция PyArray_ScalarAsCtype (..) может использоваться для извлечения значения типа C из скаляра массива, а функция PyArray_Scalar (…) может использоваться для построения скаляра массива из значения C.
Другие структуры C
Несколько новых структур C оказались полезными при разработке NumPy. Эти структуры C используются как минимум в одном вызове C-API и поэтому задокументированы здесь. Основная причина определения этих структур заключается в том, чтобы упростить использование C-API Python ParseTuple для преобразования из объектов Python в полезные объекты C.
PyArray_Dims
- типPyArray_Dims
-
Эта структура очень полезна, когда необходимо интерпретировать информацию о форме и/или шагах. Структура имеет вид:
typedef struct { npy_intp *ptr; int len; } PyArray_Dims;Члены этой структуры:
- npy_intp*ptr
-
Указатель на список целых чисел (
npy_intp), обычно представляющих форму массива или шаги массива.
- intlen
-
Длина списка целых чисел. Предполагается, что доступ к ptr[0] до ptr[len-1] безопасен.
- npy_intp*ptr
PyArray_Chunk
- типPyArray_Chunk
-
Эта структура эквивалентна структуре объекта буфера в Python до члена ptr. На 32-битных платформах (т.е. если
NPY_SIZEOF_INT==NPY_SIZEOF_INTP), член len также соответствует эквивалентному члену объекта буфера. Она полезна для представления общего куска памяти из одного сегмента.typedef struct { PyObject_HEAD PyObject *base; void *ptr; npy_intp len; int flags; } PyArray_Chunk;Члены:
- PyObject*base
-
Объект Python, из которого происходит этот кусок памяти. Необходим для правильного учета памяти.
- void*ptr
-
Указатель на начало односегментного куска памяти.
- npy_intplen
-
Длина сегмента в байтах.
- intflags
-
Любые флаги данных (например,
NPY_ARRAY_WRITEABLE), которые должны использоваться для интерпретации памяти.
- PyObject*base
PyArrayInterface
См. также
- типPyArrayInterface
-
Структура
PyArrayInterfaceопределена таким образом, чтобы NumPy и другие модули расширений могли использовать протокол быстрого интерфейса массива. Метод__array_struct__объекта, поддерживающего протокол быстрого интерфейса массива, должен возвращатьPyCapsule, содержащий указатель на структуруPyArrayInterfaceс соответствующими подробностями массива. После создания нового массива атрибут должен бытьDECREF’d, что освободит структуруPyArrayInterface. Не забудьтеINCREFобъект (чьи атрибут__array_struct__был получен) и укажите член base новогоPyArrayObjectна этот же объект. Таким образом, память для массива будет управляться правильно.typedef struct { int two; int nd; char typekind; int itemsize; int flags; npy_intp *shape; npy_intp *strides; void *data; PyObject *descr; } PyArrayInterface;- inttwo
-
целое число 2 в качестве проверки на корректность.
- intnd
-
количество измерений в массиве.
- chartypekind
-
Символ, указывающий на тип массива согласно соглашению о строках типов: ‘t’ -> битовое поле, ‘b’ -> булево, ‘i’ -> целое со знаком, ‘u’ -> целое без знака, ‘f’ -> число с плавающей точкой, ‘c’ -> комплексное число с плавающей точкой, ‘O’ -> объект, ‘S’ -> (байт-)строка, ‘U’ -> юникод, ‘V’ -> пусто.
- intitemsize
-
Количество байтов, необходимых для каждого элемента в массиве.
- intflags
-
Любые биты
NPY_ARRAY_C_CONTIGUOUS(1),NPY_ARRAY_F_CONTIGUOUS(2),NPY_ARRAY_ALIGNED(0x100),NPY_ARRAY_NOTSWAPPED(0x200), илиNPY_ARRAY_WRITEABLE(0x400) для указания чего-либо о данных. ФлагиNPY_ARRAY_ALIGNED,NPY_ARRAY_C_CONTIGUOUSиNPY_ARRAY_F_CONTIGUOUSфактически могут быть определены из других параметров. ФлагNPY_ARR_HAS_DESCR(0x800) также может быть установлен для указания объектам, потребляющим интерфейс массива версии 3, что член descr структуры присутствует (он будет проигнорирован объектами, потребляющими интерфейс массива версии 2).
- npy_intp*shape
-
Массив, содержащий размер массива в каждом измерении.
- npy_intp*strides
-
Массив, содержащий количество байтов для перехода к следующему элементу в каждом измерении.
- void*data
-
Указатель на первый элемент массива.
- PyObject*descr
-
Объект Python, описывающий тип данных более подробно (так же, как и ключ descr в
__array_interface__). Этот член может бытьNULLесли typekind и itemsize предоставляют достаточную информацию. Этот член также игнорируется, если флагNPY_ARR_HAS_DESCRне установлен в flags.
- inttwo
Внутренние структуры
Во внутренней части кода используются дополнительные объекты Python, в основном для управления памятью. Эти типы недоступны напрямую из Python и не экспонируются в C-API. Они включены сюда только для полноты и помощи в понимании кода.
- типPyUFunc_Loop1d
-
Простой связанный список C-структур, содержащий информацию, необходимую для определения 1-мерного цикла для ufunc для каждой определённой сигнатуры пользовательского типа данных.
- PyTypeObjectPyArrayMapIter_Type
-
Обработка расширенной индексации выполняется с помощью этого типа Python. Это просто оболочка вокруг C-структуры, содержащей переменные, необходимые для расширенной индексации массивов.
- типPyArrayMapIterObject
-
C-структура, связанная с
PyArrayMapIter_Type. Эта структура полезна, если вы пытаетесь понять код сопоставления расширенных индексов. Она определена в заголовкеarrayobject.h. Этот тип не экспонируется в Python и мог бы быть заменён C-структурой. Как тип Python, он использует управление памятью с подсчётом ссылок.
© 2005–2024 NumPy Developers
Licensed under the 3-clause BSD License.
https://numpy.org/doc/2.0/reference/c-api/types-and-structures.html