using CairoMakie
using DataFrames
using Statistics
using Random雨云图(Julia)
雨云图将半小提琴(「云」)、箱线图与抖动散点(「雨」)组合在一张图中,同时呈现完整分布、汇总统计量与单个观测值。在生物医学研究中,它已成为分组连续型数据条形图的首选替代方案——而 CairoMakie 将其作为单个原生 recipe 提供:rainclouds。
示例

环境配置
- 系统要求:跨平台(Linux/MacOS/Windows)
- 编程语言:Julia
- 依赖包:
CairoMakie、DataFrames、Statistics
数据准备
我们模拟三种刺激条件下流式检测的响应强度,每个条件足够的细胞数使半小提琴轮廓具有信息量。
Random.seed!(41)
conditions = ["Unstim", "Anti-CD3", "Anti-CD3/28"]
n_cells = 250
# 缩放指数分布样本模拟正值荧光强度
response = vcat(
2.0 .- 2.0 .* log.(rand(n_cells)),
2.5 .- 2.5 .* log.(rand(n_cells)),
3.5 .- 3.5 .* log.(rand(n_cells)),
)
df = DataFrame(Condition = repeat(conditions, inner = n_cells),
Response = response)750×2 DataFrame
725 rows omitted
| Row | Condition | Response |
|---|---|---|
| String | Float64 | |
| 1 | Unstim | 2.65434 |
| 2 | Unstim | 2.02358 |
| 3 | Unstim | 2.00056 |
| 4 | Unstim | 2.50641 |
| 5 | Unstim | 2.44635 |
| 6 | Unstim | 4.32714 |
| 7 | Unstim | 3.33015 |
| 8 | Unstim | 7.64955 |
| 9 | Unstim | 2.61691 |
| 10 | Unstim | 3.24195 |
| 11 | Unstim | 4.77048 |
| 12 | Unstim | 5.01465 |
| 13 | Unstim | 4.98033 |
| ⋮ | ⋮ | ⋮ |
| 739 | Anti-CD3/28 | 3.96686 |
| 740 | Anti-CD3/28 | 6.06405 |
| 741 | Anti-CD3/28 | 30.7562 |
| 742 | Anti-CD3/28 | 8.76583 |
| 743 | Anti-CD3/28 | 7.73528 |
| 744 | Anti-CD3/28 | 11.1738 |
| 745 | Anti-CD3/28 | 4.25204 |
| 746 | Anti-CD3/28 | 12.2347 |
| 747 | Anti-CD3/28 | 14.2449 |
| 748 | Anti-CD3/28 | 11.484 |
| 749 | Anti-CD3/28 | 9.90509 |
| 750 | Anti-CD3/28 | 23.8423 |
可视化
基础雨云图
一次 rainclouds 调用即可绘制云、箱与雨;side 控制小提琴相对散点的位置。
fig = Figure(size = (540, 360))
ax = Axis(fig[1, 1], xlabel = "Stimulation condition",
ylabel = "Response intensity (a.u.)")
rainclouds!(ax, df.Condition, df.Response; orientation = :vertical,
side = :right, cloud_width = 0.6, gap = 0.15,
jitter_width = 0.12, markersize = 3, color = :slateblue)
ax.xticks = (1:3, conditions)
hidespines!(ax, :t, :r)
fig横向雨云图
类别标签较长时,横向布局(orientation = :horizontal)更易读,云朵悬挂在箱体一侧。
fig = Figure(size = (540, 320))
ax = Axis(fig[1, 1], xlabel = "Response intensity (a.u.)",
ylabel = "Stimulation condition")
rainclouds!(ax, df.Condition, df.Response; orientation = :horizontal,
side = :left, cloud_width = 0.6, gap = 0.15,
jitter_width = 0.12, markersize = 3, color = :salmon)
ax.yticks = (1:3, conditions)
hidespines!(ax, :t, :r)
fig直方图云
设置 clouds = hist(绘图函数对象)将平滑小提琴替换为堆叠的分箱计数,在较小样本量下能保留离散抽样的信息。
fig = Figure(size = (540, 360))
ax = Axis(fig[1, 1], xlabel = "Stimulation condition",
ylabel = "Response intensity (a.u.)")
rainclouds!(ax, df.Condition, df.Response; orientation = :vertical,
side = :right, clouds = hist, hist_bins = 20,
cloud_width = 0.6, gap = 0.15,
jitter_width = 0.12, markersize = 3, color = :seagreen)
ax.xticks = (1:3, conditions)
hidespines!(ax, :t, :r)
fig参考文献
- Allen, M., Poggiali, D., Whitaker, K., et al. (2019). Raincloud plots: a multi-platform tool for robust data visualization. Wellcome Open Research, 4, 63.
- Makie development team. Makie.jl documentation — rainclouds. https://docs.makie.org/stable/reference/plots/rainclouds
- Danisch, S., & Krumbiegel, J. (2021). Makie.jl: Flexible high-performance data visualization for Julia. Journal of Open Source Software, 6(65), 3349.
