【问题标题】:Data filtering with Python使用 Python 进行数据过滤
【发布时间】:2021-11-13 15:58:55
【问题描述】:

我有两个列表来制作点 (x,y) 的坐标。对于每个 x 值,都有一个 y 值,我可以绘制(此处为线图)蓝色图。然而,y 变化迅速,信号模糊,尽管总体上清楚地显示出一些重复。我需要提取一条更平滑的线,就像用红色绘制的那样。任何人都可以提出如何过滤原始数据并在之后应用一些回归的建议?

这是前 20 个点的代码和数据

import matplotlib.pyplot as plt;
x = [0.00, 0.10, 0.20, 0.30, 0.40, 0.50, 0.60, 0.70, 0.80, 0.90, 1.00, 1.10, 1.20, 1.30, 1.40, 1.50, 1.60, 1.70, 1.80, 1.90]
y = [-5.39, -11.86, -14.46, -12.73, -12.74, -8.17, -3.00, -9.63, -6.86, -2.59, -7.98, -8.31, -6.62, -4.68, -7.23, -4.10, -5.43, -7.89, -7.23, -6.10]
fig, axes = plt.subplots(nrows=1, ncols=1, figsize = (10, 5));
axes.set(xlabel='x', ylabel='y');
axes.plot(x, y, linewidth = 2, color = 'dodgerblue')
plt.scatter(x, y, color = 'lime', s = 25);

完整的 x 和 y 数据可以在此链接中找到,它们是由单个空格分隔的两列文本:

https://drive.google.com/file/d/1pI4sA20BgBGEjHCkSL5TaeSBGvBORwld/view?usp=sharing

谢谢。

【问题讨论】:

  • 你能提供更多的积分吗?至少可以看到前一个或两个“峰值”的形状(如果需要,您可以进行二次采样)
  • 谢谢@mozway 我用我的 Google Drive 的链接更新了问题,并且有一个包含完整数据的文本文件。
  • 我提供了一个平滑的快速示例,明天我将尝试更新答案并提供更多详细信息

标签: python pandas regression filtering


【解决方案1】:

这是一个关于如何使用rolling+mean 来平滑数据的简单示例:

df = pd.read_csv('across-Z-along-Y-1D-Ecd_x_150.00_nm_iter_17280_time_3_335040_fs_Snapshot.dat',
                 delimiter=' ', names=['x', 'y'])
df['y2'] = df['y'].rolling(window=50, center=True).mean()
ax = df.plot('x', 'y')
df.plot('x', 'y2', ax=ax)

【讨论】:

    【解决方案2】:

    您可以尝试使用高斯滤波器来降低数据的高频平滑曲线。这是一个例子:

    import matplotlib.pyplot as plt;
    from scipy.ndimage import gaussian_filter
    
    x = [0.00, 0.10, 0.20, 0.30, 0.40, 0.50, 0.60, 0.70, 0.80, 0.90, 1.00, 1.10, 1.20, 1.30, 1.40, 1.50, 1.60, 1.70, 1.80, 1.90]
    y = [-5.39, -11.86, -14.46, -12.73, -12.74, -8.17, -3.00, -9.63, -6.86, -2.59, -7.98, -8.31, -6.62, -4.68, -7.23, -4.10, -5.43, -7.89, -7.23, -6.10]
    
    #smothing with a gaussian filter
    y = gaussian_filter(y, sigma=1)
    
    fig, axes = plt.subplots(nrows=1, ncols=1, figsize = (10, 5));
    axes.set(xlabel='x', ylabel='y');
    # line plot ........................................................
    axes.plot(x, y, linewidth = 2, color = 'dodgerblue')
    plt.scatter(x, y, color = 'lime', s = 25);
    
    plt.show()
    

    【讨论】:

      【解决方案3】:

      您可以使用statsmodels 包中的lowess 函数:

      # Python env: pip install statsmodels
      # Anaconda env: conda install statsmodels
      
      import numpy as np
      import matplotlib.pyplot as plt
      from statsmodels.nonparametric.smoothers_lowess import lowess
      
      # Your data
      # x = ...
      # y = ...
      
      # adjust few parameters
      z = lowess(y, x, frac=0.025, it=0, return_sorted=False)
      
      plt.plot(x, y)
      plt.plot(x, z)
      plt.show()
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2016-11-03
        • 1970-01-01
        • 1970-01-01
        • 2019-07-16
        • 1970-01-01
        • 2013-09-06
        • 2017-08-07
        相关资源
        最近更新 更多