plotly

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

Plotly - Interactive Visualization

Plotly - 交互式可视化

Plotly provides a wide range of interactive charts. Its "Plotly Express" API is designed for speed and ease of use with tidy DataFrames, while "Graph Objects" offers low-level control over every trace and attribute.
Plotly提供了种类丰富的交互式图表。其「Plotly Express」API专为整洁的DataFrames设计,兼顾速度与易用性;而「Graph Objects」则提供对每个轨迹和属性的底层控制。

When to Use

适用场景

  • Creating interactive charts for web applications or Jupyter notebooks
  • Visualizing 3D data (surfaces, scatter, mesh)
  • Geographic maps (scatter on maps, choropleths) with Mapbox integration
  • Financial charts (candlestick, OHLC)
  • Exploring large datasets where zooming into specific regions is required
  • Creating animations (time-series sliders)
  • Building production-ready dashboards (via Dash)
  • 为Web应用或Jupyter笔记本创建交互式图表
  • 可视化3D数据(曲面图、散点图、网格图)
  • 集成Mapbox的地理地图(地图散点图、分级统计图)
  • 金融图表(K线图、OHLC图)
  • 探索需要缩放特定区域的大型数据集
  • 创建动画(时间序列滑块)
  • 构建可投入生产的仪表板(通过Dash)

Reference Documentation

参考文档

Official docs: https://plotly.com/python/
Plotly Express: https://plotly.com/python/plotly-express/
Search patterns:
px.scatter
,
go.Figure
,
fig.update_layout
,
fig.write_html
,
px.choropleth
官方文档: https://plotly.com/python/
Plotly Express: https://plotly.com/python/plotly-express/
常用搜索关键词:
px.scatter
,
go.Figure
,
fig.update_layout
,
fig.write_html
,
px.choropleth

Core Principles

核心原则

Plotly Express (px) vs. Graph Objects (go)

Plotly Express (px) 对比 Graph Objects (go)

FeaturePlotly Express (px)Graph Objects (go)
ComplexityHigh-level, concise.Low-level, verbose.
Data FormatTidy (long-form) DataFrames.Lists, Arrays, Dicts, or DataFrames.
CustomizationGood (using update_*).Maximum / Full control.
Speed of DevVery fast.Slower.
特性Plotly Express (px)Graph Objects (go)
复杂度高级、简洁底层、繁琐
数据格式整洁(长格式)DataFrames列表、数组、字典或DataFrames
自定义程度良好(通过update_*方法)完全自定义/最高控制度
开发速度极快较慢

Use Plotly For

适合使用Plotly的场景

  • Interactive exploration (hover, zoom)
  • 3D and Geospatial visualization
  • Exporting to standalone interactive HTML files
  • Integration with Dash
  • 交互式探索(悬停、缩放)
  • 3D与地理空间可视化
  • 导出为独立的交互式HTML文件
  • 与Dash集成

Do NOT Use For

不适合使用Plotly的场景

  • Publication-quality static LaTeX plots (use Matplotlib)
  • Very large static image generation (Matplotlib is faster)
  • Low-memory environments (Plotly's JSON-based figures are memory-heavy)
  • 生成适合出版物的静态LaTeX图表(推荐使用Matplotlib)
  • 生成超大型静态图片(Matplotlib速度更快)
  • 低内存环境(Plotly基于JSON的图形占用内存较高)

Quick Reference

快速参考

Installation

安装

bash
pip install plotly pandas
bash
pip install plotly pandas

Standard Imports

标准导入

python
import plotly.express as px
import plotly.graph_objects as go
import pandas as pd
import numpy as np
python
import plotly.express as px
import plotly.graph_objects as go
import pandas as pd
import numpy as np

Basic Pattern - Plotly Express

基础用法 - Plotly Express

python
import plotly.express as px
python
import plotly.express as px

Load data

加载数据

df = px.data.iris()
df = px.data.iris()

Create interactive scatter plot

创建交互式散点图

fig = px.scatter(df, x="sepal_width", y="sepal_length", color="species", size="petal_length", hover_data=['petal_width'])
fig = px.scatter(df, x="sepal_width", y="sepal_length", color="species", size="petal_length", hover_data=['petal_width'])

Display

显示图表

fig.show()
undefined
fig.show()
undefined

Critical Rules

重要规则

✅ DO

✅ 推荐做法

  • Use Plotly Express first - 90% of tasks are easier with px
  • Prefer Tidy Data - Ensure one row per observation for easy mapping to colors/axes
  • Use update_layout - Cleanly modify titles, fonts, and background colors
  • Save as HTML - Use
    fig.write_html("plot.html")
    to share interactive charts
  • Leverage Hover Data - Add context to points without cluttering the plot
  • Set Figure Templates - Use
    template="plotly_dark"
    or
    "ggplot2"
    for instant style
  • Use marginal_x/y - In px.scatter, quickly add histograms or boxplots to margins
  • 优先使用Plotly Express - 90%的任务用px更简便
  • 优先使用整洁数据 - 确保每行对应一个观测值,便于映射颜色/坐标轴等属性
  • 使用update_layout - 清晰地修改标题、字体和背景颜色
  • 保存为HTML - 使用
    fig.write_html("plot.html")
    分享交互式图表
  • 利用悬停数据 - 为数据点添加上下文信息,避免图表过于杂乱
  • 设置图形模板 - 使用
    template="plotly_dark"
    "ggplot2"
    快速调整样式
  • 使用marginal_x/y - 在px.scatter中快速为边缘添加直方图或箱线图

❌ DON'T

❌ 不推荐做法

  • Pass huge datasets to the browser - Plotting >50k points can lag the UI; use datashader or decimation
  • Manual looping with go - If px can do it, don't use a for-loop to add traces in go
  • Forget to set axis labels - px uses column names; rename them in the DataFrame for better labels
  • Over-animate - Smooth animations are cool, but too many moving parts distract from the data
  • 向浏览器传递超大数据集 - 绘制超过50k个数据点会导致UI卡顿;建议使用datashader或数据降采样
  • 手动循环使用go - 如果px能实现,就不要用for循环在go中添加轨迹
  • 忘记设置坐标轴标签 - px会使用列名;可以在DataFrame中重命名列以获得更清晰的标签
  • 过度动画 - 流畅的动画很实用,但过多的动态元素会分散对数据的注意力

Anti-Patterns (NEVER)

反模式(绝对避免)

python
undefined
python
undefined

❌ BAD: Over-complicating a simple plot with Graph Objects

❌ 错误:用Graph Objects过度简化简单图表

fig = go.Figure() for species in df['species'].unique(): sub = df[df['species'] == species] fig.add_trace(go.Scatter(x=sub['sepal_w'], y=sub['sepal_l'], name=species))
fig = go.Figure() for species in df['species'].unique(): sub = df[df['species'] == species] fig.add_trace(go.Scatter(x=sub['sepal_w'], y=sub['sepal_l'], name=species))

✅ GOOD: Use Plotly Express (One line, automatic legend/colors)

✅ 正确:使用Plotly Express(一行代码,自动生成图例/颜色)

fig = px.scatter(df, x="sepal_width", y="sepal_length", color="species")
fig = px.scatter(df, x="sepal_width", y="sepal_length", color="species")

❌ BAD: Mixing list-style data with DataFrame-style data in px

❌ 错误:在px中混合列表式数据和DataFrame式数据

px.scatter(x=[1,2,3], y=df['column']) # Can lead to alignment issues
px.scatter(x=[1,2,3], y=df['column']) # 可能导致数据对齐问题

✅ GOOD: Stick to the DataFrame

✅ 正确:坚持使用DataFrame

px.scatter(df, x="column_a", y="column_b")
undefined
px.scatter(df, x="column_a", y="column_b")
undefined

Plotly Express (px) Deep Dive

Plotly Express (px) 深入讲解

Statistical Charts

统计图表

python
undefined
python
undefined

Boxplot with points

带数据点的箱线图

fig = px.box(df, x="day", y="total_bill", color="smoker", points="all")
fig = px.box(df, x="day", y="total_bill", color="smoker", points="all")

Violin plot with box inside

内部带箱线的小提琴图

fig = px.violin(df, x="day", y="total_bill", color="sex", box=True, points="all")
fig = px.violin(df, x="day", y="total_bill", color="sex", box=True, points="all")

Heatmap (Density Contour)

热力图(密度等高线)

fig = px.density_heatmap(df, x="total_bill", y="tip", marginal_x="histogram", marginal_y="histogram")
undefined
fig = px.density_heatmap(df, x="total_bill", y="tip", marginal_x="histogram", marginal_y="histogram")
undefined

Time Series and Faceting

时间序列与分面

python
df = px.data.stocks()
python
df = px.data.stocks()

Multiple lines from wide data

从宽数据生成多折线图

fig = px.line(df, x='date', y=["GOOG", "AAPL", "AMZN"], title="Tech Stocks")
fig = px.line(df, x='date', y=["GOOG", "AAPL", "AMZN"], title="科技股走势")

Faceting (Subplots by category)

分面(按类别生成子图)

df = px.data.tips() fig = px.scatter(df, x="total_bill", y="tip", color="smoker", facet_col="day", facet_row="time")
undefined
df = px.data.tips() fig = px.scatter(df, x="total_bill", y="tip", color="smoker", facet_col="day", facet_row="time")
undefined

3D Visualization

3D可视化

Scatter, Lines, and Surfaces

散点图、折线图与曲面图

python
undefined
python
undefined

3D Scatter

3D散点图

fig = px.scatter_3d(df, x='sepal_length', y='sepal_width', z='petal_width', color='species')
fig = px.scatter_3d(df, x='sepal_length', y='sepal_width', z='petal_width', color='species')

3D Surface (Using Graph Objects)

3D曲面图(使用Graph Objects)

z_data = pd.read_csv('https://raw.githubusercontent.com/plotly/datasets/master/api_docs/mt_bruno_elevation.csv') fig = go.Figure(data=[go.Surface(z=z_data.values)]) fig.update_layout(title='Mt Bruno Elevation', autosize=False, width=500, height=500, margin=dict(l=65, r=50, b=65, t=90))
undefined
z_data = pd.read_csv('https://raw.githubusercontent.com/plotly/datasets/master/api_docs/mt_bruno_elevation.csv') fig = go.Figure(data=[go.Surface(z=z_data.values)]) fig.update_layout(title='Mt Bruno海拔图', autosize=False, width=500, height=500, margin=dict(l=65, r=50, b=65, t=90))
undefined

Geospatial Analysis

地理空间分析

Maps and Choropleths

地图与分级统计图

python
undefined
python
undefined

Scatter on a map

地图散点图

df = px.data.gapminder().query("year == 2007") fig = px.scatter_geo(df, locations="iso_alpha", color="continent", hover_name="country", size="pop", projection="natural earth")
df = px.data.gapminder().query("year == 2007") fig = px.scatter_geo(df, locations="iso_alpha", color="continent", hover_name="country", size="pop", projection="natural earth")

Detailed Mapbox Choropleth (Needs token or use open-street-map)

详细的Mapbox分级统计图(需要token或使用open-street-map)

fig = px.choropleth_mapbox(df, geojson=counties, locations='fips', color='unemp', color_continuous_scale="Viridis", mapbox_style="carto-positron", zoom=3, center = {"lat": 37.0902, "lon": -95.7129})
undefined
fig = px.choropleth_mapbox(df, geojson=counties, locations='fips', color='unemp', color_continuous_scale="Viridis", mapbox_style="carto-positron", zoom=3, center = {"lat": 37.0902, "lon": -95.7129})
undefined

Layout and Styling (fig.update_*)

布局与样式(fig.update_*)

Fine-tuning the appearance

精细调整外观

python
fig = px.scatter(df, x="x", y="y")
python
fig = px.scatter(df, x="x", y="y")

Global layout updates

全局布局更新

fig.update_layout( title="Custom Styled Plot", xaxis_title="Dimension X", yaxis_title="Dimension Y", font=dict(family="Courier New, monospace", size=18, color="RebeccaPurple"), legend=dict(yanchor="top", y=0.99, xanchor="left", x=0.01), plot_bgcolor="white" )
fig.update_layout( title="自定义样式图表", xaxis_title="维度X", yaxis_title="维度Y", font=dict(family="Courier New, monospace", size=18, color="RebeccaPurple"), legend=dict(yanchor="top", y=0.99, xanchor="left", x=0.01), plot_bgcolor="white" )

Axis specific updates

坐标轴特定更新

fig.update_xaxes(showgrid=True, gridwidth=1, gridcolor='LightPink') fig.update_yaxes(zeroline=True, zerolinewidth=2, zerolinecolor='Black')
undefined
fig.update_xaxes(showgrid=True, gridwidth=1, gridcolor='LightPink') fig.update_yaxes(zeroline=True, zerolinewidth=2, zerolinecolor='Black')
undefined

Advanced Interaction: Animations

高级交互:动画

python
df = px.data.gapminder()
fig = px.scatter(df, x="gdpPercap", y="lifeExp", animation_frame="year", 
                 animation_group="country",
                 size="pop", color="continent", hover_name="country",
                 log_x=True, size_max=55, range_x=[100, 100000], range_y=[25, 90])
python
df = px.data.gapminder()
fig = px.scatter(df, x="gdpPercap", y="lifeExp", animation_frame="year", 
                 animation_group="country",
                 size="pop", color="continent", hover_name="country",
                 log_x=True, size_max=55, range_x=[100, 100000], range_y=[25, 90])

Practical Workflows

实用工作流

1. Interactive Scientific Report Export

1. 交互式科学报告导出

python
def create_interactive_report(df, filename="report.html"):
    """Generates a multi-chart HTML report."""
    fig1 = px.scatter(df, x="A", y="B", color="C")
    fig2 = px.histogram(df, x="A", color="C")
    
    with open(filename, 'a') as f:
        f.write(fig1.to_html(full_html=False, include_plotlyjs='cdn'))
        f.write(fig2.to_html(full_html=False, include_plotlyjs='cdn'))
python
def create_interactive_report(df, filename="report.html"):
    """生成包含多图表的HTML报告。"""
    fig1 = px.scatter(df, x="A", y="B", color="C")
    fig2 = px.histogram(df, x="A", color="C")
    
    with open(filename, 'a') as f:
        f.write(fig1.to_html(full_html=False, include_plotlyjs='cdn'))
        f.write(fig2.to_html(full_html=False, include_plotlyjs='cdn'))

Useful for sharing findings with non-technical stakeholders

便于与非技术人员分享研究成果

undefined
undefined

2. Financial Dashboard Fragment (Candlestick)

2. 金融仪表板片段(K线图)

python
import pandas as pd
from datetime import datetime

df = pd.read_csv('https://raw.githubusercontent.com/plotly/datasets/master/finance-charts-apple.csv')

fig = go.Figure(data=[go.Candlestick(x=df['Date'],
                open=df['AAPL.Open'],
                high=df['AAPL.High'],
                low=df['AAPL.Low'],
                close=df['AAPL.Close'])])
python
import pandas as pd
from datetime import datetime

df = pd.read_csv('https://raw.githubusercontent.com/plotly/datasets/master/finance-charts-apple.csv')

fig = go.Figure(data=[go.Candlestick(x=df['Date'],
                open=df['AAPL.Open'],
                high=df['AAPL.High'],
                low=df['AAPL.Low'],
                close=df['AAPL.Close'])])

Remove rangeslider for cleaner look

移除范围滑块,让图表更简洁

fig.update_layout(xaxis_rangeslider_visible=False)
undefined
fig.update_layout(xaxis_rangeslider_visible=False)
undefined

3. Mixing Subplots with go.Figure

3. 使用go.Figure混合子图

python
from plotly.subplots import make_subplots

fig = make_subplots(rows=1, cols=2, subplot_titles=("Plot A", "Plot B"))

fig.add_trace(go.Scatter(x=[1, 2, 3], y=[4, 5, 6]), row=1, col=1)
fig.add_trace(go.Bar(x=[1, 2, 3], y=[2, 3, 5]), row=1, col=2)

fig.update_layout(height=600, width=800, title_text="Side-by-Side Comparison")
python
from plotly.subplots import make_subplots

fig = make_subplots(rows=1, cols=2, subplot_titles=("图表A", "图表B"))

fig.add_trace(go.Scatter(x=[1, 2, 3], y=[4, 5, 6]), row=1, col=1)
fig.add_trace(go.Bar(x=[1, 2, 3], y=[2, 3, 5]), row=1, col=2)

fig.update_layout(height=600, width=800, title_text="并列对比")

Performance Optimization

性能优化

WebGL for Large Datasets

针对大数据集的WebGL

python
undefined
python
undefined

For scatter plots with >10,000 points, use Scattergl (Graph Objects)

对于超过10,000个点的散点图,使用Scattergl(Graph Objects)

or tell px to use webgl (available in newer versions)

或者在新版px中指定使用webgl

fig = px.scatter(df, x="large_x", y="large_y", render_mode="webgl")
fig = px.scatter(df, x="large_x", y="large_y", render_mode="webgl")

WebGL drastically improves performance by using the GPU for rendering.

WebGL通过GPU渲染大幅提升性能。

undefined
undefined

Common Pitfalls and Solutions

常见陷阱与解决方案

JSON Overhead in Notebooks

笔记本中的JSON开销

python
undefined
python
undefined

❌ Problem: Notebook file size explodes to 50MB

❌ 问题:笔记本文件大小暴增至50MB

✅ Solution: Display as static image (requires kaleido) or use a different renderer

✅ 解决方案:以静态图片显示(需要kaleido)或使用其他渲染器

fig.show(renderer="png") # Static

fig.show(renderer="png") # 静态显示

OR: Clear output after viewing

或者:查看后清除输出

undefined
undefined

Axis Scaling in Animations

动画中的坐标轴缩放

python
undefined
python
undefined

❌ Problem: Axes jump around during animation

❌ 问题:动画过程中坐标轴跳动

✅ Solution: Manually fix the ranges

✅ 解决方案:手动固定范围

fig = px.scatter(df, x="x", y="y", animation_frame="time", range_x=[0, 100], range_y=[0, 100])
undefined
fig = px.scatter(df, x="x", y="y", animation_frame="time", range_x=[0, 100], range_y=[0, 100])
undefined

Handling Missing Categories in Legend

处理图例中缺失的类别

python
undefined
python
undefined

❌ Problem: Colors change when filtering data because categories disappear

❌ 问题:过滤数据后颜色变化,因为类别消失

✅ Solution: Pass a category_orders dictionary

✅ 解决方案:传入category_orders字典

fig = px.scatter(df, x="x", y="y", color="category", category_orders={"category": ["A", "B", "C", "D"]})
undefined
fig = px.scatter(df, x="x", y="y", color="category", category_orders={"category": ["A", "B", "C", "D"]})
undefined

Best Practices

最佳实践

  1. Use Plotly Express first - Start with
    px
    for 90% of tasks; only use
    go
    when you need fine-grained control
  2. Work with tidy DataFrames - Ensure one row per observation for easy mapping to visual attributes
  3. Use
    update_layout
    for styling
    - Cleanly modify titles, fonts, and background colors without recreating figures
  4. Save as HTML for sharing - Use
    fig.write_html("plot.html")
    to share interactive charts with stakeholders
  5. Leverage hover data - Add context to points without cluttering the plot
  6. Set figure templates - Use
    template="plotly_dark"
    or
    "ggplot2"
    for instant professional styling
  7. Use marginal plots - In
    px.scatter
    , use
    marginal_x
    and
    marginal_y
    to quickly add histograms or boxplots
  8. Optimize for large datasets - Use WebGL rendering or datashader for datasets with >50k points
  9. Fix axis ranges in animations - Use
    range_x
    and
    range_y
    to prevent axes from jumping during animations
  10. Set category orders - Use
    category_orders
    to maintain consistent colors when filtering data
Plotly bridges the gap between static analysis and interactive discovery. It is the best tool for moving scientific insights from a notebook to the web.
  1. 优先使用Plotly Express - 90%的任务从
    px
    开始;仅在需要细粒度控制时使用
    go
  2. 使用整洁的DataFrames - 确保每行对应一个观测值,便于映射到可视化属性
  3. 使用
    update_layout
    进行样式设置
    - 无需重新创建图形,即可清晰修改标题、字体和背景颜色
  4. 保存为HTML用于分享 - 使用
    fig.write_html("plot.html")
    与相关人员分享交互式图表
  5. 利用悬停数据 - 为数据点添加上下文信息,避免图表过于杂乱
  6. 设置图形模板 - 使用
    template="plotly_dark"
    "ggplot2"
    快速获得专业样式
  7. 使用边缘图 - 在
    px.scatter
    中使用
    marginal_x
    marginal_y
    快速添加直方图或箱线图
  8. 针对大数据集优化 - 对超过50k个点的数据集使用WebGL渲染或datashader
  9. 固定动画中的坐标轴范围 - 使用
    range_x
    range_y
    防止动画过程中坐标轴跳动
  10. 设置类别顺序 - 使用
    category_orders
    确保过滤数据时颜色保持一致
Plotly填补了静态分析与交互式探索之间的空白。它是将科学洞察从笔记本迁移到Web的最佳工具。