Pebellslearn by building
0%
RoadmapsMatrixCoursesSandboxSign in
pandas Series and DataFrames  ›  Lesson

Selecting with loc and iloc

Indexing & Slicing 14 minloc selects rows and columns by their labels and includes the end of a slice, while iloc selects by integer position and excludes it.

Selecting with loc and iloc

"What was the branch on sale 4?" "Show rows 2 to 4, just branch and copies." A DataFrame has two ways to point at cells: by the labels printed on it, or by counting positions. pandas gives each its own tool, and mixing them up is the most common beginner bug in pandas.

The rule

loc uses labels and includes the end; iloc uses positions and excludes it.

We keep using sales, now with its revenue column (8 rows; columns date, branch, genre, copies, price, revenue).

sales.loc[4, "branch"]              # 'Delhi'   row label 4, column named branch
sales.loc[2:4, ["branch", "copies"]]  # rows labelled 2, 3 AND 4

sales.iloc[4, 1]                    # 'Delhi'   5th row, 2nd column
sales.iloc[2:4, [1, 3]]             # rows at positions 2 and 3 only

Both take [rows, columns], and both accept a single item, a list, or a slice in each part. A colon alone means "all": sales.loc[:, "price"] is the whole price column.

So far labels and positions look identical, because the default index is 0, 1, 2… The difference becomes obvious once the index is something else:

by_date = sales.set_index("date")
by_date.loc["2024-03-02"]     # both rows with that date label
by_date.iloc[0]               # the first row, whatever its label

loc also takes a boolean mask for the rows, which is how the next lesson filters data:

sales.loc[sales["copies"] > 4, "branch"]   # Delhi, Chennai

The shortcut

Say the letter out loud: i for integer position. If you are counting ("the third row"), reach for iloc. If you are naming ("the row labelled 3", "the column called price"), reach for loc. Then apply the end rule: names include the end, counts do not.

Rows 2 to 4, branch and copiesStep 1 of 4
  1. Naming or counting?

    The request says "rows 2 to 4" meaning the printed labels, and names the columns. Naming, so loc.

The trap: sales.iloc[2:4] looks like the same request but returns only two rows, because positions stop before the end.

Drills

Answer fast — trust the rule.

quick drill

How many rows does sales.loc[1:3] return?

quick drill

How many rows does sales.iloc[1:3] return?

quick drill

Which expression returns 'science' from row 2?

quick drill

What does sales.iloc[-1, 3] return?

quick drill

After by_date = sales.set_index("date"), what does by_date.loc["2024-03-03", "copies"] return?

Remember

  • loc uses labels and includes the end; iloc uses positions and excludes it.
  • i for integer: counting means iloc, naming means loc.
  • An index label can repeat, so loc can return several rows for one label.

Practice — level up

0/1 solved

Write your answer, then compare it with a rubric and a model answer.

ExplainTwo rows or three?

A colleague is surprised that sales.loc[2:4] returns three rows but sales.iloc[2:4] returns two. Explain why, and when you would reach for each.