如何在ASP.NET Razor Pages或WinForms中创建无向图?
问题修复方案
下面直接针对你代码中的错误和逻辑问题给出修正方案,同时补充C#与前端数据交互的可行方式:
1. 核心语法错误(导致图完全无法生成)
邻接矩阵第4行末尾缺失逗号,JavaScript解析失败,这是最直接的问题:
// 错误写法 var matrix = [ [null, 1, 1, null, null], [1, null, 1, 1, null], [1, 1, null, 1, null], [null, 1, 1, null, 1] [null, null, null, 1, null] ]; // 正确写法 var matrix = [ [null, 1, 1, null, null], [1, null, 1, 1, null], [1, 1, null, 1, null], [null, 1, 1, null, 1], // 补充逗号 [null, null, null, 1, null] ];
2. 力导向图逻辑调整
- SVG容器已通过
translate移到中心,center力应设为(0,0),否则节点会偏移到SVG右上角:
.force("center", d3.forceCenter(0, 0))
- 移除重复的力导向图初始化代码,避免逻辑冲突。
3. 样式生效修复
CSS定义的链接样式类是.link,需给链接元素添加该类才能让样式生效:
.append("line") .attr("class", "link") // 添加此行 .attr("stroke-width", function (d) { return Math.sqrt(d.value); });
修正后的完整前端代码
<head> <meta charset="UTF-8"> <title>Spider Diagram</title> <script src="https://d3js.org/d3.v7.min.js"></script> <style> svg { font: 10px sans-serif; } .link { stroke: #999; stroke-opacity: 0.6; } .node circle { fill: #fff; stroke: steelblue; stroke-width: 1.5px; } .node text { font-size: 12px; } </style> </head> <body> <svg width="960" height="600"></svg> <script> var matrix = [ [null, 1, 1, null, null], [1, null, 1, 1, null], [1, 1, null, 1, null], [null, 1, 1, null, 1], [null, null, null, 1, null] ]; var width = 960, height = 600, radius = Math.min(width, height) / 2 - 5; var svg = d3.select("svg") .attr("width", width) .attr("height", height) .append("g") .attr("transform", "translate(" + width / 2 + "," + height / 2 + ")"); var data = { nodes: [], links: [] }; // 创建节点 for (var i = 0; i < matrix.length; i++) { var node = { id: i + 1 }; data.nodes.push(node); } // 创建链接 for (var i = 0; i < matrix.length; i++) { for (var j = i + 1; j < matrix.length; j++) { if (matrix[i][j]) { var link = { source: i + 1, target: j + 1, value: matrix[i][j] }; data.links.push(link); } } } var color = d3.scaleOrdinal(d3.schemeCategory10); var force = d3.forceSimulation(data.nodes) .force("link", d3.forceLink(data.links).id(function (d) { return d.id; })) .force("charge", d3.forceManyBody()) .force("center", d3.forceCenter(0, 0)) .alphaTarget(1) .on("tick", ticked); var link = svg.append("g") .attr("class", "links") .selectAll("line") .data(data.links) .enter() .append("line") .attr("class", "link") .attr("stroke-width", function (d) { return Math.sqrt(d.value); }); var node = svg.append("g") .attr("class", "nodes") .selectAll("g") .data(data.nodes) .enter() .append("g"); var circles = node.append("circle") .attr("r", 5) .attr("fill", function (d) { return color(d.id); }) .call(drag(force)); var labels = node.append("text") .text(function (d) { return d.id; }) .attr("dx", 10) .attr("dy", ".35em"); node.append("title") .text(function (d) { return d.id; }); function ticked() { link .attr("x1", function (d) { return d.source.x; }) .attr("y1", function (d) { return d.source.y; }) .attr("x2", function (d) { return d.target.x; }) .attr("y2", function (d) { return d.target.y; }); node .attr("transform", function (d) { return "translate(" + d.x + "," + d.y + ")"; }); } function drag(simulation) { function dragstarted(event, d) { if (!event.active) simulation.alphaTarget(0.3).restart(); d.fx = d.x; d.fy = d.y; } function dragged(event, d) { d.fx = event.x; d.fy = event.y; } function dragended(event, d) { if (!event.active) simulation.alphaTarget(0); d.fx = null; d.fy = null; } return d3.drag() .on("start", dragstarted) .on("drag", dragged) .on("end", dragended); } </script> </body>
C#后端数据传递建议
如果需要从C#后端传递邻接矩阵到前端,可通过视图模型序列化JSON实现:
// ASP.NET Core 后端代码 public IActionResult Index() { var matrix = new int?[][] { new int?[] { null, 1, 1, null, null }, new int?[] { 1, null, 1, 1, null }, new int?[] { 1, 1, null, 1, null }, new int?[] { null, 1, 1, null, 1 }, new int?[] { null, null, null, 1, null } }; ViewData["Matrix"] = System.Text.Json.JsonSerializer.Serialize(matrix); return View(); }
前端视图中读取数据:
var matrix = @Html.Raw(ViewData["Matrix"]);
内容的提问来源于stack exchange,提问作者Finsser
相关产品推荐
相关产品推荐

