【问题标题】:Why is my JSON object changing before I manipulate it? [duplicate]为什么我的 JSON 对象在我操作它之前会发生变化? [复制]
【发布时间】:2014-02-26 19:08:35
【问题描述】:

这是我的代码:

var data = $.parseJSON('[{"Date":"2014-02-19","Count":"963"},{"Date":"2014-02-20","Count":"2638"}]');
console.log(data);
console.log(typeof data[0].Count);
data.forEach(function(d) {
    d.Count = +d.Count;
});
console.log(typeof data[0].Count);

第一个控制台日志将我的计数视为每个对象内的数字。

第二个控制台日志是字符串。

最后的 console.log 是数字。

有人可以向我解释为什么第一个控制台日志将每个 Count 视为一个数字,当我在使用 d.Count = +d.Count 代码行将 Count 操作为数字之前记录数据对象时?

这是其中的代码:http://jsfiddle.net/b73fZ/

【问题讨论】:

  • 谷歌浏览器魔法。尝试先记录它,添加延迟,然后在延迟结束之前在控制台中扩展对象。魔法消失了。 jsfiddle.net/b73fZ 如果你在延迟结束前不展开对象,它会显示一个数字。我不知道它背后的细节,但在我看来,chrome 在需要显示之前不会查看对象的属性。

标签: javascript jquery json parsing typeof


【解决方案1】:

我相信这与控制台输出对象的时间有关。看看这些:

如果您使用的是 Chrome/webkit,您可能会在显示三角形(“twistie”)附近看到一个“小蓝色 i”,其工具提示显示当开发人员第一次展开该 twistie 时数据已填充。我稍微修改了您的 jsFiddle 示例here,您可以看到输出是您所期望的:

var data = $.parseJSON('[{"Date":"2014-02-19","Count":"963"},{"Date":"2014-02-20","Count":"2638"},{"Date":"2014-02-21","Count":"1962"},{"Date":"2014-02-22","Count":"1122"},{"Date":"2014-02-23","Count":"1192"},{"Date":"2014-02-24","Count":"2204"},{"Date":"2014-02-25","Count":"1906"},{"Date":"2014-02-26","Count":"1362"}]');
console.log(data);                  // (twistie) [Object, Object, Object, Object, Object, Object, Object, Object]
$.each(data, function () {
    console.log(this);              // Object {Date: "2014-02-19", Count: "963"}, Object {Date: "2014-02-20", Count: "2638"}, ... 
});
console.log(typeof data[0].Count);  // string
data.forEach(function (d) {
    d.Count = +d.Count;
});
console.log(typeof data[0].Count);  // number

【讨论】:

    【解决方案2】:

    试一试

    var data = $.parseJSON('[{"Date":"2014-02-19","Count":"963"},{"Date":"2014-02-20","Count":"2638"},{"Date":"2014-02-21","Count":"1962"},{"Date":"2014-02-22","Count":"1122"},{"Date":"2014-02-23","Count":"1192"},{"Date":"2014-02-24","Count":"2204"},{"Date":"2014-02-25","Count":"1906"},{"Date":"2014-02-26","Count":"1362"}]');
    data.forEach( function (d) {
        Object.keys(d).forEach (function (e) {
            document.write(e + ' ' + typeof e + ' ');
        })
        document.writeln("<br>");
    });
    document.writeln("<br>"+typeof data[0].Count);
    data.forEach(function(d) {
        d.Count = +d.Count;
    });
    document.writeln("<br>"+typeof data[0].Count);
    
    Date string Count string 
    Date string Count string 
    Date string Count string 
    Date string Count string 
    Date string Count string 
    Date string Count string 
    Date string Count string 
    Date string Count string 
    
    string 
    number 
    

    您会发现这可能是一个 console.log 错误,正如 cmets 所建议的那样。

    【讨论】:

    • 这实际上不是一个错误,而是对console.log 实际作用的常见误解。它在执行时捕获对象的引用,但不一定保存当时的状态副本。因此,您在控制台中实际看到的不一定是调用 console.log 时所持有的对象。
    【解决方案3】:

    当你console.log(data)时,数据对象有所有修改后的值,这意味着已经应用了forEach,所以它将Count显示为Number。

    让我用一个例子来解释

    var data = $.parseJSON('[{"Date":"2014-02-19","Count":"963"},{"Date":"2014-02- 20","Count":"2638"}]');
        console.log(data);                  //The log will show you 20 rather than 963.
        data[0].Count = 20;                 //Modify the object
    

    在示例中,我们首先对数据进行控制台,我们希望 Count 的值为 963,但它的值为 20。

    因此,第一个控制台日志将计数视为数字,因为您在 foreach 中对其进行了修改。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2019-07-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-04-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多