Warum gibt pylint für unspy.ndarray.shape "unsubscriptable-object" zurück?

9

Ich habe gerade den folgenden "minimalen" Repro-Fall zusammengestellt (Minimum in Anführungszeichen, weil ich sicherstellen wollte, dass pylintkeine anderen Fehler, Warnungen, Hinweise oder Vorschläge ausgegeben wurden - was bedeutet, dass es ein bisschen Boilerplate gibt):

pylint_error.py :

"""
Docstring
"""

import numpy as np


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


if __name__ == "__main__":
    main()

Wenn ich pylintdiesen Code ( pylint pylint_error.py) ausführe, erhalte ich die folgende Ausgabe:

$> 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)

Es wird behauptet, dass dies test.shapenicht abonnierbar ist, obwohl es ganz klar ist. Wenn ich den Code ausführe, funktioniert es einwandfrei:

$> python pylint_error.py
1

Was führt also pylintzu Verwirrung und wie kann ich das beheben?

Einige zusätzliche Hinweise:

  • Wenn ich den Test deklariere, verschwindet np.arange(1)der Fehler
  • Wenn ich Test erklären , wie np.zeros(1), np.zeros((1)), np.ones(1)oder np.ones((1))der Fehler nicht nicht weggehen
  • Wenn ich den Test deklariere, verschwindet np.full((1), 1)der Fehler
  • Die Angabe der Art ( test: np.ndarray = np.array([1])) nicht nicht beheben den Fehler
  • Die Angabe eines dtype( np.array([1], dtype=np.uint8)) nicht nicht den Fehler beheben
  • Wenn Sie ein Stück test ( test[:].shape) nehmen, verschwindet der Fehler

Mein erster Instinkt besagt, dass das inkonsistente Verhalten mit verschiedenen NumPYMethoden ( arangevs zerosvs fullusw.) darauf hindeutet, dass es sich nur um einen Fehler handelt NumPY. Es ist jedoch möglich, NumPYdass ich ein Missverständnis habe. Ich möchte sichergehen, dass ich keinen Code mit undefiniertem Verhalten schreibe, der nur bei Unfällen funktioniert.

stevendesu
quelle
1
Ich würde pylintvorher beschuldigennumpy
hpaulj

Antworten:

5

Ich habe nicht genug Ruf, um einen Kommentar abzugeben, aber es sieht so aus, als wäre dies ein offenes Problem: https://github.com/PyCQA/pylint/issues/3139

Bis das Problem am Ende behoben ist, würde ich einfach die Zeile in ändern

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

zu meiner pylintrcDatei.

Ignorieren der Schwerkraft
quelle
1
Vielen Dank für die Verknüpfung des Problems. Leider pylint auch beschwert sich über Leitungen zu lang ist, so glaube ich , mit Stick kann print(test[:].shape[0])über Ihre Lösung , da sie kürzer meine Linien macht und erspart mir pylints quälende unaufhörlichen
stevendesu
2
HINWEIS: Neuere Versionen von Pylint warnen vor dem Deaktivieren durch ID. Daher empfehle ich in der vorhergehenden Zeile etwas Ähnliches:# pylint: disable=unsubscriptable-object # pylint/issues/3139
Bryce Schober
2

Stand November 2019:

Wie durch einen der Benutzer in der Diskussion über die genannten GitHub könnten Sie das Problem durch die Herabstufung lösen sowohl Pylint und astroid , zB inrequirements.txt

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

oder

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