Filtering and Querying
The Delhi manager asks: "Which of my sales were science books?" You do not want to scan eight rows by eye, and certainly not eighty thousand. Filtering keeps only the rows that answer yes to a question.
The rule
Build a True/False column, then keep the True rows.
A comparison on a column gives a boolean Series, one True or False per row:
sales["branch"] == "Delhi"
# 0 False, 1 True, 2 False, 3 False, 4 True, 5 False, 6 False, 7 TruePut that Series inside the brackets and pandas keeps the rows marked True:
delhi = sales[sales["branch"] == "Delhi"] # rows 1, 4, 7Combine conditions with & (and), | (or) and ~ (not), wrapping each condition in parentheses:
sales[(sales["branch"] == "Delhi") & (sales["genre"] == "science")] # rows 1 and 7
sales[~(sales["genre"] == "comics")] # everything except comicsTwo helpers save typing:
sales[sales["branch"].isin(["Pune", "Chennai"])] # branch is any of these
sales[sales["copies"].between(2, 4)] # 2 to 4, ends included.query() lets you write the same condition as a readable string, with plain and/or:
sales.query("branch == 'Delhi' and genre == 'science'")
sales.query("copies > 3")To filter rows and choose columns at once, use loc:
sales.loc[sales["copies"] > 3, ["branch", "copies"]]The shortcut
Read every filter as "rows where …" and check each piece has parentheses. Then count before you trust: mask.sum() tells you how many rows will survive, because each True counts as 1.
Write each condition
sales["branch"] == "Delhi"is True for rows 1, 4, 7.sales["genre"] == "science"is True for rows 1, 2, 7.
The trap: forgetting parentheses. sales["branch"] == "Delhi" & sales["genre"] == "science" raises an error, because & is evaluated before ==.
Drills
Answer fast — trust the rule.
How many rows does sales[sales["copies"] > 3] keep?
Which rows does sales[sales["branch"].isin(["Pune", "Chennai"])] keep?
Which is the correct pandas filter for "comics or fewer than 2 copies"?
How many rows does sales.query("price == 400 and copies >= 3") return?
Remember
- Build a True/False column, then keep the True rows.
- Use
&,|,~with parentheses around each condition, or write.query()withand/or. - Count with
mask.sum()before trusting a filter.
