Jquery - 计算JSON对象

时间:2016-02-01 01:06:44

标签: javascript jquery json

我正在构建一个图表系统,它将显示所有数据条目。我使用ajax检索我的数据,然后循环数据并按颜色(红色,蓝色和黄色)对结果进行分组,然后将它们除以月份。

我设置了基础对象(dateCounts_Red,dateCounts_Blue和dateCounts_Yellow),因此默认情况下它会在0处开始所有月份。然后,当计数器找到匹配的颜色和月份时,它会添加。

当我输出我的dateCounts时,我得到:

{"2015":{"2015-12":1,"2015-10":null,"2015-08":null,"2015-11":null}}
{"2015":{"2015-12":0,"2015-10":null}}
{"2015":{"2015-12":0,"2015-10":null}}

这是我到目前为止的代码:

var dateCounts_Red = {"2015":{"2015-01":0,"2015-02":0,"2015-03":0,"2015-04":0},"2015":{"2015-05":0},"2015":{"2015-06":0},"2015":{"2015-07":0},"2015":{"2015-08":0},"2015":{"2015-09":0},"2015":{"2015-10":0},"2015":{"2015-11":0},"2015":{"2015-12":0}};
var dateCounts_Blue = {"2015":{"2015-01":0,"2015-02":0,"2015-03":0,"2015-04":0},"2015":{"2015-05":0},"2015":{"2015-06":0},"2015":{"2015-07":0},"2015":{"2015-08":0},"2015":{"2015-09":0},"2015":{"2015-10":0},"2015":{"2015-11":0},"2015":{"2015-12":0}};
var dateCounts_Yellow = {"2015":{"2015-01":0,"2015-02":0,"2015-03":0,"2015-04":0},"2015":{"2015-05":0},"2015":{"2015-06":0},"2015":{"2015-07":0},"2015":{"2015-08":0},"2015":{"2015-09":0},"2015":{"2015-10":0},"2015":{"2015-11":0},"2015":{"2015-12":0}};

data.d.results.forEach(function(element) {
  var date = element.created_date.slice(0, 7);
  var yr = date.slice(0, 4);
  var Color = element.colorvalue;

  if(Color == "red") {
  dateCounts_Red[yr][date]++;
  }

  if(Color == "blue"){
  dateCounts_Blue[yr][date]++;
  }

  if(Color == "yellow"){
  dateCounts_Yellow[yr][date]++;
  }

});

Red_yr_2015_data = [dateCounts_Red['2015']['2015-01'], dateCounts_Red['2015']['2015-02'], dateCounts_Red['2015']['2015-03'], dateCounts_Red['2015']['2015-04'], dateCounts_Red['2015']['2015-05'], dateCounts_Red['2015']['2015-06'], dateCounts_Red['2015']['2015-07'], dateCounts_Red['2015']['2015-08'], dateCounts_Red['2015']['2015-09'], dateCounts_Red['2015']['2015-10'], dateCounts_Red['2015']['2015-11'], dateCounts_Red['2015']['2015-12']];
Blue_yr_2015_data = [dateCounts_Blue['2015']['2015-01'], dateCounts_Blue['2015']['2015-02'], dateCounts_Blue['2015']['2015-03'], dateCounts_Blue['2015']['2015-04'], dateCounts_Blue['2015']['2015-05'], dateCounts_Blue['2015']['2015-06'], dateCounts_Blue['2015']['2015-07'], dateCounts_Blue['2015']['2015-08'], dateCounts_Blue['2015']['2015-09'], dateCounts_Blue['2015']['2015-10'], dateCounts_Blue['2015']['2015-11'], dateCounts_Blue['2015']['2015-12']];
Yellow_yr_2015_data = [dateCounts_Yellow['2015']['2015-01'], dateCounts_Yellow['2015']['2015-02'], dateCounts_Yellow['2015']['2015-03'], dateCounts_Yellow['2015']['2015-04'], dateCounts_Yellow['2015']['2015-05'], dateCounts_Yellow['2015']['2015-06'], dateCounts_Yellow['2015']['2015-07'], dateCounts_Yellow['2015']['2015-08'], dateCounts_Yellow['2015']['2015-09'], dateCounts_Yellow['2015']['2015-10'], dateCounts_Yellow['2015']['2015-11'], dateCounts_Yellow['2015']['2015-12']];

我目前从我的Highcharts js中收到以下错误:

Uncaught TypeError: Cannot set property 'index' of undefined

这会阻止图表系统正常工作,返回的数据不会随其预期数据一起返回。

这是问题https://jsfiddle.net/awo5aaqb/21/

的完整示例

有人知道我失踪了吗?

3 个答案:

答案 0 :(得分:3)

您的日期计数对象存在重大结构缺陷。

当你美化它们时,它们看起来像:

var dateCounts_Blue = {
      "2015": {
        "2015-01": 0,
        "2015-02": 0,
        "2015-03": 0,
        "2015-04": 0
      },
      "2015": {
        "2015-05": 0
      },
      "2015": {
        "2015-06": 0
      },
      "2015": {
        "2015-07": 0
      },
       ......

对象键必须是唯一的,因此这些键明显重复,编译器将重复写入重复项。

修复从开头的预期模式分组中脱离的模式

答案 1 :(得分:1)

var dateCounts_Red = {
"2015":
{
"2015-01":0,
"2015-02":0,
"2015-03":0,
"2015-04":0,
"2015-05":0,
"2015-06":0,
"2015-07":0,
"2015-08":0,
"2015-09":0,
"2015-10":0,
"2015-11":0,
"2015-12":0
},
};
var dateCounts_Blue = {
"2015":{
"2015-01":0,
"2015-02":0,
"2015-03":0,
"2015-04":0,
"2015-05":0,
"2015-06":0,
"2015-07":0,
"2015-08":0,
"2015-09":0,
"2015-10":0, 
"2015-11":0,
"2015-12":0
}
};
var dateCounts_Yellow = {
"2015":{
"2015-01":0,
"2015-02":0,
"2015-03":0,
"2015-04":0,
"2015-05":0,
"2015-06":0,
"2015-07":0,
"2015-08":0,
"2015-09":0,
"2015-10":0,
"2015-11":0,
"2015-12":0}
};

您的数据结构存在缺陷,并且在执行foreach循环时比较值变得不一致,因为它将它与多个值进行比较,上面的JSON是您问题的修复。

答案 2 :(得分:1)

不完全是codereview.stackexchange.com,但我大量修改了你的javascript以使其更好用

$.ajax({
  url: basePath,
  dataType: 'json',
  cache: false,
  success: function(data) {

    var counts = {};

    data.d.results.forEach(function(element) {
      // If you know it's all the same year, you could totally ignore this
      var yr = element.created_date.slice(0, 4);
      var month = parseInt(element.created_date.slice(5,7));
      var color = element.colorvalue;

      if (counts[color] === undefined) {
        counts[color] = {};
      }
      if (counts[color][yr] === undefined) {
        counts[color][yr] = {};
      }

      current_value = counts[color][yr][month];
      if (current_value === undefined) {
        // Doesnt exist yet, so add it
        counts[color][yr][month] = 1;
      } else {
        // Exists, so increment by 1
        counts[color][yr][month] = current_value + 1;
      }
    });

    console.log(JSON.stringify(counts));
    console.log(transform_series(counts['red']['2015']));
    console.log(transform_series(counts['blue']['2015']));
    console.log(transform_series(counts['yellow']['2015']));

    var Options = {

      chart: {
        renderTo: 'myfirstchart',
        type: 'column',
        margin: 75,
        options3d: {
          enabled: true,
          alpha: 25,
          beta: 0,
          depth: 70
        }
      },
      title: {
        text: "Test Highcharts"
      },
      subtitle: {
        text: 'Test charts'
      },
      plotOptions: {
        column: {
          depth: 25
        }
      },
      xAxis: {
        categories: ["Janvier", "Février", "Mars", "Avril", "Mai", "Juin", "Juillet", "Août", "Septembre", "Octobre", "Novembre", "Décembre"]
      },
      yAxis: {
        title: {
          text: "Number of entries"
        }
      },
      tooltip: {
        headerFormat: '<b>{point.key}</b><br>',
        pointFormat: '<span style="color:{series.color}">\u25CF</span> {series.name}: {point.y} / {point.stackTotal}'
      },

      plotOptions: {
        column: {
          stacking: 'normal',
          depth: 40
        }
      },
      series: [{
        name: 'Red',
        color: 'red',
        data: transform_series(counts['red']['2015']),
        stack: '2015'
      }, {
        name: 'Blue',
        color: 'blue',
        data: transform_series(counts['blue']['2015']),
        stack: '2015'
      }, {
        name: 'Yellow',
        color: 'yellow',
        data: transform_series(counts['yellow']['2015']),
        stack: '2015'
      }]

    };

    return new Highcharts.Chart(Options);

  }
});


// this transforms the hash {10: 5, 11:1, 12:1} to get you all 12 months
// and returns an array of values [ 0, 0, 0, 0, 0 ... 5, 1, 1] that
// can be used in high charts
function transform_series(series) {
        return Array.apply(null, Array(13)).map(function (_, i) {return (series[i] === undefined) ? 0 : series[i];}).slice(1,13);
}