您现在的位置是:网站首页 > 时间序列数据处理文章详情

时间序列数据处理

时间序列数据的特点

时间序列数据是按时间顺序排列的数据点集合,通常具有以下特点:

  1. 时间依赖性:当前值与历史值相关
  2. 趋势性:长期上升或下降的走势
  3. 季节性:固定周期内的重复模式
  4. 噪声:随机波动
// 示例时间序列数据
const timeSeriesData = [
  ['2023-01-01', 156],
  ['2023-01-02', 178],
  ['2023-01-03', 192],
  // ...更多数据
];

ECharts 中的时间序列处理

ECharts 提供了专门的时间轴(xAxis.type = 'time')来处理时间序列数据。相比普通类别轴,时间轴能自动处理:

  1. 时间间隔不均匀的情况
  2. 时间格式化显示
  3. 动态缩放和平移
  4. 跨天/月/年的自动刻度计算
option = {
  xAxis: {
    type: 'time',
    axisLabel: {
      formatter: '{yyyy}-{MM}-{dd}'
    }
  },
  yAxis: {
    type: 'value'
  },
  series: [{
    data: timeSeriesData,
    type: 'line'
  }]
};

数据预处理技巧

时间格式转换

ECharts 支持多种时间格式,但推荐使用时间戳或ISO格式:

// 将日期字符串转换为时间戳
function processData(rawData) {
  return rawData.map(item => {
    return [new Date(item[0]).getTime(), item[1]];
  });
}

// 或者使用ISO格式
const isoData = [
  ['2023-01-01T00:00:00', 156],
  ['2023-01-02T00:00:00', 178]
];

缺失值处理

常见处理方法:

  1. 线性插值
  2. 前值填充
  3. 置零处理
function fillMissingData(data, interval = 86400000 /* 1天 */) {
  const result = [];
  for (let i = 1; i < data.length; i++) {
    const prevTime = new Date(data[i-1][0]).getTime();
    const currTime = new Date(data[i][0]).getTime();
    const gap = currTime - prevTime;
    
    if (gap > interval) {
      const missingCount = Math.round(gap / interval) - 1;
      for (let j = 1; j <= missingCount; j++) {
        const interpolatedTime = prevTime + j * interval;
        const interpolatedValue = data[i-1][1] + 
          (data[i][1] - data[i-1][1]) * j / (missingCount + 1);
        result.push([new Date(interpolatedTime), interpolatedValue]);
      }
    }
    result.push(data[i]);
  }
  return result;
}

高级时间轴配置

多时间段对比

option = {
  xAxis: [{
    type: 'time',
    gridIndex: 0
  }, {
    type: 'time',
    gridIndex: 1
  }],
  yAxis: [{
    gridIndex: 0
  }, {
    gridIndex: 1
  }],
  grid: [{
    bottom: '55%'
  }, {
    top: '55%'
  }],
  series: [{
    data: data2022,
    xAxisIndex: 0,
    yAxisIndex: 0
  }, {
    data: data2023,
    xAxisIndex: 1,
    yAxisIndex: 1
  }]
};

动态数据更新

let currentDate = new Date('2023-01-01');
const realTimeData = [];

function updateChart() {
  currentDate.setDate(currentDate.getDate() + 1);
  const newValue = Math.random() * 200;
  realTimeData.push([currentDate.toISOString(), newValue]);
  
  if (realTimeData.length > 30) {
    realTimeData.shift();
  }
  
  myChart.setOption({
    series: [{
      data: realTimeData
    }]
  });
}

setInterval(updateChart, 1000);

性能优化策略

大数据量处理

  1. 使用采样降频
  2. 启用渐进渲染
  3. 使用WebWorker预处理
option = {
  series: [{
    type: 'line',
    progressive: 1000,
    progressiveThreshold: 5000,
    data: largeTimeSeriesData
  }]
};

视觉优化技巧

option = {
  dataZoom: [{
    type: 'inside',
    xAxisIndex: 0,
    filterMode: 'filter'
  }, {
    type: 'slider',
    xAxisIndex: 0,
    filterMode: 'filter'
  }],
  visualMap: {
    type: 'piecewise',
    dimension: 1,
    pieces: [{
      gt: 200,
      color: '#c23531'
    }, {
      gt: 150,
      lte: 200,
      color: '#2f4554'
    }]
  }
};

实际应用案例

股票K线图实现

option = {
  xAxis: {
    type: 'time',
    axisPointer: {
      snap: true
    }
  },
  yAxis: {
    scale: true
  },
  series: [{
    type: 'candlestick',
    data: klineData.map(item => [
      item[0], // 时间
      item[1], // 开盘价
      item[2], // 收盘价
      item[3], // 最低价
      item[4]  // 最高价
    ]),
    itemStyle: {
      color: '#ec0000',
      color0: '#00da3c',
      borderColor: '#8A0000',
      borderColor0: '#008F28'
    }
  }]
};

多周期天气数据

option = {
  xAxis: {
    type: 'time',
    axisLabel: {
      formatter: function(value) {
        const date = new Date(value);
        return `${date.getHours()}时`;
      }
    }
  },
  series: [{
    data: hourlyTempData,
    type: 'line',
    smooth: true,
    markArea: {
      data: [[{
        xAxis: '07:00',
        itemStyle: { color: 'rgba(255, 173, 177, 0.4)' }
      }, {
        xAxis: '19:00'
      }]]
    }
  }]
};

交互增强功能

时间范围选择器

option = {
  toolbox: {
    feature: {
      dataZoom: {
        yAxisIndex: 'none'
      },
      restore: {},
      saveAsImage: {}
    }
  },
  dataZoom: [{
    type: 'slider',
    xAxisIndex: 0,
    filterMode: 'filter',
    height: 20,
    bottom: 10
  }]
};

时间点标记

option = {
  series: [{
    type: 'line',
    markPoint: {
      data: [{
        type: 'max',
        name: '最大值'
      }, {
        type: 'min',
        name: '最小值'
      }, {
        coord: ['2023-06-15', 189],
        name: '特殊事件'
      }]
    }
  }]
};

我的名片

网名:~川~

岗位:console.log 调试员

坐标:重庆市-九龙坡区

邮箱:cc@qdcc.cn

沙漏人生

站点信息

  • 建站时间:2013/03/16
  • 本站运行
  • 文章数量
  • 总访问量
微信公众号
每次关注
都是向财富自由迈进的一步