Repository: numpy/numpy
File: numpy/_core/src/multiarray/ctors.c (C)

Code before:

static PyArray_Descr *
_infer_descr_from_dtype(PyArray_DTypeMeta *dtype) {
    if (dtype == NULL) {
        return PyArray_DescrFromType(NPY_DEFAULT_TYPE);
    }
    if (dtype->singleton != NULL) {
        Py_INCREF(dtype->singleton);
        return dtype->singleton;
    }
    return NPY_DT_CALL_default_descr(dtype);
}

/*
 * Recursive helper to assign using a coercion cache. This function
 * must consume the cache depth first, just as the cache was originally
 * produced.
 */
NPY_NO_EXPORT int
PyArray_AssignFromCache_Recursive(
        PyArrayObject *self, const int ndim, coercion_cache_obj **cache)
{
    /* Consume first cache element by extracting information and freeing it */
    PyObject *obj = (*cache)->arr_or_sequence;
    Py_INCREF(obj);
    PyObject *orig_obj = (*cache)->converted_obj;
    npy_bool sequence = (*cache)->sequence;
    int depth = (*cache)->depth;
    int ret = 0;
    *cache = npy_unlink_coercion_cache(*cache);

    /* The element is either a sequence, or an array */
    if (!sequence) {
        /* Straight forward array assignment */
        assert(PyArray_Check(obj));
        if (PyArray_CopyInto(self, (PyArrayObject *)obj) < 0) {
            goto fail;
        }
    }
    else {
        assert(depth != ndim);
        // this macro thakes *the argument* of PySequence_Fast, which is orig_obj;
        // not the object returned by PySequence_Fast, which is obj
        NPY_BEGIN_CRITICAL_SECTION_SEQUENCE_FAST(orig_obj);
        npy_intp length = PySequence_Length(obj);
        if (length != PyArray_DIMS(self)[0]) {
            PyErr_SetString(PyExc_RuntimeError,
                            "Inconsistent object during array creation? "
                            "Content of sequences changed (length inconsistent).");
            ret = -1;
            goto finish_section;

Review comment (suggestion):
I'd call this differently, maybe `orig_seq` -- `orig_obj` seems super confusing in this context -- even more since `converted_obj` is assigned to it.

Code after:

static PyArray_Descr *
_infer_descr_from_dtype(PyArray_DTypeMeta *dtype) {
    if (dtype == NULL) {
        return PyArray_DescrFromType(NPY_DEFAULT_TYPE);
    }
    if (dtype->singleton != NULL) {
        Py_INCREF(dtype->singleton);
        return dtype->singleton;
    }
    return NPY_DT_CALL_default_descr(dtype);
}

/*
 * Recursive helper to assign using a coercion cache. This function
 * must consume the cache depth first, just as the cache was originally
 * produced.
 */
NPY_NO_EXPORT int
PyArray_AssignFromCache_Recursive(
        PyArrayObject *self, const int ndim, coercion_cache_obj **cache)
{
    int ret = -1;
    /* Consume first cache element by extracting information and freeing it */
    PyObject *obj = (*cache)->arr_or_sequence;
    Py_INCREF(obj);
    npy_bool is_sequence = (*cache)->sequence;
    /*
      If it is a sequence, this object is the argument to PySequence_Fast, e.g.
      the iterable that the user wants to coerce into an array
    */
    PyObject *orig_seq = (*cache)->converted_obj;
    /* Owned reference to an item in the sequence */
    PyObject *item_pyvalue = NULL;
    int depth = (*cache)->depth;
    *cache = npy_unlink_coercion_cache(*cache);

    /* The element is either a sequence or an array */
    if (!is_sequence) {
        /* Straight forward array assignment */
        assert(PyArray_Check(obj));
        if (PyArray_CopyInto(self, (PyArrayObject *)obj) < 0) {
            goto finish;
        }
    }
    else {
        assert(depth != ndim);
        npy_intp orig_length = PyArray_DIMS(self)[0];
        int err = 1;
        NPY_BEGIN_CRITICAL_SECTION_SEQUENCE_FAST(orig_seq);
        for (npy_intp i = 0; i < orig_length; i++) {