J'ai une fonction qui prend l'argument NBins
. Je veux appeler cette fonction avec un scalaire 50
ou un tableau [0, 10, 20, 30]
. Comment puis-je identifier au sein de la fonction, quelle est sa longueur NBins
? ou dit différemment, si c'est un scalaire ou un vecteur?
J'ai essayé ceci:
>>> N=[2,3,5]
>>> P = 5
>>> len(N)
3
>>> len(P)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: object of type 'int' has no len()
>>>
Comme vous le voyez, je ne peux pas demander len
à P
, car il est pas un tableau .... Y at - il quelque chose comme isarray
ou isscalar
en python?
Merci
type
?Réponses:
Pour prendre en charge tout type de séquence, cochez
collections.Sequence
au lieu delist
.Remarque :
isinstance
prend également en charge un tuple de classes, la vérificationtype(x) in (..., ...)
doit être évitée et n'est pas nécessaire.Vous pouvez également vérifier
not isinstance(x, (str, unicode))
la source
list
pour devenir faux pour les scalaires ... mercicollections.Sequence
c'est aussi un ABC pour la chaîne, donc cela devrait être pris en compte. J'utilise quelque chose commeif type(x) is not str and isinstance(x, collections.Sequence):
. Ce n'est pas génial, mais c'est fiable.type
, et vérifiez égalementnot isinstance(x, (str, unicode))
Python 2Les réponses précédentes supposent que le tableau est une liste standard python. En tant que personne qui utilise numpy souvent, je recommanderais un test très pythonique de:
la source
__len__
attribut (donc je suppose, pas techniquement un type scalaire)if hasattr(N, '__len__') and (not isinstance(N, str))
rendrait correctement compte des chaînes.En combinant les réponses de @jamylak et @ jpaddison3 ensemble, si vous devez être robuste contre les tableaux numpy en entrée et les gérer de la même manière que les listes, vous devez utiliser
Ceci est robuste contre les sous-classes de tableaux list, tuple et numpy.
Et si vous voulez également être robuste contre toutes les autres sous-classes de séquence (pas seulement la liste et le tuple), utilisez
Pourquoi devriez-vous procéder
isinstance
ainsi sans vous comparertype(P)
à une valeur cible? Voici un exemple, où nous créons et étudions le comportement d'NewList
une sous-classe triviale de liste.Malgré leur comparaison
x
et leury
égalité, leur manipulationtype
entraînerait un comportement différent. Cependant, puisqu'ilx
s'agit d'une instance d'une sous-classe delist
, usingisinstance(x,list)
donne le comportement et les traitements souhaitésx
ety
de la même manière.la source
isinstance(P, (list, tuple, set, np.ndarray))
Existe-t-il un équivalent à isscalar () dans numpy? Oui.
la source
>>> np.isscalar('abcd')
revientTrue
.return (isinstance(num, generic) or type(num) in ScalarType or isinstance(num, numbers.Number))
numpy.isscalar()
fonction souffre d'un certain nombre de défauts de conception inconciliables et sera probablement déconseillée lors d'une prochaine révision. Pour paraphraser la documentation officielle : "Dans presque tous les cas,np.ndim(x) == 0
il faut utiliser à la place denp.isscaler(x)
, car le premier retournera également correctement true pour les tableaux 0d." Une alternative robuste et compatible avec le futurnumpy.isscalar()
serait donc de boucler trivialementnumpy.ndim()
: par exemple,def is_scalar(obj): return np.ndim(obj) == 0
np.isscalar
c'est déroutant. Doc officiel suggéré d'utilisernp.array.ndim
partout, c'est-ànp.isscalar(np.array(12))
- dire Faux alors qu'il devrait être considéré comme scalaire carnp.array(12).ndim
est 0.Alors que l'approche de @ jamylak est la meilleure, voici une approche alternative
la source
type(p) in (list, )
.Une autre approche alternative (utilisation de la propriété de nom de classe ):
Pas besoin d'importer quoi que ce soit.
la source
Voici la meilleure approche que j'ai trouvée: Vérifier l'existence de
__len__
et__getitem__
.Vous vous demandez peut-être pourquoi? Les raisons incluent:
isinstance(obj, abc.Sequence)
échoue sur certains objets, y compris le tenseur de PyTorch car ils n'implémentent pas__contains__
.__len__
et__getitem__
qui me semble être des méthodes minimales pour les objets de type tableau.Alors sans plus tarder:
Notez que j'ai ajouté des paramètres par défaut, car la plupart du temps, vous souhaiterez peut-être considérer les chaînes comme des valeurs, et non comme des tableaux. De même pour les tuples.
la source
la source
Vous pouvez vérifier le type de données de la variable.
Il vous donnera un type de données de P.
Pour que vous puissiez différencier qu'il s'agit d'un entier ou d'un tableau.
la source
Je suis surpris qu'une telle question de base ne semble pas avoir de réponse immédiate en python. Il me semble que presque toutes les réponses proposées utilisent une sorte de vérification de type, ce qui n'est généralement pas conseillé en python et elles semblent limitées à un cas spécifique (elles échouent avec différents types numériques ou objets génériques itérables qui ne sont pas des tuples ou des listes).
Pour moi, ce qui fonctionne mieux, c'est d'importer numpy et d'utiliser array.size, par exemple:
A noter également:
mais:
la source
Utilisez simplement
size
au lieu delen
!la source
np.size(5)
etnp.size([5])
sont tous les deux ==1
, donc cela ne distingue pas correctement le type (c'est-à-dire, identifier un scalaire), ce qui, je crois, est le but.preds_test [0] est de forme (128,128,1) Permet de vérifier son type de données en utilisant la fonction isinstance () isinstance prend 2 arguments. Le premier argument correspond aux données Le deuxième argument correspond au type de données isinstance (preds_test [0], np.ndarray) donne la sortie True. Cela signifie que preds_test [0] est un tableau.
la source
Pour répondre à la question dans le titre, un moyen direct de savoir si une variable est un scalaire est d'essayer de la convertir en un flottant. Si vous obtenez
TypeError
, ce n'est pas le cas.la source