做了这些年数据科学项目,几乎每个项目躲不开一个坎:数据算完了,分析做完了,该给产品、业务或者客户看的时候,到底用什么画图?
团队里每次选型都能吵上半天。有人是Python老手,坚持用Plotly一条路走到黑;有人被老板指定过ECharts,从此只认这家;还有人张口闭口D3.js,说这才是"可视化工程师"的尊严。说实话,这些库我全都在真实项目里用过,各有各的香,也各有各的坑。这篇评测我不会念文档,就按我实际踩过的场景、查过的源码、压测过的数据量来聊,把这几年主流的Web可视化与分析库掰开揉碎讲清楚。
如果你正打算从零搭一个数据大屏,或者想把Python分析结果搬到Web页面里,再或者你就是想在几个候选库里挑一个少走弯路——这篇文章应该能帮你省下一周试错时间。
1. 先说结论:这篇评测到底在比什么
1.1 为什么Web数据可视化在数据科学里变得这么重要
以前做数据分析,一张Matplotlib图走天下,最多用Excel透视表应付一下。但现在不一样了:分析结果不再是给自己看的,而是要放进产品、App、企业后台,或者面向客户交付。数据科学家或者数据分析师写出的图表,往往要变成可交互、可筛选、可下钻的Web组件。
于是出现了一个尴尬的断层:Python生态里最顺手的那套画图方案,到了Web端就不好使。反过来,Web前端工程师熟门熟路的那套图表库,数据科学团队拿来又觉得API绕、数据结构对不上。
这也正是需要一篇横向评测的原因。不同场景下,"好用的可视化库"定义完全不一样。如果你只是做探索性分析,画完图自己看一眼规律,那快速和灵活是第一位的;如果你做的是企业级数据产品,图表要嵌到几千个用户的系统里,那稳定性、性能、技术支持才最重要。
我给这次评测定了个基本框架,后面所有库都按这个框架来打分。
1.2 我给8个库定下的6条硬指标
评测不能光靠"我觉着好用"。我给自己列了6条硬指标,每条下面都有实测过的具体场景:
- 渲染性能:同样一万个点、十万个点,滚动缩放时的帧率能不能扛住。这是数据科学项目最容易被低估的一环。
- API设计:接入一批JSON数据,到画出一个能看的图,需要写多少行代码。API是贴近数据处理习惯,还是贴近DOM操作习惯。
- 交互能力:tooltip、缩放、拖拽、框选、联动筛选这些基本交互,是内置还是得自己手撸。
- 数据接入方式:能不能直接吃DataFrame、CSV、JSON,要不要先做大量数据转换。
- 与Python/R/JS生态的衔接:尤其是和Jupyter Notebook、Flask、Django、React/Vue这些框架相处的融洽程度。
- 长期维护与License:社区活跃度、文档质量、版本迭代速度,以及商用是否要花钱。
这6条指标其实是有权重的。比如你是做内部数据分析工具的,性能权重可以调低一点;你是做面向C端用户的复杂图表产品的,API设计可能比License更重要。评测后面我会给一个按场景的决策表,直接对着自己的项目抄作业就行。
2. 逐库评测:全球主流可视化库实力对比
2.1 ECharts——中文互联网生态绕不开的王者
先聊ECharts,因为它几乎是中国Web可视化的事实标准。我最早接触ECharts是2017年前后,那时候版本才3.x,近两年升级到5.x之后,性能和使用体验都上了一个台阶。
ECharts最大的优势是内置能力极其丰富。折线、柱状、饼图这些不谈,桑基图、关系图、树图、地图、漏斗图、仪表盘,全是声明式配置,一个option对象搞定。尤其在中国做数据大屏,ECharts配一个深色主题,好看程度直接拉满。dataset组件出来以后,数据管理也规范了很多,可以直接维护一份二维表数据,多个图表共享。
性能方面,ECharts在5.0之后引入了useUTC、large模式等优化。实测下来,开启large: true后渲染十万级散点没有明显卡顿;如果是千万级数据,那还是要走WebGL渲染或者后端聚合。这里我有一个习惯:凡是超过两万条的数据点,我都会优先开启canvas渲染而不是svg,然后用sampling做降采样,肉眼几乎看不出差别,性能却能快好几倍。
和Python生态的衔接,国内最常用的是pyecharts,我实测过几个版本,优点是配置项和JS版高度统一,Jupyter里能直接渲染,缺点是包体偏大、文档更新偶尔滞后。如果只是做快速原型,pyecharts非常方便;如果做生产系统,我更推荐后端直接产出JSON配置,前端统一加载ECharts渲染,前后端完全解耦,方便调优。
// ECharts 5 的基本使用,dataset 方式管理数据 const chart = echarts.init(document.getElementById('main')); chart.setOption({ dataset: { source: [ ['Month', 'Sales'], ['Jan', 120], ['Feb', 200], ['Mar', 150], ['Apr', 80] ] }, tooltip: {}, xAxis: { type: 'category' }, yAxis: {}, series: [{ type: 'line', smooth: true }] });ECharts适合什么场景?一句话:一切需要快速、稳定、开箱即用的Web图表,特别是中文环境的后台管理和数据大屏。
2.2 Plotly——从Python搬进浏览器最顺手的那个
Plotly和ECharts完全不同。人家出生就带着统计学基因,最早的定位就是给Python、R用户做交互式图表,后来才有了Dash和Web支持。
Plotly.py是我个人在Notebook里最常用的交互式绘图库。一句fig.show()就能看到可缩放、可悬停的图,这在数据分析探索阶段太爽了。和Pandas的DataFrame兼容性极好,plotly.express两行代码就能出一个很漂亮的散点图矩阵,这对数据科学家来说是巨大的时间节省。
到Web端是另一回事。Plotly的React版本plotly.js功能完整,但包体是真的大,基础版就好几百KB,如果做了按需引入,也能控制在可接受范围。Dash是它的杀手级应用,纯Python就能写数据分析Web应用,不用碰JS,对只会Python的分析师极其友好。
我这里有一个真实的团队协作案例:我们之前给运营部门搭过一个活动效果分析后台,用的是Dash + Plotly,开发周期一周,整个项目几乎没有写前端代码,图表联动、回调刷新全靠Python函数搞定。这种体验是ECharts给不了的。
但Plotly也有明显的短板:深度定制不灵活。如果你想画一个非标的自定义图表,或者做特别复杂的事件交互,回到Plotly的配置体系里就会觉得束手束脚。另外在大数据量下,Plotly的WebGL模式虽然有效,但调优难度比ECharts高,某些版本在十万点以上会出现明显的交互掉帧。
import pandas as pd import plotly.express as px df = pd.read_csv("sales.csv") fig = px.scatter(df, x="date", y="revenue", color="channel", title="渠道营收走势") fig.show()2.3 D3.js——最强灵活性和最高学习成本的极致平衡
D3.js是所有前端可视化工程师的必修课,但我不太建议数据科学团队拿它当主力工具。这话可能会得罪一些人,但我经历过,所以讲点实在的。
D3强到什么程度?它本质上不是图表库,而是一套数据驱动文档的底层工具。你能用D3画出任何你能想象到的东西,从最简单的柱状图到完全自定义的力导向图、地图、3D效果,几乎没有天花板。数据新闻界很多神图都是D3作品。
但D3的代价同样巨大:没有现成的图表组件,一切都要自己搭。坐标轴要自己生成,tooltip要自己写,缩放要自己绑事件,响应式要自己布局。一个ECharts里5分钟做好的折线图,用D3新手可能要折腾半天。
在数据科学团队里,我见过太多D3项目最后烂尾的案例:一开始设计师给了个炫酷的效果图,前端工程师用D3照着做,做着做着发现数据字段全变复杂了,交互一多就崩,最后整个图表重写。所以我的建议是:如果你的团队没有专门的前端可视化工程师,或者项目周期紧张,别碰D3。如果真有特殊图表需求,可以考虑基于D3上层封装的库,比如AntV底层或Observable Plot,这些多少能帮你减轻一些痛苦。
2.4 AntV——企业级数据产品里最省心的全家桶
AntV是蚂蚁集团开源的一套数据可视化方案,这两年在中后台领域势头很猛。你如果用过Ant Design,对AntV的体验会有天然的熟悉感。
AntV和ECharts的定位其实有重叠,但气质完全不同。ECharts的核心是"给一个option就出图",一个图表库打天下;AntV则是一套全家桶:G2做统计图表,G2Plot是基于G2封装的一整套高交互图表库,S2做表格分析,L7做地理空间可视化。你要是做复杂的数据分析产品,AntV的设计语言和高交互能力确实更均匀一些。
我实际开发中的一个感受是:AntV的G2Plot在处理业务交互时比ECharts更细腻。比如tooltip的联动展示、图例筛选、状态标记,G2Plot内置的交互状态管理比ECharts成熟,文档里对"交互"概念讲得很透彻。G2本身则类似于"统计图形语法"的实现,如果你了解ggplot2的图层思维,上手G2会非常顺。
不过AntV的文档质量和版本一致性是个老大难问题。G2、G2Plot、S2、L7几个库之间的安装方式不同,升级还经常带来breaking change。我们项目踩过一次从G2 4.x升5.x的坑,图表整个要重写。所以用AntV的时候,我特别建议锁定版本,不要轻易跟最新版。
2.5 Chart.js——轻量小项目的断舍离
Chart.js在"全球主流"里肯定有一席,尤其在海外的轻量级项目中非常流行。核心优势是轻,压缩后几十KB,语法简单,会用对象配置就能画。
对于简单的几张图表,Chart.js是很舒适的。它内置了动画、响应式和基础的tooltip,用来做快速原型、个人博客、小型看板都够用。
但在数据科学场景里,Chart.js暴露的问题也很明显:图表类型相对有限,复杂的组合图实现起来比较别扭;对大数据量的处理能力不足,连一万个点的散点图滚动起来都烧CPU;地理可视化、关系图这些高级类型基本没有。我自己的经验是,Chart.js适合"这个项目只要一张图表,别整太复杂"的场景,但凡你有数据下钻、多维筛选的需求,就尽早换更重的库。
2.6 Highcharts——商业软件里真正有保障的老江湖
Highcharts在国外企业市场占有率相当高,特点是成熟稳定、文档极好。它的API设计走的是传统JS老牌风格,各类配置堆积但组织得比较清晰,新手很容易照着文档写出图来。
最大的门槛是License。Highcharts对商用收费,个人学习免费,如果你的项目要给甲方交付,这个授权成本必须提前算进预算里。很多国内团队因此敬而远之,但在欧美企业,这笔钱通常不是什么大问题。
从数据科学角度说,Highcharts和Python的衔接比ECharts差一些,社区封装的highcharts库维护也不算勤快。如果你的公司总部在海外、客户都在欧美,Highcharts的稳定性和文档确实能省心;如果你主要是国内数据科学项目,ECharts性价比高得多。
2.7 Bokeh——为Python交互而生但生态稍显迟滞
Bokeh是我早期做Python交互可视化时用过一阵子的库,定位和Plotly很像,也提供Python到Web的桥接。Bokeh的渲染引擎是canvas,交互组件丰富,还能和Bokeh Server做实时数据推送,当年在金融数据分析领域很受欢迎。
但现在不得不承认,Bokeh的热度比Plotly低了不少。一方面API设计偏传统,体验不如plotly.express直接;另一方面社区迭代慢,新特性不如对手多。我现在的建议是:如果你已经在Plotly生态里,没必要为了Bokeh切换。除非你确实需要Bokeh Server那种异步推送能力,否则同质化竞争里选生态更发达的Plotly更稳。
2.8 一张表看懂8个库的核心差异
| 库 | 渲染方式 | 上手难度 | 大数据量 | 交互能力 | 主要License | 最佳场景 |
|---|---|---|---|---|---|---|
| ECharts | Canvas/SVG | 低 | 强 | 很强 | Apache 2.0 | 中文生态、大屏、后台报表 |
| Plotly | SVG/WebGL | 低 | 中 | 强 | MIT | Python探索、Dash快速应用 |
| D3.js | SVG/Canvas/WebGL | 高 | 强(靠手写) | 极强(靠手写) | BSD | 定制化高难度可视化 |
| AntV | Canvas/SVG/WebGL | 中 | 中上 | 很强 | MIT | 企业级中后台数据产品 |
| Chart.js | Canvas | 极低 | 弱 | 中 | MIT | 轻量小项目 |
| Highcharts | SVG | 低 | 中 | 强 | 商用收费 | 欧美企业、文档依赖 |
| Bokeh | Canvas | 中 | 中 | 较强 | BSD | Python实时交互应用 |
3. 数据科学场景实测:从数据框到看板的真实体验
3.1 大数据量渲染性能对比,十万个点到底扛不扛得住
这部分我压测了一个数据科学家最常遇到的场景:十万条记录,横轴是时间,纵轴是数值,用户希望能流畅地缩放、拖拽、查看tooltip。
先说结论:ECharts在开启large模式后表现最好,缩放和拖拽基本保持在30帧以上。Plotly在WebGL模式下能扛住,但第一次渲染有明显卡顿感,交互响应也不如ECharts丝滑。Chart.js在十万点时直接白屏警告,基本放弃。D3.js没问题,但性能优化全靠自己写四叉树和降采样,成本太高。AntV的G2Plot在这个量级也有一战之力,只是配置调整比ECharts复杂。
实际项目中我并不建议直接让浏览器硬扛十万个原始数据点,哪怕性能撑得住。更合理的做法是在后端做一次聚合降维,比如时间维度按分钟聚合、数值维度做分位数采样,把十万点压到两三千个点,前端无论用什么库都能瞬间渲染,而且图表的视觉信息几乎没有损失。这个思路在数据科学里叫"视觉聚合",核心是把数据预处理做在图表之前,而不是指望图表库帮你扛住一切。
3.2 交互联动与探索式分析能力拆解
数据科学的可视化不只是"看图",更重要的是"探索"。分析师拿到一张图,第一反应往往是:这个异常点是什么?这一片聚类里包含哪些样本?能不能把鼠标悬停上去看到详细信息?
这就对交互能力提出了很高要求。ECharts的tooltip和dispatchAction是一套非常成熟的事件系统,通过事件可以实现图表之间联动。比如我点击左边折线图的一个类别,右边柱状图自动高亮对应的分组数据,这种"点击-联动"在ECharts里一个myChart.on('click')事件加一次数据过滤就完成了。
Plotly在探索式分析上有天然优势。因为plotly.py本身就是给Python用户交互用的,hover_data可以直接把DataFrame的多列塞进悬停提示里,对变量之间的关系看得清清楚楚。
G2Plot的交互方式更偏向状态化:它把选中、悬停、刷选都抽象成图表状态,多个图表之间通过状态同步来联动。这个理念对大型数据产品来说更优雅,但学习曲线也更高。
我个人的建议是:如果图表是给分析师自己探索用的,选Plotly;如果图表是给业务方或者客户用的,选ECharts或AntV,交互更可控、更符合产品预期。
3.3 与Python/JS生态的集成,别让数据卡在格式转换上
数据科学团队最常见的组合是"Python做后端分析 + Web做前端呈现"。这时候库选得好不好,很大程度取决于前后端衔接顺不顺。
JSON是这中间的通用语言。Pandas的df.to_json(orient='records')可以直接生成前端绘图要的数据格式,ECharts的dataset.source、G2Plot的data字段都能直接吃掉这个结构。我自己习惯在后端定义一个轻量的返回模板,把图表配置、数据、交互参数统一组装成JSON吐给前端,这样前端代码几乎不关心数据是从哪儿来的。
如果团队里全是Python工程师、不想碰前端,那Plotly Dash是最高效的方案。Dash的回调机制帮你把图表的点击、筛选、更新全部封装成Python函数,写起来像在写Flask接口,但实际产出了一个完整可交互的Web应用。我在这里提醒一句:Dash应用上线后考虑并发和内存问题,因为每个用户会话都可能持有独立的图表状态,部署时的资源规划要做足。
如果想在React/Vue项目里用Python数据,流程通常是:Python后端计算 → 输出JSON → 前端调ECharts/Plotly渲染。这套流程里最不值得踩的坑是数据结构不一致。比如ECharts需要{ value: 10, name: 'A' },而你的后端返回的是{ amount: 10, label: 'A' },看似差不多,前端就得加一层map转换。建议在项目初期就统一好字段命名规范,后端直接按图表库要求的schema输出,能省掉大量胶水代码。
3.4 真实案例复盘:从零搭一个销售数据探索看板
拿我近期帮一家电商客户做的销售看板举例。客户要求:周维度的销售额趋势、渠道占比、Top商品排名,并且每个图都能按地区筛选。
选型时我评估了两套方案。方案A是Dash + Plotly,开发最快,几个回调就搞定联动筛选,适合内部给运营团队用。方案B是ECharts + 自研前端,性能好、视觉统一,适合以后嵌到客户App里。
最后因为需求要对外交付,选了方案B。前端用Vue3,后端FastAPI提供聚合接口,数据从订单表里按天聚合,传给前端约500条记录。ECharts这边配置了三个图表的dataset共享同一份数据source,通过global事件实现筛选联动。整体开发用了三天,后面上线后运行很稳。
这个例子不是想说方案B一定比方案A好,而是提醒你:选型必须结合交付形态。你给内部用,效率优先;给客户用,可维护性和性能优先。没有最好的库,只有最匹配的组合。
4. 选型决策:按需求匹配的可视化库
4.1 轻量小项目该怎么选
如果你的项目只是个人博客、教学演示、临时的内部分析页面,不想引入重库,那Chart.js就是最优解。体积小、零配置、开箱即用。缺点是以后扩不动,但"以后"的事到时候再说。
如果项目规模小但还希望能好看一点,ECharts轻量模式也可以按需引入模块,压缩后体积比Chart.js大不了多少,但图表类型和交互选项多得多,等你要加图的时候不用二次重构。
4.2 主力用Python的数据科学项目怎么选
首选明确推荐Plotly。它的Python接口最友好,探索阶段画图效率极高,然后可以直接用Dash把结果做成Web应用。整个过程不用离开Python环境,对分析师相当友好。
另一个方案是pyecharts,用起来也很顺手,但如果你看重社区、文档、长期维护,Plotly还是更稳。如果你决定用ECharts阵营,也可以让后端产出JSON配置,前端独立加载ECharts渲染,但这要求团队里至少有一个人会前端。
4.3 企业级报表和数据产品怎么选
面向客户、包含复杂权限和定制主题的中后台,AntV和ECharts都值得考虑。
- 如果你用Ant Design全家桶,闭眼选AntV,设计语言一致,组件间衔接最顺畅。
- 如果团队更熟悉ECharts,或者项目已经大量使用ECharts,保持一致性更重要。
- 如果公司做海外业务、客户对License合规要求严格,Highcharts是稳妥选择,前提是预算够。
这里提醒一下:企业级项目别只看功能是否满足今天的需求,更要看团队后续能不能维护。ECharts和AntV都有非常庞大的中文社区,出了问题搜一下就有答案,这对交付型团队是很宝贵的资产。
4.4 想做高度定制化图表项目怎么选
只有一个标准答案:D3.js。但请准备好专职前端可视化工程师和足够的排期。另一种折中思路是用D3的底层能力 + 上层封装库(比如Observable Plot或者AntV G2),既能享受D3的灵活性,又不至于从零写坐标轴。
4.5 一张选型决策表,直接抄作业
| 场景特征 | 推荐方案 | 一句话理由 |
|---|---|---|
| 内部快速分析、Python为主 | Plotly + Dash | 开发效率最高,全程不碰JS |
| 国内大屏、后台报表 | ECharts | 功能全、性能强、生态好 |
| 中后台,已有Ant Design | AntV系列 | 设计统一,交互细腻 |
| 轻量小页面,只要简单图 | Chart.js | 体积小,上手快 |
| 海外交付、License要合规 | Highcharts | 文档成熟,商用需付费 |
| 复杂定制、可视化没有天花板 | D3.js | 灵活性最强,成本也最高 |
5. 藏在细节里的坑:真实项目避坑手册
5.1 性能优化,别把锅甩给图表库
很多人一发现页面卡,第一反应是"这个库性能不行"。但我在项目里遇到过太多次,真正的问题反而是数据没做预处理、DOM结构有问题、或者是坐标轴在动态更新时频繁重绘。
先说坐标轴。时间轴如果用的是字符串格式,图表库每次更新都要重新解析,开销很大。统一改成时间戳毫秒值,性能提升立竿见影。
再说数据。前端绘图之前,一定要做合理的降采样。很多图表库本身带sampling参数,比如ECharts的sampling: 'lttb',它用LTTB算法把上千个数据点压成一百多个点,同时保留峰谷趋势。这个手段用了之后,我能把很多弱设备的渲染帧率从10帧拉到50帧以上。
还有一点是容器尺寸。图表所在的div如果用了百分比高度,而父容器高度又依赖内容撑开,就会产生循环依赖,导致图表在某些浏览器里反复重绘。解决办法是绘图前固定容器高度,或者用ResizeObserver监听尺寸变化后手动调用resize。
5.2 事件与状态的几个隐蔽问题
交互图表最怕的是事件绑了一堆,最后状态乱了。我在ECharts项目里碰到过一个问题:点击图例筛选后,再通过代码setOption更新数据,图例选中状态被重置了,用户一脸懵。
原因在于setOption默认是合并配置,但某些字段的合并策略和你想象的完全不同。解决办法是设置notMerge: true来整体替换,或者在更新前手动读取当前图例状态,再合入新配置。
Plotly里有个类似的坑:你在回调里更新图表数据,如果连续触发多个回调,图表会出现闪烁,因为Dash的回调默认是独立运行的。建议用Pattern-Matching Callbacks或者把多个输出合到一个回调里,减少中间态渲染。
还有Tooltip在移动端的兼容问题:ECharts默认tooltip是跟随手指移动的,如果容器有滚动,tooltip会错位。解决办法是设置confine: true把tooltip限制在容器内,并关闭triggerOn: 'mousemove',改为点击触发。
5.3 打包、主题和国际化最容易拖垮上线
这三个问题看着不起眼,却总在上线前突然给你一刀。
打包体积:ECharts只要按需引入,体积能压到原来的三分之一。我一般只用核心模块:echarts/core+charts里的折线柱状图 +components里的tooltip和legend。如果你用的构建工具支持tree-shaking,这个小习惯能让首屏加载快很多。
主题:客户如果有多套品牌主题,建议把主题配置统一放到一个配置文件里,不要散落在各个图表的option中。ECharts支持注册自定义主题,注册后用init(dom, themeName)直接调用。改一套品牌色,全局图表一起变。
国际化:中英文混排的图表要注意数字格式。比如欧洲客户习惯千分位用点、小数用逗号,中国客户相反。ECharts可以通过formatter统一处理,最好在封装层做,而不是每张图写一遍。Plotly的tickformat也支持这类格式化,提前做规范能避免后期几百张图一个个改。
6. 写在最后的话
做了这么多年可视化项目,我最深的体会是:选型这件事,没有绝对的标准答案,只能结合团队情况和交付场景来判断。
我见过太多团队选库时只看"哪个功能多",最后却在数据接入、交互维护、包体积这些环节上反复踩坑。也有团队觉得D3最牛,结果项目交付时间一拖再拖。反过来看,我知道有团队只用ECharts,照样做出了业内数一数二的复杂数据产品。
所以我最后再分享一个自己一直在用的经验法测:如果这个项目只能让你选一个库,优先选团队技能天花板最低的库。什么意思?就是选一个整个团队都能上手的工具,而不是只有个别高手能驾驭的工具。因为可视化项目真正重要的不是一开始画出多炫的效果,而是接下来三个月、半年里,任何人都能在这个基础上稳定迭代和排坑。
把选型的事情想清楚,后面的开发就顺了。希望这篇评测能让你少走一些我当年走过的弯路。