KevsRobots Learning Platform
49% Percent Complete
By Kevin McAleer, 5 Minutes
DuckDB integrates tightly with Pandas and Polars. You can query DataFrames directly using SQL and get results back as DataFrames.
Seeing new terms (DataFrame registration, persistence, Parquet)? See the Beginner glossary.
Why this matters:
Useful for small scripts and notebooks when you don’t need persistence.
import duckdb, pandas as pd
# Load a DataFrame
url = 'https://raw.githubusercontent.com/mwaskom/seaborn-data/master/tips.csv'
df = pd.read_csv(url)
# Query a DataFrame directly (DuckDB auto-registers the variable name df)
res = duckdb.query("""
SELECT day, time, ROUND(AVG(total_bill), 2) AS avg_bill
FROM df
GROUP BY day, time
ORDER BY avg_bill DESC
""").df()
print(res.head())
You try it (2–3 min)
- Select only
day, time, tipand computetip_pctin SQL- Filter to
time = 'Dinner'and sort bytip_pctdesc
Notes:
duckdb.query(..) can see variables in the current scope (like df)..df() converts the result to a Pandas DataFrame.Use a connection when you want to create tables, run several queries, or reuse state across cells.
import duckdb
con = duckdb.connect("analytics.duckdb") # creates the file if missing
# Create or reuse a table from a remote CSV
con.execute("""
CREATE TABLE IF NOT EXISTS tips AS
SELECT * FROM read_csv_auto('https://raw.githubusercontent.com/mwaskom/seaborn-data/master/tips.csv')
""")
# Run more queries using the same state
out = con.execute("SELECT day, COUNT(*) AS orders FROM tips GROUP BY day ORDER BY orders DESC").df()
print(out)
con.close()
You try it (2–3 min)
- Add a view
v_tips_enrichedwithtip_pct- Create a table
tip_summary(day, time, revenue, orders)from that view
Notes:
.duckdb file makes your analysis portable and versionable..execute() to run SQL; call .df() to get results into Pandas.When you have an in-memory DataFrame and want to join it with tables.
import duckdb, pandas as pd
local_df = pd.DataFrame({
"day": ["Thur", "Fri", "Sat", "Sun"],
"is_weekend": [False, False, True, True]
})
con = duckdb.connect("analytics.duckdb")
con.register("days", local_df) # now usable as table `days`
res = con.execute("""
SELECT t.day, d.is_weekend, COUNT(*) AS orders
FROM tips t
JOIN days d ON d.day = t.day
GROUP BY t.day, d.is_weekend
ORDER BY orders DESC
""").df()
print(res)
con.close()
You try it (2–3 min)
- Add
avg_tip_pctusingtip / NULLIF(total_bill,0) * 100- Sort by
avg_tip_pctand compare weekend vs weekday
Notes:
register exposes a DataFrame as a temporary table for this connection..df() returns Pandas..pl() returns Polars (requires polars).# Optional: Polars
# pip install polars
import duckdb, polars as pl
q = duckdb.query("SELECT 42 AS answer")
res_pl: pl.DataFrame = q.pl()
print(res_pl)
See also: Troubleshooting DuckDB for common Python/SSL/export issues.
Use ? placeholders and pass values as a list/tuple.
threshold = 20
rows = duckdb.query("SELECT * FROM tips WHERE total_bill > ?", [threshold]).df()
You try it (1–2 min)
- Bind a
min_tip_pctvariable and filter usingtip / NULLIF(total_bill,0) * 100 > ?
exports/).pip install polars.SSL on macOS (certificate verify failed):
- Run the Python certificate script once:
bash "/Applications/Python 3.13/Install Certificates.command"- Or in a venv:
pip install certifithenexport SSL_CERT_FILE="$(python -c 'import certifi; print(certifi.where())')"- Alternative: let DuckDB fetch via httpfs:
import duckdb con = duckdb.connect(); con.execute("INSTALL httpfs; LOAD httpfs;") df = con.execute("SELECT * FROM read_csv_auto('https://…/tips.csv')").df()
You can use the arrows ← → on your keyboard to navigate between lessons.
Comments