Python 如何在多个1-d numpy数组中的元素之间采用模式

Python 如何在多个1-d numpy数组中的元素之间采用模式,python,numpy,element,Python,Numpy,Element,我能够按以下方式逐元素计算多个列表/数组的总和 sum([np.array([1,2,3,4,5]), np.array([1,2,3,4,5])]) = array([ 2, 4, 6, 8, 10]) 我想对阵列中每个元素的模式执行类似的操作,并获得预期的结果: 模式[np.数组[1,2,3,4,5],np.数组[1,2,3,4,5]]=数组[1,2,3,4,5] 在没有单一模式的情况下,我想随机选择其中一个数组中的元素作为输出,如下所示: 模式[np.数组[0,2,3,4,0],n

我能够按以下方式逐元素计算多个列表/数组的总和

sum([np.array([1,2,3,4,5]), np.array([1,2,3,4,5])]) = array([ 2,  4,  6,  8, 10])
我想对阵列中每个元素的模式执行类似的操作,并获得预期的结果:

模式[np.数组[1,2,3,4,5],np.数组[1,2,3,4,5]]=数组[1,2,3,4,5]

在没有单一模式的情况下,我想随机选择其中一个数组中的元素作为输出,如下所示:

模式[np.数组[0,2,3,4,0],np.数组[1,2,9,4,5]]=数组[1,2,9,4,0]

最后,我希望能够跨任意数量的等长数组执行此操作

注意:我尝试使用统计库模式,但出现以下错误:

>>> mode([np.array([1,2,3,4,5]), np.array([1,2,3,4,5])])
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/anaconda3/lib/python3.7/statistics.py", line 501, in mode
    table = _counts(data)
  File "/anaconda3/lib/python3.7/statistics.py", line 252, in _counts
    table = collections.Counter(iter(data)).most_common()
  File "/anaconda3/lib/python3.7/collections/__init__.py", line 566, in __init__
    self.update(*args, **kwds)
  File "/anaconda3/lib/python3.7/collections/__init__.py", line 653, in update
    _count_elements(self, iterable)
TypeError: unhashable type: 'numpy.ndarray'
当只使用一个列表时,它也会抛出一个错误

因此,我正在寻找实现这一目标的方法


一个关键要求是,阵列元素中模式的输出向量必须与每个向量长度相同,我将把它输入混淆矩阵,以便与参考向量进行比较。

您可以使用scipy.stats.mode找到模式。您还可以将多个numpy数组连接到单个数组中,然后将其馈送到模式

import numpy as np
import scipy.stats

arrays = [np.array([0,2,3,4,0]), np.array([1,2,9,4,5])]

result = scipy.stats.mode(np.concatenate(arrays))
# ModeResult(mode=array([0]), count=array([2]))

result.mode
# array([0])
scipy.stats.mode的返回值是一个名为tuple ModeResult的值,其中包括模式和值出现的次数

要查找每列的模式,可以将阵列堆叠到二维阵列中,然后沿第一个轴查找模式

arrays = [
    np.array([0, 2, 3, 4, 0]), 
    np.array([1, 2, 9, 4, 5]), 
    np.array([0, 9, 9, 4, 1])]
result = scipy.stats.mode(np.stack(arrays), axis=0)
result.mode
# array([[0, 2, 9, 4, 0]])

您可以使用scipy.stats.mode找到该模式。您还可以将多个numpy数组连接到单个数组中,然后将其馈送到模式

import numpy as np
import scipy.stats

arrays = [np.array([0,2,3,4,0]), np.array([1,2,9,4,5])]

result = scipy.stats.mode(np.concatenate(arrays))
# ModeResult(mode=array([0]), count=array([2]))

result.mode
# array([0])
scipy.stats.mode的返回值是一个名为tuple ModeResult的值,其中包括模式和值出现的次数

要查找每列的模式,可以将阵列堆叠到二维阵列中,然后沿第一个轴查找模式

arrays = [
    np.array([0, 2, 3, 4, 0]), 
    np.array([1, 2, 9, 4, 5]), 
    np.array([0, 9, 9, 4, 1])]
result = scipy.stats.mode(np.stack(arrays), axis=0)
result.mode
# array([[0, 2, 9, 4, 0]])

举两个例子:

In [358]: alist = [np.array([1,2,3,4,5]), np.array([1,2,3,4,5])]                        
In [359]: alist1 = [np.array([0,2,3,4,0]), np.array([1,2,9,4,5])]                       
两个来源:

In [360]: import statistics                                                             
In [361]: from scipy import stats                                                       
使用zip*alist,我们可以采用相应的“配对”模式:

In [362]: [statistics.mode(foo) for foo in zip(*alist)]                                 
Out[362]: [1, 2, 3, 4, 5]
In [363]: [statistics.mode(foo) for foo in zip(*alist1)]                                
....
StatisticsError: no unique mode; found 2 equally common values
模式文档警告此错误

scipy版本将列表转换为2d数组;哪个

In [365]: stats.mode(alist,axis=0)                                                      
Out[365]: ModeResult(mode=array([[1, 2, 3, 4, 5]]), count=array([[2, 2, 2, 2, 2]]))
In [366]: stats.mode(alist1,axis=0)                                                     
Out[366]: ModeResult(mode=array([[0, 2, 3, 4, 0]]), count=array([[1, 2, 1, 2, 1]]))
In [367]: np.array(alist1)                                                              
Out[367]: 
array([[0, 2, 3, 4, 0],
       [1, 2, 9, 4, 5]])
stats.mode代码是Python,因此可以对其进行研究。对于这样的轴选择,它显然会在列上迭代,在每个列上采用1d模式。因此,速度将与列表理解情况相当。但对StatError案的处理是不同的

但我们可以使用一点实用功能来处理错误情况:

In [375]: def myfn(foo): 
     ...:     try: 
     ...:         return statistics.mode(foo) 
     ...:     except statistics.StatisticsError: 
     ...:         return None # or a random value 
     ...:                                                                               
In [376]: [myfn(foo) for foo in zip(*alist)]                                            
Out[376]: [1, 2, 3, 4, 5]
In [377]: [myfn(foo) for foo in zip(*alist1)]                                           
Out[377]: [None, 2, None, 4, None]
列表理解时间是有利的:

In [378]: timeit [myfn(foo) for foo in zip(*alist1)]                                    
73.6 µs ± 278 ns per loop (mean ± std. dev. of 7 runs, 10000 loops each)
In [379]: timeit stats.mode(alist1,axis=0)                                              
384 µs ± 1.09 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)

举两个例子:

In [358]: alist = [np.array([1,2,3,4,5]), np.array([1,2,3,4,5])]                        
In [359]: alist1 = [np.array([0,2,3,4,0]), np.array([1,2,9,4,5])]                       
两个来源:

In [360]: import statistics                                                             
In [361]: from scipy import stats                                                       
使用zip*alist,我们可以采用相应的“配对”模式:

In [362]: [statistics.mode(foo) for foo in zip(*alist)]                                 
Out[362]: [1, 2, 3, 4, 5]
In [363]: [statistics.mode(foo) for foo in zip(*alist1)]                                
....
StatisticsError: no unique mode; found 2 equally common values
模式文档警告此错误

scipy版本将列表转换为2d数组;哪个

In [365]: stats.mode(alist,axis=0)                                                      
Out[365]: ModeResult(mode=array([[1, 2, 3, 4, 5]]), count=array([[2, 2, 2, 2, 2]]))
In [366]: stats.mode(alist1,axis=0)                                                     
Out[366]: ModeResult(mode=array([[0, 2, 3, 4, 0]]), count=array([[1, 2, 1, 2, 1]]))
In [367]: np.array(alist1)                                                              
Out[367]: 
array([[0, 2, 3, 4, 0],
       [1, 2, 9, 4, 5]])
stats.mode代码是Python,因此可以对其进行研究。对于这样的轴选择,它显然会在列上迭代,在每个列上采用1d模式。因此,速度将与列表理解情况相当。但对StatError案的处理是不同的

但我们可以使用一点实用功能来处理错误情况:

In [375]: def myfn(foo): 
     ...:     try: 
     ...:         return statistics.mode(foo) 
     ...:     except statistics.StatisticsError: 
     ...:         return None # or a random value 
     ...:                                                                               
In [376]: [myfn(foo) for foo in zip(*alist)]                                            
Out[376]: [1, 2, 3, 4, 5]
In [377]: [myfn(foo) for foo in zip(*alist1)]                                           
Out[377]: [None, 2, None, 4, None]
列表理解时间是有利的:

In [378]: timeit [myfn(foo) for foo in zip(*alist1)]                                    
73.6 µs ± 278 ns per loop (mean ± std. dev. of 7 runs, 10000 loops each)
In [379]: timeit stats.mode(alist1,axis=0)                                              
384 µs ± 1.09 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)

你可以用我试过的。我将发布我收到的错误。此外,即使它是tto工作,我将如何处理没有模式的情况?你将不得不张贴一个最小的,可重复的例子,并解释什么是错误的。发布一些其他人可以在不更改任何内容的情况下运行的代码。模式是为数字定义的,不进行任何类型的对象方法定义。scipy模式根据输入生成2d数组,并在列之间迭代,每次确定一列的模式。我怀疑[modeargs for args in zip[arr1,arr2]]也可以。您可以使用我尝试过的。我将发布我收到的错误。此外,即使它是tto工作,我将如何处理没有模式的情况?你将不得不张贴一个最小的,可重复的例子,并解释什么是错误的。发布一些其他人可以在不更改任何内容的情况下运行的代码。模式是为数字定义的,不进行任何类型的对象方法定义。scipy模式根据输入生成2d数组,并在列之间迭代,每次确定一列的模式。我怀疑[modeargs for args in zip[arr1,arr2]]也可以。您使用的是什么版本的scipy?我在scipy.1.4.1版中没有看到这个错误。如果找到多个模式,则scipy.stats.mode返回的数字最小。不完全是,我将添加更多要求。另外,这会抛出一个错误:statistics.StatisticsError:无唯一模式;发现3个同样常见的值是坏的!我使用的是统计库中的模式。如果找到多个/没有模式,而不是随机数,我可以接受选择的最小数字。最大的要求是我不是采用数组中元素的模式,而是采用数组之间的模式,一个元素接一个元素。否则,这就很接近了。有没有转置th的方法
是吗?我想我明白了。请查看我的更新答案。您使用的是什么版本的scipy?我在scipy.1.4.1版中没有看到这个错误。如果找到多个模式,则scipy.stats.mode返回的数字最小。不完全是,我将添加更多要求。另外,这会抛出一个错误:statistics.StatisticsError:无唯一模式;发现3个同样常见的值是坏的!我使用的是统计库中的模式。如果找到多个/没有模式,而不是随机数,我可以接受选择的最小数字。最大的要求是我不是采用数组中元素的模式,而是采用数组之间的模式,一个元素接一个元素。否则,这就很接近了。有没有办法把这个转过来?我想我明白了。请看我的最新答案。