Numpy: np.random.choice devuelve un índice fuera de rango en un problema de matriz enmascarado.

Creado en 15 ago. 2020  ·  6Comentarios  ·  Fuente: numpy/numpy

import numpy as np

a = np.array([0.1, 0.2, 0.4, 0.3])
masked_a = np.ma.masked_array(a, [0, 0, 1, 1])
counter = np.zeros(len(a) + 1)
while True:
    action = np.random.choice(len(a), p=masked_a)
    counter[action] += 1
    print(counter / counter.sum())

# [0.09931198 0.20076697 0.         0.         0.69992105]

No debería devolver un índice> 3, pero cuando el último elemento de la matriz enmascarada es verdadero, puede devolver índice = 4

00 - Bug numpy.ma numpy.random

Todos 6 comentarios

El problema también ocurre en Generator.choice en la versión de desarrollo de numpy:

In [1]: import numpy as np

In [2]: np.__version__ 
Out[2]: '1.20.0.dev0+986e533'

In [3]: rng = np.random.default_rng()

In [4]: pm = np.ma.masked_array([0.1, 0.2, 0.4, 0.3], mask=[0, 0, 1, 1])

In [5]: rng.choice(4, p=pm, size=12)
Out[5]: array([4, 4, 4, 0, 4, 1, 4, 0, 0, 4, 4, 4])

Anteriormente agregué la etiqueta "error", pero eso es un juicio subjetivo. Hay otras funciones en numpy que no manejan matrices enmascaradas correctamente (o mejor, "correctamente", ya que "corrección" también puede ser una decisión) donde no necesariamente lo consideramos un error. Quizás este sea solo un ejemplo de comportamiento indefinido, y la respuesta corta al problema es "¡no hagas eso!". Sin embargo, sería mejor si pudiéramos generar una excepción en lugar de devolver resultados sin sentido.

Sería bastante fácil agregar una verificación explícita para una matriz enmascarada y generar un error si alguno de los valores está realmente enmascarado, pero eso se siente como una solución ad hoc muy específica.

¿Se envía Generator.choice a __array_function__ ? Si no es así, probablemente debería hacerlo.

Si es así, entonces creo que simplemente agregamos esto con todos los otros errores de "maskedarray decae porque aún no hemos implementado __array_function__ ".

Anteriormente agregué la etiqueta "error", pero eso es un juicio subjetivo. Hay otras funciones en numpy que no manejan matrices enmascaradas correctamente (o mejor, "correctamente", ya que "corrección" también puede ser una decisión) donde no necesariamente lo consideramos un error. Quizás este sea solo un ejemplo de comportamiento indefinido, y la respuesta corta al problema es "¡no hagas eso!". Sin embargo, sería mejor si pudiéramos generar una excepción en lugar de devolver resultados sin sentido.

Sería bastante fácil agregar una verificación explícita para una matriz enmascarada y generar un error si alguno de los valores está realmente enmascarado, pero eso se siente como una solución ad hoc muy específica.

Creo que si no lo maneja correctamente, no debería permitir pasar una matriz enmascarada (debería generar una excepción) pero funciona correctamente en su mayoría (funciona bien excepto en algunos casos). puede causar problemas potenciales para el entorno de producción.

No hay uso de __array_function__ en Generator . Si bien muchas entradas obligan a que se comporten bien C contiguas, es probable que en ese caso algunas funciones no siempre fuercen esto de manera lo suficientemente religiosa.

Si agrega NPY_ARRAY_ENSUREARRAY , terminará con un ndarray que está lleno e ignora la máscara. Es difícil decir que esto es "correcto". En el ejemplo de @WarrenWeckesser , esto termina usando pm=np.array([.1,.2,.3,.4]) como probabilidades.

¿Fue útil esta página
0 / 5 - 0 calificaciones