嗨,我在d3中使用了一个大的json文件,大约75 KB。它似乎适用于32个数据对象,但随后在控制台中出现错误。无法读取未定义的属性“ length”。自从我将其放入http://jsonlint.com/并通过验证以来,我的json似乎还可以。我知道这里曾问过类似的问题,但我是d3的新手,所以不知道如何修改代码。我认为这可能与d3如何从json文件中获取数据有关。
这是完整的d3代码:

function truncate(str, maxLength, suffix) {
if(str.length > maxLength) {
    str = str.substring(0, maxLength + 1);
    str = str.substring(0, Math.min(str.length, str.lastIndexOf(" ")));
    str = str + suffix;
}
return str;
}

var margin = {top: 20, right: 200, bottom: 0, left: 20},
    width = 300,
    height = 650;

var start_year = 2004,
    end_year = 2013;

var c = d3.scale.category20c();

var x = d3.scale.linear()
    .range([0, width]);

var xAxis = d3.svg.axis()
    .scale(x)
    .orient("top");

var formatYears = d3.format("0000");
xAxis.tickFormat(formatYears);

var svg = d3.select("body").append("svg")
    .attr("width", width + margin.left + margin.right)
    .attr("height", height + margin.top + margin.bottom)
    .style("margin-left", margin.left + "px")
    .append("g")
    .attr("transform", "translate(" + margin.left + "," + margin.top + ")");

d3.json("data.json", function(error, data) {
        if (error) throw error;

x.domain([start_year, end_year]);
var xScale = d3.scale.linear()
    .domain([start_year, end_year])
    .range([0, width]);

svg.append("g")
    .attr("class", "x axis")
    .attr("transform", "translate(0," + 0 + ")")
    .call(xAxis);

console.log(data.length);
var len = data.length;
for (var j = 0; j < len; j++) {
    // try{
    var g = svg.append("g").attr("class","journal");

    var circles = g.selectAll("circle")
        .data(data[j]['articles'])
        .enter()
        .append("circle");

    var text = g.selectAll("text")
        .data(data[j]['articles'])
        .enter()
        .append("text");

    var rScale = d3.scale.linear()
        .domain([0, d3.max(data[j]['articles'], function(d) { return d[1]; })])
        .range([2, 9]);

    circles
        .attr("cx", function(d, i) { return xScale(d[0]); })
        .attr("cy", j*20+20)
        .attr("r", function(d) { return rScale(d[1]); })
        .style("fill", function(d) { return c(j); });

    text
        .attr("y", j*20+25)
        .attr("x",function(d, i) { return xScale(d[0])-5; })
        .attr("class","value")
        .text(function(d){ return d[1]; })
        .style("fill", function(d) { return c(j); })
        .style("display","none");

    g.append("text")
        .attr("y", j*20+25)
        .attr("x",width+20)
        .attr("class","label")
        .text(truncate(data[j]['name'],30,"..."))
        .style("fill", function(d) { return c(j); })
        .on("mouseover", mouseover)
        .on("mouseout", mouseout);
    // }
    // catch(err){
    //  console.log(err);
    //  continue;
    // }
};

function mouseover(p) {
    var g = d3.select(this).node().parentNode;
    d3.select(g).selectAll("circle").style("display","none");
    d3.select(g).selectAll("text.value").style("display","block");
}

function mouseout(p) {
    var g = d3.select(this).node().parentNode;
    d3.select(g).selectAll("circle").style("display","block");
    d3.select(g).selectAll("text.value").style("display","none");
}


});



样本json:

[{"articles":[[2004,25],[2005,25],[2006,26],[2007,31],[2008,20],[2009,26],[2010,19],[2011,18],[2012,24],[2013,17]],"total": 231,"name": " Acta Inf. " },
{"articles":[[2008,1]],"total": 1,"name": " nf. " },
{"articles":[[2005,27],[2006,30],[2007,27],[2008,75],[2009,31],[2010,34],[2011,46],[2012,35],[2013,60]],"total": 365,"name": " Displays " },
{"articles":[[2010,20],[2011,16],[2012,16]],"total": 52,"name": " IJKDB " },
{"articles":[[2004,61],[2005,70],[2006,72],[2007,71],[2008,79],[2009,65],[2010,80],[2011,77],[2012,82],[2013,121]],"total": 778,"name": " Computers in Industry " },
{"articles":[[2010,1]],"total": 1,"name": " rs in Industry " },
{"articles":[[2005,1]],"total": 1,"name": " ry " }, ...


编辑:不再在控制台中收到错误,我的JSON出了点问题。但是,仍然没有在可视化中显示所有条目,这是我的整个JSON文件https://api.myjson.com/bins/425wh

编辑2:现在全部显示!所有数据都存在,但是因为d3画布的高度太小而没有显示

最佳答案

问题出在最后一个条目中。最后一个条目是一个正确的数组,应该是一个对象,因此您的数据集的最后一条记录中的数组内有数组。您将需要展平数据集数组。

从AJAX提取数据后添加。

data = [].concat.apply([], data);//this will flatten all your array within array into a single array of records,


编辑

第二个问题:


  我只看到实际显示的几个?例如,不会出现名为“教育中的人工智能”的期刊。


问题在于svg高度较小,要显示的数据较多,因此在30条记录后将被切断。

因此,具有这样的动态高度:

d3.select("body svg").attr("height",len*20.2);//20.2 is approx height of one element


现在高度将取决于需要显示的数据长度。

我已经相应地更新了小提琴

工作代码here

09-10 00:55
查看更多