• Примитивный модуль на C для Python течёт по памяти?

    @MikhailEdoshin
    Со списком все в порядке, проблема во взаимодействии функций. Py_BuildValue возвращает new reference, то есть объект со счетчиком ссылок, установленным в единицу, которым теперь владеет ваш код. Функция же PyList_Append не забирает у вас этот объект, а тоже увеличивает счетчик ссылок еще на единицу. Теперь у полученной строки будет два владельца — список и ваш код. Когда вы удалите список, он честно отнимет свою единичку от счетчика ссылок, но ваша-то там останется, поэтому Питон будет думать, что кто-то где-то эту строку еще использует.

    Вам нужно или явно уменьшить счетчик:

    PyObject *list, *item; /* static, право, ни к чему */
    list = PyList_New(0);
    item = Py_BuildValue("s"; "test");
    PyList_Append(list, item);
    Py_DECREF(item);
    return list;
    

    или же использовать функцию, которая не увеличивает счетчик (steals reference):

    PyObject *list;
    list = PyList_New(1); /* оставляем место для элемента */
    PyList_SET_ITEM(list, Py_BuildValue("s"; "test"));
    return list;
    

    (В данном случае я использовал макрос PyList_SET_ITEM, который как раз подходит для заполнения новых списков.)
    Ответ написан
    4 комментария