Cython: Как перемещать большие объекты, не копируя их?
Я использую Cython, чтобы обернуть код C ++ и выставить его на Python для интерактивной работы. Моя проблема заключается в том, что мне нужно читать большие графики (несколько гигабайт) из файла, и они в конечном итоге дважды в памяти. Может ли кто-нибудь помочь мне диагностировать и решить эту проблему?
Моя оболочка Cython для класса графа выглядит так:
cdef extern from "../src/graph/Graph.h":
cdef cppclass _Graph "Graph":
_Graph() except +
_Graph(count) except +
count numberOfNodes() except +
count numberOfEdges() except +
cdef class Graph:
"""An undirected, optionally weighted graph"""
cdef _Graph _this
def __cinit__(self, n=None):
if n is not None:
self._this = _Graph(n)
# any _thisect which appears as a return type needs to implement setThis
cdef setThis(self, _Graph other):
#del self._this
self._this = other
return self
def numberOfNodes(self):
return self._this.numberOfNodes()
def numberOfEdges(self):
return self._this.numberOfEdges()
Если необходимо вернуть граф Python, его нужно создать пустым, а затемsetThis
метод используется для установки нативного_Graph
экземпляр. Это происходит, например, когдаGraph
читается из файла. Это работа этого класса:
cdef extern from "../src/io/METISGraphReader.h":
cdef cppclass _METISGraphReader "METISGraphReader":
_METISGraphReader() except +
_Graph read(string path) except +
cdef class METISGraphReader:
""" Reads the METIS adjacency file format [1]
[1]: http://people.sc.fsu.edu/~jburkardt/data/metis_graph/metis_graph.html
"""
cdef _METISGraphReader _this
def read(self, path):
pathbytes = path.encode("utf-8") # string needs to be converted to bytes, which are coerced to std::string
return Graph(0).setThis(self._this.read(pathbytes))
Интерактивное использование выглядит следующим образом:
>>> G = graphio.METISGraphReader().read("giant.metis.graph")
После того, как чтение из файла завершено и используется память X ГБ, наступает фаза, на которой, очевидно, происходит копирование, и после этого используется память 2X ГБ. Вся память освобождается, когдаdel G
называется.
Где моя ошибка, которая приводит к копированию и существованию дважды в памяти?