Estoy tratando de acelerar la respuesta aquí usando Cython. Intento compilar el código (después de hacer el cygwinccompiler.py
hack explicado aquí ), pero aparece un fatal error: numpy/arrayobject.h: No such file or directory...compilation terminated
error. ¿Alguien puede decirme si hay un problema con mi código o alguna sutileza esotérica con Cython?
Abajo está mi código.
import numpy as np
import scipy as sp
cimport numpy as np
cimport cython
cdef inline np.ndarray[np.int, ndim=1] fbincount(np.ndarray[np.int_t, ndim=1] x):
cdef int m = np.amax(x)+1
cdef int n = x.size
cdef unsigned int i
cdef np.ndarray[np.int_t, ndim=1] c = np.zeros(m, dtype=np.int)
for i in xrange(n):
c[<unsigned int>x[i]] += 1
return c
cdef packed struct Point:
np.float64_t f0, f1
@cython.boundscheck(False)
def sparsemaker(np.ndarray[np.float_t, ndim=2] X not None,
np.ndarray[np.float_t, ndim=2] Y not None,
np.ndarray[np.float_t, ndim=2] Z not None):
cdef np.ndarray[np.float64_t, ndim=1] counts, factor
cdef np.ndarray[np.int_t, ndim=1] row, col, repeats
cdef np.ndarray[Point] indices
cdef int x_, y_
_, row = np.unique(X, return_inverse=True); x_ = _.size
_, col = np.unique(Y, return_inverse=True); y_ = _.size
indices = np.rec.fromarrays([row,col])
_, repeats = np.unique(indices, return_inverse=True)
counts = 1. / fbincount(repeats)
Z.flat *= counts.take(repeats)
return sp.sparse.csr_matrix((Z.flat,(row,col)), shape=(x_, y_)).toarray()
Respuestas:
En su
setup.py
, elExtension
debería tener el argumentoinclude_dirs=[numpy.get_include()]
.Además, te falta
np.import_array()
tu código.-
Ejemplo setup.py:
fuente
np.import_array()
? ¿No es eso para el Numpy C-API ?warning: untitled.pyx:8:49: Buffer unpacking not optimized away.
np.import_array()
. Sin embargo, rara vez escribo extensiones de Cython que usan numpy sin él, así que lo uso por costumbre. En cuanto a su otro problema, lo que citó es solo una advertencia, no un error. Si tiene otros errores que necesitan reparación, haga una nueva publicación.include_dirs=[numpy.get_include()]
es un buen truco gracias!include_dirs
pasado asetup()
se ignora en las últimas destutils, se debe pasar a cada unoExtension
, al menos en macPara un proyecto de un archivo como el suyo, otra alternativa es usar
pyximport
. No necesita crear unsetup.py
... ni siquiera necesita abrir una línea de comando si usa IPython ... todo es muy conveniente. En su caso, intente ejecutar estos comandos en IPython o en un script Python normal:Es posible que deba editar el compilador, por supuesto. Esto hace que la importación y la recarga funcionen igual para los
.pyx
archivos que para los.py
archivos.Fuente: http://wiki.cython.org/InstallingOnWindows
fuente
pyximport
afecta la velocidad de mi código? Y finalmente, la sección aquí: " Desde Cython 0.11, el módulo pyximport también tiene soporte de compilación experimental para módulos Python normales ..." implica que todavía tiene algunos problemas para resolver. ¿Puedes explicar eso también?.py
módulos se compilan normalmente (no con cython) mientras que los.pyx
módulos se compilan con cython. Si pasapyimport = True
enpyximport.install()
, entonces se usará Cython por todo, incluso por ejemploimport random
oimport os
. No sugiero usar esa función, simplemente porque no hay una razón convincente para usarla, y podría crear problemas. Probablemente lo usan principalmente los desarrolladores de cython.pyximport
funciona, creará exactamente el mismo código C que cualquier otro método. Así que pruébalo y verás. Me refiero al hecho de que cuando el proceso de compilación se complica bastante, por ejemplo, enlaces a bibliotecas externos del sistema, puede encontrarse con que pyximport falla y necesita unasetup.py
ycythonize
especificar exactamente cómo construirlo. Pero el hecho de que su.pyx
módulo tengaimport
s ocimport
s no significa que no se pueda compilarpyximport
; bien puede estar totalmente bien.El error significa que no se encuentra un archivo de encabezado numpy durante la compilación.
Intenta hacerlo
export CFLAGS=-I/usr/lib/python2.7/site-packages/numpy/core/include/
y luego compila. Este es un problema con algunos paquetes diferentes. Hay un error archivado en ArchLinux para el mismo problema: https://bugs.archlinux.org/task/22326fuente
export
línea? En misetup.py
archivopython setup.py
) ejecute elexport ..
comando primero. Establece las variables ambientales del shell, no nada que tenga que ver directamente con [pc] ython.'export' is not recognized as an internal or external command, operable program or batch file.
error ... simplemente no puedo ganar con este ...Respuesta simple
Una manera más simple es agregar la ruta a su archivo
distutils.cfg
. Su nombre de ruta de Windows 7 es por defectoC:\Python27\Lib\distutils\
. Simplemente afirma los siguientes contenidos y debería funcionar:Archivo de configuración completo
Para darle un ejemplo de cómo podría verse el archivo de configuración, se lee todo mi archivo:
fuente
Debería poder hacerlo dentro de la
cythonize()
función como se menciona aquí , pero no funciona porque hay un problema conocidofuente
Si eres demasiado vago para escribir archivos de configuración y descubrir la ruta para incluir directorios, prueba cyper . Puede compilar su código Cython y configurarlo
include_dirs
para Numpy automáticamente.Cargue su código en una cadena, luego simplemente ejecute
cymodule = cyper.inline(code_string)
, luego su función estará disponible de formacymodule.sparsemaker
instantánea. Algo como estoPuede instalar cyper a través de
pip install cyper
.fuente