如何用上一个和下一个邻居的均值替换离群值?

时间:2019-05-21 09:40:18

标签: python python-3.x numpy jupyter

我有一个非常大的数据集,它击败了两个激光频率并以频率读出拍频。计数器。

问题是我的数据集中有很多异常值。

滤波不是一种选择,因为离群值的滤波/消除会杀死我用于分析拍频的Allan偏差的宝贵信息。

消除异常值的问题是我想比较三个不同拍频的艾伦偏差。如果现在删除一些点,则我的x轴将比以前更短,而我的allan偏差x轴的缩放比例将有所不同。 (adev基本上会建立一个新的x轴,从我的采样率间隔开始,直到我最长的测量时间->这是我的最高拍频x轴值。)

抱歉,如果这令人困惑,我想提供尽可能多的信息。

因此,无论如何,直到现在,我的工作是使我所有的Allan偏差都可以工作并成功消除异常值,将我的清单切成间隔并将每个间隔的所有y值与该间隔的标准偏差进行比较。

我现在要更改的是,我不想删除异常值,而是希望用其上一个和下一个邻居的均值替换它们。

在下面您可以找到带有异常值的列表的测试代码,在使用numpy的地方似乎有问题,而我并不真正理解为什么。

错误被给出为“'numpy.int32'对象没有属性'where'”。我必须将数据集转换为熊猫结构吗?

代码执行的操作是搜索高于/低于我的阈值的值,将其替换为NaN,然后​​用我的均值替换NaN。我不是真的喜欢使用NaN替代品,所以我将非常感谢您的帮助。


l = np.array([[0,4],[1,3],[2,25],[3,4],[4,28],[5,4],[6,3],[7,4],[8,4]])

print(*l)

sd = np.std(l[:,1])

print(sd)

for i in l[:,1]:

    if l[i,1] > sd:
        print(l[i,1])
        l[i,1].where(l[i,1].replace(to_replace = l[i,1], value = np.nan),
                other = (l[i,1].fillna(method='ffill')+l[i,1].fillna(method='bfill'))/2)

所以我想要的是一个具有离群值的列表/数组,用先前/后续邻居的方式替换

  

错误消息:“ numpy.int32”对象没有属性“ where”

1 个答案:

答案 0 :(得分:0)

一个选项的确可以通过

将所有工作转化为熊猫
import pandas as pd
dataset = pd.DataFrame({'Column1':data[:,0],'Column2':data[:,1]})

这将解决错误,因为pandas dataframe对象具有where命令。 Howewer,这不是强制性的,我们仍然可以仅使用numpy进行操作

例如,检测异常值的最简单方法是查看异常值是否不在均值+ -3std范围内。 下面的代码示例,使用您的设置

import numpy as np
l = np.array([[0,4],[1,3],[2,25],[3,4],[4,28],[5,4],[6,3],[7,4],[8,4]])
std = np.std(l[:,1])
mean=np.mean(l[:,1])
for i in range (len(l[:,1])):
    if((l[i,1]<=mean+2*std)&(l[i,1]>=mean-2*std)):
        pass
    else:
        if (i!=len(l[:,1])-1)&(i!=0):
              l[i,1]=(l[i-1,1]+l[i+1,1])/2
        else:
              l[i,1]=mean

我们在这里首先检查的是值在行的异常值

if((l[i,1]<=mean+2*std)&(l[i,1]>=mean-2*std)):
        pass

然后检查其不是第一个还是最后一个元素

if (i!=len(l[:,1])-1)&(i!=1):

如果是,则在字段中输入均值:

else:
     l[i,1]=mean