2017-04-09 80 views
1

在我的脚本中,我需要比较相当大的NumPy数组(2D或3D)和阈值。 的比较本身可以做很容易与“allclose”功能,这样做:将NumPy数组与阈值进行比较并返回差异

Threshold = 0.1 
if (np.allclose(Arr1, Arr2, Threshold, equal_nan=True)): 
    Print('Same') 

最简单的(但天真的)办法知道哪些小区是不一样的是使用一个简单的for循环这样的代码之一:

def CheckWhichCellsAreNotEqualInArrays(Arr1,Arr2,Threshold): 
    if not Arr1.shape == Arr2.shape: 
     return ['Arrays size not the same'] 
    Dimensions = Arr1.shape 
    Diff = [] 
    for i in range(Dimensions [0]): 
     for j in range(Dimensions [1]): 
      if not np.allclose(Arr1[i][j], Arr2[i][j], Threshold, equal_nan=True): 
       Diff.append(',' + str(i) + ',' + str(j) + ',' + str(Arr1[i,j]) + ',' 
       + str(Arr2[i,j]) + ',' + str(Threshold) + ',Fail\n') 
     return Diff 

(和相同的用于3D阵列 - 以1更for循环)

这种方式是非常缓慢的,当阵列是大和全没有相等的细胞。

如果他们不一样 - 是否有一个快速直接的方式 - 获取不均匀细胞的列表?也许NumPy本身有一些内置函数?

+0

生产样品数据? – Divakar

+0

是的。 如果单元格不相等 - 我想获取单元格的坐标和两个数组中的值。 – Nissim

回答

0

功能allclose相当于allisclose的组合。因此,您可以将整个数组应用isclose,然后在需要时将all应用于某些轴,而不是循环使用阵列的某些维度。 (重要的是,all取轴参数,而allclose不取)。使用4D随机数据阵列的示例,其中正在比较一些2D切片。

threshold = 0.1 
arr1 = 10 + np.random.normal(size=((40, 30, 20, 10))) 
arr2 = arr1 + 0.3 * np.random.normal(size=((40, 30, 20, 10))) 
print(np.all(np.isclose(arr1, arr2, threshold), axis=(2, 3))) 

的打印的二维数组表示哪个切片的满足allclose条件:

array([[False, True, True, ..., True, True, False], 
     [ True, False, True, ..., True, True, False], 
     [False, True, True, ..., False, True, True], 
     ..., 
     [False, False, True, ..., True, True, True], 
     [ True, True, True, ..., False, True, True], 
     [ True, False, True, ..., True, False, False]], dtype=bool) 

即,arr1[0, 0]arr2[0, 0]不接近;但是arr1[0, 1]arr2[0, 1]都是。如有必要,您可以深入查看元素级别以确定close条件的完全失败; np.isclose(arr1, arr2, threshold)拥有所有这些信息。