java&echarts 做的人物关系图

本文介绍了一个使用ECharts实现社交网络关系可视化的示例,通过从数据库获取联系人信息并将其展示为节点链接图,实现了动态加载数据和交互式图表。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


<pre name="code" class="java">import org.springframework.context.annotation.Scope;

import org.springframework.stereotype.Controller;

import org.springframework.ui.ModelMap;

import org.springframework.web.bind.annotation.RequestMapping;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;

import javax.servlet.http.HttpServletRequest;


@Controller
@Scope("prototype")
public class EchartsController {
    String Driver = "com.mysql.jdbc.Driver";
    String URL = "jdbc:mysql://192.168.0.240:3306/ims";
    String Username = "user";
    String Password = "password";

    @RequestMapping("/echarts/show")
    public String showecharts(ModelMap modelMap, HttpServletRequest request)
        throws SQLException, ClassNotFoundException {
        String category = "1";
        String nodes = "";
        String links = "";
        String owner = "";
        String ownername = "";
        Class.forName(Driver);

        Connection conn = DriverManager.getConnection(URL, Username, Password);
        String num = request.getParameter("num");
        String sqlString = "select count(*) from t_phone_book where friendnum='" +
            num + "'";
        ResultSet resultSet = conn.createStatement().executeQuery(sqlString);
        resultSet.next();

        long size = resultSet.getLong(1);

        if (size > 0) {
            resultSet = conn.createStatement()
                            .executeQuery("select * from t_phone_book where num='" +
                    num + "'");

            while (resultSet.next()) {
                ownername = resultSet.getString("name");
                owner = "{category:" + category + ", name: '" + ownername +
                    "',value : 4,draggable: true},";
            }

            resultSet = conn.createStatement()
                            .executeQuery("select * from t_phone_book where friendnum='" +
                    num + "'");

            while (resultSet.next()) {
                String othername = resultSet.getString("name");
                num = resultSet.getString("num");
                nodes += ("{category:" + category + ", name: '" + othername +
                "',value : 5,label:'" + num + "'}\n,");
                links += ("{source : '" + ownername + "', target : '" +
                othername + "', weight : 2}\n,");
            }
        } else {
            if (num == null) {
                resultSet = conn.createStatement()
                                .executeQuery("select * from t_phone_book where num='92323535654111'");

                while (resultSet.next()) {
                    ownername = resultSet.getString("name");
                    owner = "{category:" + category + ", name: '" + ownername +
                        "',value : 4,draggable: true},";
                }

                resultSet = conn.createStatement()
                                .executeQuery("select * from t_phone_book where friendnum='92323535654111'");

                while (resultSet.next()) {
                    String othername = resultSet.getString("name");
                    num = resultSet.getString("num");
                    nodes += ("{category:" + category + ", name: '" +
                    othername + "',value :6,label:'" + num + "'}\n,");
                    links += ("{source : '" + ownername + "', target : '" +
                    othername + "', weight : 6}\n,");
                }
            } else {
                resultSet = conn.createStatement()
                                .executeQuery("select * from t_phone_book where num='" +
                        num + "'");

                while (resultSet.next()) {
                    ownername = resultSet.getString("name");

                    String othername = resultSet.getString("name");
                    owner = "{category:1, name: '" + ownername +
                        "',value : 140},";
                    nodes += ("{category:" + category + ", name: '" +
                    othername + "',value :6,label:'" + num + "'}\n,");
                    links += ("{source : '" + ownername + "', target : '" +
                    othername + "', weight : 6}\n,");
                }

                request.getSession()
                       .setAttribute("config", "minRadius : 50,maxRadius : 100,");
                request.getSession().setAttribute("nodes", nodes);
                request.getSession().setAttribute("links", links);
                request.getSession().setAttribute("owner", owner);

                return "/force.jsp";
            }
        }

        if ((nodes != null) && !nodes.equals("")) {
            request.getSession()
                   .setAttribute("config", "minRadius : 15,maxRadius : 20,");
            nodes = nodes.substring(0, nodes.length() - 1);
            links = links.substring(0, links.length() - 1);
            request.getSession().setAttribute("nodes", nodes);
            request.getSession().setAttribute("links", links);
        }

        request.getSession().setAttribute("owner", owner);

        return "/force.jsp";
    }
}



<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>ECharts · Example</title>
    <link rel="shortcut icon" href="asset/ico/favicon.png">
    <link href="asset/css/bootstrap.css" rel="stylesheet">
    <link href="asset/css/carousel.css" rel="stylesheet">
    <link href="asset/css/echartsHome.css" rel="stylesheet">
    <!-- HTML5 shim and Respond.js IE8 support of HTML5 elements and media queries -->
    <!--[if lt IE 9]>
      <script src="https://oss.maxcdn.com/html5shiv/3.7.2/html5shiv.min.js"></script>
      <script src="https://oss.maxcdn.com/respond/1.4.2/respond.min.js"></script>
    <![endif]-->
    <script src="www/js/echarts.js"></script>
    <script src="asset/js/codemirror.js"></script>
    <script src="asset/js/javascript.js"></script>
    <link href="asset/css/codemirror.css" rel="stylesheet">
    <link href="asset/css/monokai.css" rel="stylesheet">
</head>
<body>

    <!-- Fixed navbar -->
    <div class="container-fluid">
        <div class="row-fluid example">
            <div id="sidebar-code" class="col-md-4" style="display:none;">
                <div class="well sidebar-nav">
                    <div class="nav-header"><a href="#" onclick="autoResize()" class="glyphicon glyphicon-resize-full" id ="icon-resize" ></a>option</div>
                    <textarea id="code" name="code">
				option = {
					title : {
						text: '人物关系:乔布斯',
						x:'right',
						y:'bottom'
					},
					tooltip : {
						trigger: 'item',
						formatter: '{a} : {b}'
					},
						toolbox: {
						show : true,
						feature : {
							restore : {show: true},
							magicType: {show: true, type: ['force', 'chord']},
							saveAsImage : {show: true}
						}
					},
					legend: {
						x: 'left',
						data:['家人','朋友']
					},
					   isShowScrollBar:false,
					
					series : [
						{
							type:'force',
							name : "人物关系",
							ribbonType: false,
							categories : [
								{
									name: '人物'
								},
								{
									name: '家人'
<!--									symbol: 'diamond'    形状  diamond 矩形   默认是圆形 -->   
								},
								{
									name:'朋友'
								}
							],
							itemStyle: {
								normal: {
									label: {
										show: true,
										textStyle: {
											color: '#333'
										}
									},
									nodeStyle : {
										brushType : 'both',
										borderColor : 'rgba(255,215,0,0.4)',
										borderWidth : 1
									}
								},
								emphasis: {
									label: {
										show: false
										// textStyle: null      // 默认使用全局文本样式,详见TEXTSTYLE
									},
									nodeStyle : {
										//r: 30
									},
									linkStyle : {}
								}
							},
							${config}
<%--							minRadius : 20, //圆圈最小半径--%>
<%--							maxRadius : 30,	//最大半径--%>
							gravity: 1,
							scaling: 2,  
							draggable: true,
							linkSymbol: 'arrow',
							steps: 10,
							coolDown: 0.9,
							density : 0.8,
							attractiveness: 0.8,
							//preventOverlap: true,
							nodes:[
								${owner}
								${nodes}
		
						],
							links : [
								${links}
							]
						}
					]
				};
				var ecConfig = require('echarts/config');
				function focus(param) {
				
			    var data = param.data;
			    var links = option.series[0].links;
			    var nodes = option.series[0].nodes;
			    if (
			        data.source !== undefined
			        && data.target !== undefined
			    ) { //点击的是边
			        var sourceNode = nodes[data.source];
			        var targetNode = nodes[data.target];
			        console.log("选中了边 " + sourceNode.name + ' -> ' + targetNode.name + ' (' + data.weight + ')');
			    } else { // 点击的是点
			    	$("#num").val(data.label);
			        console.log("选中了" + data.name + '(' + data.value + ')');
			    }
			    if(data.label!==undefined){
			    window.location.href="http://localhost:8080/Echats/?num="+URLencode(data.label)+"";
			    }
			}
				myChart.on(ecConfig.EVENT.CLICK, focus);
				myChart.on(ecConfig.EVENT.FORCE_LAYOUT_END, function () {
					console.log(myChart.chart.force.getPosition());
				});
				
				
				function URLencode(sStr) 
					{
					    return escape(sStr).replace(/\+/g, '%2B').replace(/\"/g,'%22').replace(/\'/g, '%27').replace(/\//g,'%2F');
					}
									
				</textarea>
                </div><!--/.well -->
            </div><!--/span-->
            <div id="graphic" class="col-md-8" style="width:100%;">
                <div id="main" class="main" style="width:100%;height:600px;"></div>
                <div>
                    <button type="button" class="btn btn-sm btn-success" onclick="refresh(true)">刷 新</button>
                    <span class="text-primary">切换主题</span>
                    <select id="theme-select"></select>
                    <span id='wrong-message' style="color:red"></span>
                </div>
            </div><!--/span-->
        </div><!--/row-->
    </div><!--/.fluid-container-->
    <script src="asset/js/jquery.min.js"></script>
    <script src="asset/js/echartsHome.js"></script>
    <script src="asset/js/bootstrap.min.js"></script>
    <script src="asset/js/echartsExample.js"></script>
</body>
</html>
  



路径一定要找好,否则会没有效果

<think>我们正在处理用户关于使用JSON文件创建关系谱的问题。用户希望了解如何利用JSON文件生成关系谱,涉及数据可视化工具和JSON解析。 根据引用内容,我们有一些关于JSON解析的参考资料(引用[1][2][3][4]),但用户的问题更侧重于如何将JSON数据转化为关系谱。 步骤: 1. 解析JSON文件:我们需要读取JSON文件并解析成程序可以处理的数据结构(如对象、数组等)。 2. 设计关系谱的数据结构:关系谱通常由节点(nodes)和边(edges)组成。我们需要从JSON数据中提取出节点和边的信息。 3. 使用可视化工具:将提取的节点和边数据传递给可视化库(如ECharts、D3.js等)进行绘制。 我们以引用[1]和[2]中的Java解析为例,但用户可能使用多种语言,这里我们以Python为例(因为引用[3]提到Python的JSON解析),因为Python在数据处理和可视化方面有丰富的库。 具体步骤: 步骤1:解析JSON文件 在Python中,我们可以使用内置的json模块来解析JSON文件。 步骤2:构建节点和边 根据JSON数据结构,设计如何提取节点和边。例如,假设我们的JSON数据表示人物之间的关系,那么每个人物是一个节点,人物之间的关系是边。 步骤3:使用可视化库 我们可以使用ECharts(通过pyecharts库)或networkx(结合matplotlib)来绘制关系。 示例: 假设我们有一个JSON文件(relations.json),内容如下: { "people": [ { "id": 1, "name": "Alice", "friends": [2, 3] }, { "id": 2, "name": "Bob", "friends": [1, 3] }, { "id": 3, "name": "Charlie", "friends": [1] } ] } 我们需要将这个JSON文件解析,然后构建节点列表和边列表。 节点列表:每个节点是一个字典,包含节点的id、名称等属性。 边列表:每条边表示两个节点之间的关系,由源节点和目标节点组成。 然后,我们可以使用pyecharts中的Graph来绘制。 代码示例: 首先,安装必要的库(如果未安装): pip install pyecharts 然后,编写代码: """ import json from pyecharts.charts import Graph from pyecharts import options as opts # 读取JSON文件 with open('relations.json', 'r', encoding='utf-8') as f: data = json.load(f) # 构建节点和边 nodes = [] links = [] # 遍历每个人 for person in data['people']: nodes.append({ 'name': person['name'], 'symbolSize': 10 # 节点大小 }) # 遍历每个人的朋友 for friend_id in person['friends']: # 找到朋友的名字(这里假设id和数组索引没有直接对应,所以需要查找) # 注意:实际中可能通过id映射,但这里为了简单,我们假设朋友id就是节点在列表中的索引(减1,因为id从1开始) # 但注意:我们的数据中id和数组顺序一致,所以可以直接用id-1作为索引,但实际中可能需要构建映射关系 # 这里我们构建一个映射:id到节点名称的映射(因为节点名称是唯一的) # 但为了简单,我们在构建节点时记录id,然后在构建边时使用节点名称作为标识 # 修改节点构建,加入id(但pyecharts的Graph节点用name标识,所以边用source和target为name) # 因此,我们这里先不构建映射,而是稍后通过id查找节点名称?但是注意,我们还没有构建所有节点,所以不能立即查找。 # 因此,我们改变策略:先构建一个id到name的映射字典 pass # 由于构建边时需要通过id找到对应的节点名称,所以我们先构建一个id到name的映射 id_to_name = {} for person in data['people']: id_to_name[person['id']] = person['name'] # 重新构建节点(这次我们记录id,但Graph节点主要用name,所以节点只需要name即可,但为了区分,我们也可以将id作为节点的一个属性) nodes = [{'name': id_to_name[person['id']]} for person in data['people']] # 构建边 links = [] for person in data['people']: source_name = id_to_name[person['id']] for friend_id in person['friends']: target_name = id_to_name[friend_id] links.append({ 'source': source_name, 'target': target_name }) # 创建关系 graph = Graph() graph.add( "", nodes, links, repulsion=4000, # 节点之间的斥力 edge_symbol=['circle', 'arrow'], # 边的两端形状 edge_symbol_size=4, label_opts=opts.LabelOpts(is_show=True), # 显示节点标签 linestyle_opts=opts.LineStyleOpts(width=0.5, curve=0.3, opacity=0.7) # 线的样式 ) graph.set_global_opts(title_opts=opts.TitleOpts(title="关系谱")) graph.render("relation_graph.html") # 生成HTML文件 """ 注意:以上代码是一个基本示例。实际中,JSON数据结构可能更复杂,需要根据具体的数据格式调整节点和边的提取方式。 另外,用户可能使用其他工具,如D3.js(JavaScript库)或Gephi(桌面软件)等。这里我们展示了使用Python的pyecharts库的方法。 如果用户的数据量很大,可能需要考虑使用更高效的工具(如Gephi)或进行数据简化。 根据引用[3],JSON是一种轻量级的数据交换格式,在多种语言中都有解析库,因此用户可以根据自己熟悉的语言选择解析方式。 引用[4]展示了一个JSON数据的URL,用户也可以从网络获取JSON数据。 相关问题: 1. 如何解析复杂的嵌套JSON数据来构建关系谱? 2. 除了pyecharts,还有哪些常用的关系谱可视化工具? 3. 如何优化大型关系谱的渲染性能?</think>### 如何使用JSON文件创建关系谱 要利用JSON文件生成关系谱,需通过**数据解析→结构转换→可视化渲染**三步实现。以下是详细步骤和工具推荐: --- #### 一、JSON解析与数据提取(核心步骤) 1. **解析JSON文件** 使用编程语言或工具提取节点(nodes)和关系(edges)数据: - **Python示例**(内置`json`库): ```python import json with open('data.json') as f: data = json.load(f) # 解析为字典/列表 ``` - **Java示例**(参考引用[1][2]): ```java import org.json.*; JSONObject json = new JSONObject(new JSONTokener(new FileReader("data.json"))); JSONArray nodes = json.getJSONArray("nodes"); // 提取节点数组 ``` 2. **构建谱数据结构** 关系谱需两类数据: - **节点列表**:实体对象(如人物、公司) ```json "nodes": [ {"id": "A", "name": "Alice", "type": "person"}, {"id": "B", "name": "Bob", "type": "person"} ] ``` - **边列表**:节点间关系(如合作、隶属) ```json "edges": [ {"source": "A", "target": "B", "relation": "friend"} ] ``` --- #### 二、可视化工具推荐 将解析后的数据导入可视化库生成谱: | 工具 | 语言 | 特点 | 适用场景 | |------|------|------|----------| | **PyVis** | Python | 交互式网络,支持动态效果 | 快速原型开发 | | **ECharts** | JavaScript | 高性能关系,丰富配置项 | Web应用嵌入 | | **Gephi** | 桌面软件 | 复杂网络分析,社区检测 | 学术研究/大型网络 | | **D3.js** | JavaScript | 高度定制化,SVG渲染 | 定制化需求强的项目 | ##### 示例:PyVis生成谱(Python) ```python from pyvis.network import Network import json # 1. 解析JSON with open('relations.json') as f: data = json.load(f) # 2. 创建网络 net = Network(height="800px") for node in data["nodes"]: net.add_node(node["id"], label=node["name"], group=node["type"]) for edge in data["edges"]: net.add_edge(edge["source"], edge["target"], title=edge["relation"]) # 3. 保存为HTML net.show("graph.html") ``` --- #### 三、关键技巧 1. **数据预处理** - 扁平化嵌套JSON(参考引用[3]) - 使用`pandas`清洗数据(Python): ```python import pandas as pd edges_df = pd.json_normalize(data, record_path=['relationships']) ``` 2. **动态数据加载** 若JSON来自API(如引用[4]),用异步请求获取: ```javascript // JavaScript示例(ECharts) fetch('http://api.example.com/graph_data') .then(response => response.json()) .then(data => renderGraph(data)); ``` 3. **增强可视化效果** - 按节点类型着色 - 用边宽度表示关系强度 - 添加点击事件显示详细信息 --- ### 工具链总结 ```mermaid graph LR A[JSON文件] --> B{解析工具} B -->|Python| C[json/pandas] B -->|Java| D[org.json] C & D --> E[数据转换] E --> F{可视化库} F --> G[PyVis/ECharts] F --> H[Gephi/D3.js] G & H --> I[交互式关系谱] ``` > **提示**: > - 简单场景用**PyVis**(5行代码出) > - Web项目选**ECharts**(引用[4]的API数据可直接接入) > - 学术研究用**Gephi**(支持模块化分析) --- ### 相关问题 1. 如何处理非结构化JSON数据来构建关系谱? 2. 有哪些适合超大规模关系谱(>10万节点)的优化方案? 3. 如何通过自然语言处理(NLP)自动从文本生成JSON关系数据? 4. ECharts与D3.js在渲染关系谱时性能有何差异? > 引用参考: > JSON解析方法(引用[1][2])和跨平台特性(引用[3])是数据处理基础,API数据接入(引用[4])可直接用于动态谱场景[^1][^2][^3][^4]。
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值