まとめワッフルチャートは、10×10 の 100 個のタイルを「1 タイル = 1%」として、A プラン 45%・B プラン 30%・C プラン 18%・解約 7% のような構成比を塗り分けて見せる図です。np.round(share * 100) で割合をタイル数に変え、matplotlib.patches.Rectangle を 2 重ループで左上から順に並べるだけで描けます。四捨五入でタイル数の合計が 100 からずれることがあるので、最後のカテゴリで 100 - 他の合計 と帳尻を合わせる 1 行が欠かせません。円グラフの角度より「45 個のマス」のほうが数えて確かめられるので、割合をざっくり伝える場面で円グラフの代わりになります。
ax オブジェクトと fig.tight_layout の基本は 基本の縦型棒グラフ で確認しておくと、このページでは Rectangle を並べる部分だけに集中できます。
直感
#
契約者の 45% が A プラン、30% が B プラン、18% が C プラン、7% が解約だったとします。円グラフにすると 18% と 7% の角度の差は読みにくいのですが、100 個のマスに塗り分けると「C プランは 18 マス、解約は 7 マス」と数えられます。ワッフルチャートがやっていることは、割合に 100 をかけてタイル数にし、そのタイルを左上から順に色で埋めていくだけです。1 タイル = 1% という単位が固定されているので、どの図でも同じ読み方ができます。
割合 share (0.45, 0.30, …)→
×100 して四捨五入 → タイル数→
最後のカテゴリで合計を 100 に調整→
左上から行ごとに Rectangle を並べる→
凡例に名前と % を添える
Python で描く
#
次のコードは 4 カテゴリの割合を 45・30・18・7 個のタイルに変換し、10×10 のグリッドに左上から敷き詰めます。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
| import numpy as np
import matplotlib.pyplot as plt
from matplotlib.patches import Rectangle
labels = ["A プラン", "B プラン", "C プラン", "解約"]
share = np.array([0.45, 0.30, 0.18, 0.07])
colors = ["#2563eb", "#22c55e", "#fbbf24", "#ef4444"]
grid_size = 10
tiles = np.round(share * grid_size * grid_size).astype(int)
tiles[-1] = grid_size * grid_size - tiles[:-1].sum() # 誤差調整
fig, ax = plt.subplots(figsize=(4.5, 4.5))
ax.set_xticks([])
ax.set_yticks([])
ax.set_aspect("equal")
start = 0
for color, count in zip(colors, tiles):
for n in range(count):
row = (start + n) // grid_size
col = (start + n) % grid_size
ax.add_patch(
Rectangle((col, grid_size - 1 - row), 1, 1, facecolor=color, edgecolor="white")
)
start += count
ax.set_xlim(0, grid_size)
ax.set_ylim(0, grid_size)
ax.set_title("プラン構成比のワッフルチャート")
legend_handles = [Rectangle((0, 0), 1, 1, color=c) for c in colors]
ax.legend(legend_handles, [f"{l} {s*100:.0f}%" for l, s in zip(labels, share)], loc="lower center", ncol=2, frameon=False, bbox_to_anchor=(0.5, -0.12))
fig.tight_layout()
plt.show()
|

実行結果の読み方
#
上から 4 行と半分が青(A プラン 45 個)、続く 3 行が緑(B プラン 30 個)、黄色が 18 個、赤が 7 個で、合計 100 マスがぴったり埋まります。「A プランが半分近く」「解約は 1 行に満たない」という読み方が、角度を比べるより素直にできます。細かい差(18% と 20%)は凡例の数値で確かめます。
何が起きているか(ステップで見る)
#
コードを読む前に、この手法が図の上で何をしているかを追ってみましょう。「再生」を押すか、スライダーを動かすと 1 手順ずつ進みます。
見るポイント:構成比は件数ではなく割合で比べる。積み上げると全体(100%)に占める大きさが面積になる。
使いどころと落とし穴
#
「契約者 100 人のうち 45 人が A プラン」のように、割合を人数の感覚で伝えたいプレゼンやダッシュボードに向いています。凡例にパーセントを併記しておけば正確な値も失われず、edgecolor の白い縁を消すと柔らかい印象、残すと正方形の並びが強調されるので、用途で選びます。一方、12.3% のような小数点以下の精度は 1 タイル = 1% では表せないので、精度が必要なら ドーナツチャート ではなく長さで読める 積み上げ棒グラフ か横棒グラフを使います。
失敗しやすいのはタイル数とカテゴリ数です。50 タイルや 64 タイルにすると 1 タイルが 2% や 1.56% になり、読者は換算を強いられます。カテゴリが 6 色以上になると隣接するタイルの色の区別がつかなくなるので、4〜5 カテゴリに集約し、残りは「その他」にまとめてグレーで塗ります。