> 文档中心 > Java均值滤波思想降折线噪点

Java均值滤波思想降折线噪点


项目场景:

项目需求:PLC共采集8000个点,监测8000个点位内的产品厚度波动。

问题描述

8000个点采集下来,检测点和预想值出现了偏差,出现这些点会使整个产品被系统判定为次品,从而报废。以下为次品图:

在这里插入图片描述
其实这个产品是没有问题的,所以要做滤波处理,将这些点为的值处理为正常值。

方案:

看了很多滤波方式,大多都是处理图像,想要改造费时费力,最终决定使用简单点儿的均值滤波。

代码:

/     * @param dataList 目标点     * @param tag 窗口大小 tag越大折线越平滑     * @return 返回处理后新的点位数组     */private static List Meanss(List dataList, int tag) {//定义返回新的点位数组 List newPoints = new ArrayList();  try {     if (dataList.size() < tag || dataList.isEmpty())  throw new Exception("目标数组内容异常");     if (tag % 2 != 0)  throw new Exception("目标参数异常"); } catch (Exception e) {     e.printStackTrace(); } //判断是否偶数 if (tag % 2 == 0) {     //从tag / 2 开始赋值     int before = tag / 2;     //到tag / 2 结束赋值     int length = dataList.size() - (tag / 2);     //将tag / 2 之前的值不做运算,存入新数组     for (int j = 0; j < before; j++) {  newPoints.add(dataList.get(j));     }     //前后(tag/2)位参与计算不赋值     for (int i = before; i < length; i++) {  //获取需要求平均值的子数组  List tags = dataList.subList(i - before, i + before);  //使用reduce计算BigDecimal平均值  BigDecimal avgNum = tags.stream().reduce(BigDecimal.ZERO, BigDecimal::add).divide(BigDecimal.valueOf(tag), 1);  newPoints.add(avgNum);     }     //后 tag/2 个点位不计算,原值加入     for (int k = length; k < dataList.size(); k++) {  newPoints.add(dataList.get(k));     } } return newPoints;    }

过滤后结果

过滤前:

在这里插入图片描述

过滤后:
在这里插入图片描述
完美解决