Pandas idxmax & idxmin

max() tells you the biggest number in a column. It does not tell you who it belongs to. idxmax() answers that second question — it returns the index label of the row holding that maximum, which you can hand straight to .loc to pull back the whole record.

idxmax() returns the index label of the largest value, not the value itself. Pull the whole row with df.loc[], get the top row per group, and avoid the…

Part of the free Pandas course at LearnCodingFast — hands-on lessons with examples you run in your browser, plus practice exercises and a quick quiz.

This is the everyday "which product sold most?" question, and getting it wrong — by sorting the entire frame, or by confusing idxmax with argmax — is one of the most common beginner mistakes in pandas.

What You'll Learn in This Lesson

1 The Value vs. the Location

These two methods answer different questions, and mixing them up is where the confusion starts:

On its own that label is not very interesting. Its power is that .loc accepts it, so the two together give you the complete winning row:

idxmin() is the exact mirror image and takes all the same arguments, so everything below applies to finding minimums too.

2 idxmax vs. argmax — the Bug That Hides

argmax() returns the position (0, 1, 2 …). idxmax() returns the label . On a fresh DataFrame these are the same number, so code using the wrong one appears to work — until you filter the rows or set a custom index, and the labels stop matching the positions.

After a filter, the surviving rows keep their original labels — so a frame of three rows might have labels 1, 2 and 5. That is exactly when position and label part company.

3 The Best Row in Every Group

This is where idxmax really earns its place. Suppose you want the top-selling product per region . A plain groupby("region").max() will not do it — that aggregates every column independently, so you can end up with one region's highest sales sitting next to a different product's name. A row that never existed.

groupby(...)["sales"].idxmax() instead returns one label per group . Feed those labels to .loc and you get real, intact rows:

4 Edge Cases: Ties, NaN, Empty & axis=1

5 🎯 Your Turn

Given a table of city temperature readings, find the single hottest reading, the single coldest, and the hottest reading in each country — keeping every column of those rows intact.

❓ Frequently Asked Questions

Lesson complete — you can now name the winner, not just the number!

You know that idxmax returns a label, that .loc turns that label into a full row, and that groupby(...).idxmax() is the honest way to get the best record per group.

🚀 Up next: Ranking & Top-N — rank rows and pull the top few with rank and nlargest .

Practice quiz

What does df["sales"].idxmax() return?

  • The largest sales value
  • The index label of the largest value
  • The row as a Series
  • The column name

Answer: The index label of the largest value. idxmax returns the index LABEL where the maximum sits — not the value itself.

How do you get the whole row containing the largest value?

  • df.max()

idxmax gives you the label; feed that label to .loc to pull back the entire row.

What is the difference between .max() and .idxmax()?

  • They are identical
  • max returns the value, idxmax returns where it is
  • max is faster
  • idxmax only works on integers

Answer: max returns the value, idxmax returns where it is. max answers 'what is the biggest number', idxmax answers 'which row holds it'.

If two rows tie for the maximum, what does idxmax return?

  • Both labels
  • The last one
  • The first one it meets
  • NaN

Answer: The first one it meets. Ties are broken by position — idxmax returns the first occurrence only.

By default, how does idxmax treat NaN values?

  • Returns NaN
  • Raises an error
  • Skips them (skipna=True)
  • Treats them as zero

Answer: Skips them (skipna=True). skipna defaults to True, so missing values are ignored when finding the maximum.

What happens if you call idxmax() on an empty Series?

  • Returns None
  • Returns 0
  • Returns NaN
  • Raises a ValueError

Answer: Raises a ValueError. There is no label to return, so pandas raises ValueError: attempt to get argmax of an empty sequence.

Which argument makes idxmax scan across columns instead of down rows?

  • axis=1
  • across=True
  • rows=False
  • orient='columns'

Answer: axis=1. axis=1 works row-wise, returning the column NAME holding each row's maximum.

How do you find the best-selling row within every region?

  • df.groupby('region').max()
  • region
  • sales

Answer: region. groupby(...).idxmax() gives one label per group; .loc turns those labels back into full rows.

How does argmax differ from idxmax?

  • They are the same method
  • argmax returns a position, idxmax returns a label
  • argmax works on strings only
  • argmax is deprecated

Answer: argmax returns a position, idxmax returns a label. argmax gives the integer POSITION (use with .iloc); idxmax gives the index LABEL (use with .loc).

Why is df.loc[df['x'].idxmax()] better than sorting the whole frame?

  • It is not, sorting is always better
  • It reads more clearly and avoids sorting every row
  • It handles NaN differently
  • Sorting cannot find a maximum

Answer: It reads more clearly and avoids sorting every row. Sorting rearranges every row just to read the top one; idxmax goes straight to it and states your intent.

Continue this course