代码之家  ›  专栏  ›  技术社区  ›  id101112

如何从我的熊猫数据帧中检测出峰值(异常值)

  •  3
  • id101112  · 技术社区  · 6 年前

    我有一个熊猫数据帧,有几个速度值在不断移动,但它是一个传感器数据,所以我们经常会在移动平均值似乎也没有帮助的某些点的中间出现错误,所以我可以使用什么方法从中删除这些异常值或峰值数据?

    示例:

    data points=0.5,0.5,0.7,0.6,0.5,0.7,0.5,0.4,0.6,4,0.5,0.5,4,5,6,0.4,0.7,0.8,0.9_
    

    在这个数据中,如果我看到点4、4、5、6完全是离群值, 在我使用5分钟窗口框架的滚动平均值平滑这些值之前,但是我仍然得到了许多我想要删除的blip点的类型,是否有人建议我使用任何技术来消除这些点。

    我有一个更清晰的数据视图:

    如果你在这里看到数据是如何显示一些离群点的,我必须删除这些离群点? 你知道怎样才能摆脱这些问题吗?

    例子:

    data points = {0.5,0.5,0.7,0.6,0.5,0.7,0.5,0.4,0.6,4,0.5,0.5,4,5,6,0.4,0.7,0.8,0.9}
    

    在这个数据中,如果我看到点4、4、5、6完全是离群值, 在我使用5分钟的窗口框架滚动平均值来平滑这些值之前,但是我仍然得到了许多类型的点,我想删除这些点,有人能建议我任何技术来消除这些点吗?

    我有一个更清晰的数据视图: enter image description here

    如果你在这里看到数据是如何显示一些离群点的,我必须删除这些离群点? 你知道怎样才能摆脱这些问题吗?

    2 回复  |  直到 6 年前
        1
  •  3
  •   vestland    6 年前

    我真的认为z-score使用的是scipy.stats.zscore.html“rel=”nofollow noreferrer“>scipy.stats.zscore(). is the way to go here.请参阅本帖中的相关问题。在这里,他们主要关注使用哪种方法来删除潜在的异常值。如我所见,您的挑战要简单一点,因为根据提供的数据判断,在不需要转换数据的情况下,识别潜在的异常值是非常直接的。下面是一个这样做的代码片段。但是请记住,异常值的存在和不存在完全取决于您的数据集。在删除了一些离群值之后,以前没有看起来像离群值的东西,现在会突然这样做。看看:

    导入matplotlib.pyplot as plt 将熊猫作为PD导入 将numpy导入为np 从scipy导入统计 #您的数据(作为列表) 数据=[0.5,0.5,0.7,0.6,0.5,0.7,0.5,0.4,0.6,4,0.5,0.5,4,5,6,0.4,0.7,0.8,0.9] #初始绘图 df1=pd.数据帧(数据=数据) df1.columns=[“数据”] df1.绘图(style='o') #用于识别和删除异常值的函数 定义异常值(df,级别): #1.临时数据帧 df=df1.copy(深=真) #2.第二步。选择Z分数的级别以识别和删除异常值 df_z=df[(np.abs(stats.zscore(df))<level).all(axis=1)] ix_keep=df_z.索引 #第三条:用要保留的索引子集原始数据帧 df_keep=df.loc[ix_keep] 返回(df_keep)
    
    

    原始数据:

    测试运行1:z-score=4:

    如您所见,由于级别设置得太高,因此未删除任何数据。

    测试运行2:z-score=2:

    现在我们到了某个地方。删除了两个异常值,但仍有一些可疑数据。

    测试运行3:z-score=1.2:

    这看起来真不错。剩下的数据现在似乎比以前更加均匀地分布。但现在,由原始数据点突出显示的数据点开始看起来有点像一个潜在的离群值。那么在哪里停车呢?这完全取决于你!

    edit:here's the whole thing for an easy copy&paste:

    导入matplotlib.pyplot as plt 将熊猫作为PD导入 将numpy导入为np 从scipy导入统计 #您的数据(作为列表) 数据=[0.5,0.5,0.7,0.6,0.5,0.7,0.5,0.4,0.6,4,0.5,0.5,4,5,6,0.4,0.7,0.8,0.9] #初始绘图 df1=pd.数据帧(数据=数据) df1.columns=[“数据”] df1.绘图(style='o') #用于识别和删除异常值的函数 定义异常值(df,级别): #1.临时数据帧 df=df1.copy(深=真) #2.第二步。选择Z分数的级别以识别和删除异常值 df_z=df[(np.abs(stats.zscore(df))<level).all(axis=1)] ix_keep=df_z.索引 #第三条:用要保留的索引子集原始数据帧 df_keep=df.loc[ix_keep] 返回(df_keep) #删除异常值 级别=1.2 打印(“df_clean=outliers(df=df1,level=”+str(level))+') df_clean=异常值(df=df1,level=level) #最终绘图 df ou clean.plot(style='o')
    是到这里的路。在中查看相关问题this post.在那里,他们专注于使用哪种方法之前删除潜在的异常值。如我所见,您的挑战要简单一点,因为根据提供的数据判断,在不需要转换数据的情况下,识别潜在的异常值是非常直接的。下面是一个这样做的代码片段。但是请记住,异常值的存在和不存在完全取决于您的数据集。移除后一些离群值,以前看起来不像离群值的东西,现在突然就会这样了。看看:

    import matplotlib.pyplot as plt
    import pandas as pd
    import numpy as np
    from scipy import stats
    
    # your data (as a list)
    data = [0.5,0.5,0.7,0.6,0.5,0.7,0.5,0.4,0.6,4,0.5,0.5,4,5,6,0.4,0.7,0.8,0.9]
    
    # initial plot
    df1 = pd.DataFrame(data = data)
    df1.columns = ['data']
    df1.plot(style = 'o')
    
    # Function to identify and remove outliers
    def outliers(df, level):
    
        # 1. temporary dataframe
        df = df1.copy(deep = True)
    
        # 2. Select a level for a Z-score to identify and remove outliers
        df_Z = df[(np.abs(stats.zscore(df)) < level).all(axis=1)]
        ix_keep = df_Z.index
    
        # 3. Subset the raw dataframe with the indexes you'd like to keep
        df_keep = df.loc[ix_keep]
    
        return(df_keep)
    

    原始数据:

    enter image description here

    试运行1:Z分=4:

    enter image description here

    如您所见,由于级别设置得太高,没有删除任何数据。

    试运行2:Z分=2:

    enter image description here

    现在我们到了某个地方。删除了两个异常值,但仍有一些可疑数据。

    试运行3:Z分=1.2:

    enter image description here

    这看起来真不错。剩下的数据现在似乎比以前更加均匀地分布。但现在,由原始数据点突出显示的数据点开始看起来有点像一个潜在的离群值。那么在哪里停车呢?这完全取决于你!

    编辑:以下是简单复制和粘贴的全部内容:

    import matplotlib.pyplot as plt
    import pandas as pd
    import numpy as np
    from scipy import stats
    
    # your data (as a list)
    data = [0.5,0.5,0.7,0.6,0.5,0.7,0.5,0.4,0.6,4,0.5,0.5,4,5,6,0.4,0.7,0.8,0.9]
    
    # initial plot
    df1 = pd.DataFrame(data = data)
    df1.columns = ['data']
    df1.plot(style = 'o')
    
    # Function to identify and remove outliers
    def outliers(df, level):
    
        # 1. temporary dataframe
        df = df1.copy(deep = True)
    
        # 2. Select a level for a Z-score to identify and remove outliers
        df_Z = df[(np.abs(stats.zscore(df)) < level).all(axis=1)]
        ix_keep = df_Z.index
    
        # 3. Subset the raw dataframe with the indexes you'd like to keep
        df_keep = df.loc[ix_keep]
    
        return(df_keep)
    
    # remove outliers
    level = 1.2
    print("df_clean = outliers(df = df1, level = " + str(level)+')')
    df_clean = outliers(df = df1, level = level)
    
    # final plot
    df_clean.plot(style = 'o')
    
        2
  •  1
  •   Dav2357    6 年前

    您可以将某个分位数上的值切割为以下值:

    import numpy as np
    clean_data=np.array(data_points)[(data_points<=np.percentile(data_points, 95))]
    

    在熊猫中你会用到 df.quantile ,你可以找到它 here

    或者您可以使用q3+1.5*iqr方法消除异常值,就像通过箱线图一样。