¿Por qué pylint devuelve `unsubscriptable-object` para numpy.ndarray.shape?

9

Acabo de armar el siguiente caso de repro "mínimo" (mínimo entre comillas porque quería asegurarme de que pylintno arroje otros errores, advertencias, sugerencias o sugerencias, lo que significa que hay un poco de repetitivo):

pylint_error.py :

"""
Docstring
"""

import numpy as np


def main():
    """
    Main entrypoint
    """
    test = np.array([1])
    print(test.shape[0])


if __name__ == "__main__":
    main()

Cuando ejecuto pylinteste código ( pylint pylint_error.py) obtengo el siguiente resultado:

$> pylint pylint_error.py
************* Module pylint_error
pylint_error.py:13:10: E1136: Value 'test.shape' is unsubscriptable (unsubscriptable-object)

------------------------------------------------------------------
Your code has been rated at 1.67/10 (previous run: 1.67/10, +0.00)

Afirma que test.shapeno es subscriptable, aunque claramente lo es. Cuando ejecuto el código funciona bien:

$> python pylint_error.py
1

Entonces, ¿qué está causando pylintconfusión y cómo puedo solucionarlo?

Algunas notas adicionales:

  • Si declaro la prueba ya que np.arange(1)el error desaparece
  • Si Declaro prueba como np.zeros(1), np.zeros((1)), np.ones(1), o np.ones((1))el error no no desaparece
  • Si declaro la prueba ya que np.full((1), 1)el error desaparece
  • Especificar el tipo ( test: np.ndarray = np.array([1])) no corrige el error
  • Especificar a dtype( np.array([1], dtype=np.uint8)) no corrige el error
  • Tomar una porción de prueba ( test[:].shape) hace que el error desaparezca

Mi primer instinto dice que el comportamiento inconsistente con varios NumPYmétodos ( arangevs zerosvs full, etc.) sugiere que es solo un error NumPY. Sin embargo, es posible que haya algún concepto subyacente NumPYque no entiendo. Me gustaría estar seguro de que no estoy escribiendo código con un comportamiento indefinido que solo funciona por accidente.

stevendesu
fuente
1
Me culpo pylintantesnumpy
hpaulj

Respuestas:

5

No tengo suficiente reputación para comentar, pero parece que este es un problema abierto: https://github.com/PyCQA/pylint/issues/3139

Hasta que el problema se resuelva por su parte, simplemente cambiaría la línea a

    print(test.shape[0])  # pylint: disable=E1136  # pylint/issues/3139

a mi pylintrcarchivo

ignorando la gravedad
fuente
1
Gracias por vincular el problema. Por desgracia pylint también se queja de líneas es demasiado largo, así que creo que puede seguir con print(test[:].shape[0])más de su solución, ya que hace que mis líneas más cortas y me salva de pylints incesantes molesta
stevendesu
2
NOTA: Las versiones recientes de pylint advierten sobre la desactivación por ID, por lo que recomiendo algo más como esto en la línea anterior:# pylint: disable=unsubscriptable-object # pylint/issues/3139
Bryce Schober
2

A partir de noviembre de 2019:

Como mencionó uno de los usuarios en la discusión sobre GitHub , podría resolver el problema degradando tanto pylint como astroid , por ejemplo, enrequirements.txt

astroid>=2.0, <2.3
pylint>=2.3, <2.4

o

pip install astroid==2.2.5 & pip install pylint==2.3.1
Tomasz Bartkowiak
fuente