Charts from DataFrames
pandas can draw a DataFrame or Series directly with .plot, using matplotlib underneath: one call turns a pivot table into grouped bars. Pass ax= to choose where it draws.
- Draw a Series or DataFrame with
.plot(kind=...)or.plot.bar()and.plot.barh(), onto a chosenax - Explain how a DataFrame's index and columns become the x-axis and the legend
- Lay out several charts with
plt.subplots(nrows, ncols)and draw one on each Axes
After a groupby or pivot_table the numbers are already in a DataFrame or Series, labelled. .plot draws them with matplotlib in one call: the index becomes the x-axis, and each column becomes one series (one colour of bar, one line), named in a legend. kind= picks the chart ("bar", "barh", "line", "hist", "scatter"), or use the method form .plot.bar(). It returns the Axes it drew on; pass ax= to draw on one you made.
You may meet seaborn, a separate library built on matplotlib for statistical charts. It isn't installed in this course's browser Python, so the course draws the same kinds of chart with pandas and matplotlib.
Run each example to see what it prints. Running examples doesn't count toward progress.
import matplotlib.pyplot as plt import pandas as pd orders = pd.DataFrame({ "ship_state": ["TX", "CA", "NY", "TX", "NY", "TX"], "channel": ["web", "web", "web", "web", "phone", "app"], "total": [35.84, 91.47, 55.72, 246.6, 54.55, 39.15], }) table = orders.pivot_table(index="ship_state", columns="channel", values="total", aggfunc="sum", fill_value=0) fig, ax = plt.subplots() drawn = table.plot(kind="bar", ax=ax, title="Revenue by state and channel") print(drawn is ax, len(ax.patches)) print([t.get_text() for t in ax.get_legend().get_texts()]) print([t.get_text() for t in ax.get_xticklabels()], ax.get_xlabel()) plt.show()
import pandas as pd films = pd.DataFrame({"budget_musd": [41.1, 43.1, 9.8], "revenue_musd": [105.8, 207.4, 10.7]}) films.plot(kind="scatter", x="budget_musd")
plt.subplots(nrows, ncols) makes a grid: axes is then an array of Axes, one per panel (axes[0], axes[1] for one row). Draw each chart on its own Axes with ax=. A shared y-axis (sharey=True) makes panels comparable.
import matplotlib.pyplot as plt import pandas as pd films = pd.DataFrame({ "title": ["The Country of Glass", "The Harbor on Fire", "The Island at Dawn", "Quiet Orchard", "Silent Kingdom", "Last Tide"], "release_year": [2015, 1996, 2014, 2019, 1987, 2003], "runtime_min": [87, 133, 117, 79, 107, 69], }) fig, axes = plt.subplots(1, 2) films["runtime_min"].plot.hist(ax=axes[0], bins=[60, 90, 120, 150], title="Runtime (min)") decade = films["release_year"] // 10 * 10 decade.value_counts().sort_index().plot.bar(ax=axes[1], title="Films per decade") print(len(fig.axes), [a.get_title() for a in fig.axes]) print([float(p.get_height()) for p in axes[0].patches]) print([t.get_text() for t in axes[1].get_xticklabels()], [int(p.get_height()) for p in axes[1].patches]) plt.show()
When to use it: quick charts of tables you already grouped, and anything where index and columns are the chart's labels. Switch to ax methods for fine control. Mistakes to avoid: plotting an unsorted value_counts when the categories have a natural order; forgetting ax= (pandas then draws on whichever Axes is current, usually the last one created, not the panel you meant); and plotting a wide table when you meant one column (df["col"].plot).
df.plot(kind=..., ax=...)andseries.plot.bar()draw with matplotlib and return the Axes.- Index → x-axis; columns → series and legend.
plt.subplots(nrows, ncols)gives a grid of Axes; draw each panel withax=axes[i].- Next: which chart answers which question.