使用向量化函数重新分类 numpy float 数组时出现广播错误
Broadcasting error when reclassifying numpy float array using vectorized function
我想评估 2D numpy float 数组中的每个值是否落在某个数值 class 的最小、最大边界内。接下来,我想将该值重新分配给与 class 关联的 'score'。
例如 class 边界可以是:
>>> class1 = (0, 1.5)
>>> class2 = (1.5, 2.5)
>>> class3 = (2.5, 3.5)
class 分数是:
>>> score1 = 0.75
>>> score2 = 0.50
>>> score3 = 0.25
任何 class 之外的值应默认为例如99.
我已经尝试了以下方法,但是 运行 由于广播而陷入 ValueError。
>>> import numpy as np
>>> arr_f = (6-0)*np.random.random_sample((4,4)) + 0 # array of random floats
>>> def reclasser(x, classes, news):
>>> compare = [x >= min and x < max for (min, max) in classes]
>>> try:
>>> return news[compare.index(True)
>>> except Value Error:
>>> return 99.0
>>> v_func = np.vectorize(reclasser)
>>> out = v_func(arr_f, [class1, class2, class3], [score1, score2, score3])
ValueError: operands could not be broadcast together with shapes (4,4) (4,2) (4,)
如果您能就此错误发生的原因以及如何补救提出任何建议,我们将不胜感激。另外,如果我在使用向量化函数的道路上完全走错了路,我也很高兴听到这个消息。
尝试先让代码在不使用 np.vectorize
的情况下运行。即使将单个浮点数作为第一个参数,上面的代码也不会工作。你拼错了ValueError
;使用 min
和 max
作为变量名也不是一个好主意(它们是 Python 函数)。 reclasser
的固定版本是:
def reclasser(x, classes, news):
compare = [min(cls) < x < max(cls) for cls in classes]
try:
return news[compare.index(True)]
except ValueError:
return 99.0
也就是说,我认为使用重分类器和 np.vectorize
过于复杂。相反,您可以这样做:
# class -> score mapping as a dict
class_scores = {class1: score1, class2: score2, class3: score3}
# matrix of default scores
scores = 99 * np.ones(arr_f.shape)
for cls, score in class_scores.items():
# see which array values belong into current class
in_cls = np.logical_and(cls[0] < arr_f, arr_f < cls[1])
# update scores for current class
scores[np.where(in_cls)] = score
scores
将是对应于原始数据数组的分数数组。
我想评估 2D numpy float 数组中的每个值是否落在某个数值 class 的最小、最大边界内。接下来,我想将该值重新分配给与 class 关联的 'score'。
例如 class 边界可以是:
>>> class1 = (0, 1.5)
>>> class2 = (1.5, 2.5)
>>> class3 = (2.5, 3.5)
class 分数是:
>>> score1 = 0.75
>>> score2 = 0.50
>>> score3 = 0.25
任何 class 之外的值应默认为例如99.
我已经尝试了以下方法,但是 运行 由于广播而陷入 ValueError。
>>> import numpy as np
>>> arr_f = (6-0)*np.random.random_sample((4,4)) + 0 # array of random floats
>>> def reclasser(x, classes, news):
>>> compare = [x >= min and x < max for (min, max) in classes]
>>> try:
>>> return news[compare.index(True)
>>> except Value Error:
>>> return 99.0
>>> v_func = np.vectorize(reclasser)
>>> out = v_func(arr_f, [class1, class2, class3], [score1, score2, score3])
ValueError: operands could not be broadcast together with shapes (4,4) (4,2) (4,)
如果您能就此错误发生的原因以及如何补救提出任何建议,我们将不胜感激。另外,如果我在使用向量化函数的道路上完全走错了路,我也很高兴听到这个消息。
尝试先让代码在不使用 np.vectorize
的情况下运行。即使将单个浮点数作为第一个参数,上面的代码也不会工作。你拼错了ValueError
;使用 min
和 max
作为变量名也不是一个好主意(它们是 Python 函数)。 reclasser
的固定版本是:
def reclasser(x, classes, news):
compare = [min(cls) < x < max(cls) for cls in classes]
try:
return news[compare.index(True)]
except ValueError:
return 99.0
也就是说,我认为使用重分类器和 np.vectorize
过于复杂。相反,您可以这样做:
# class -> score mapping as a dict
class_scores = {class1: score1, class2: score2, class3: score3}
# matrix of default scores
scores = 99 * np.ones(arr_f.shape)
for cls, score in class_scores.items():
# see which array values belong into current class
in_cls = np.logical_and(cls[0] < arr_f, arr_f < cls[1])
# update scores for current class
scores[np.where(in_cls)] = score
scores
将是对应于原始数据数组的分数数组。