When comprehensions are new to you, every for loop looks like something to compress onto one line. But their value is not brevity — it is being able to declare, in one sentence, what this list is.

Where they fit

python
# reads as "the list of tax-inclusive prices, from the price list"
prices_with_tax = [int(p * 1.1) for p in prices]

# "the list of names of the items that are in stock"
in_stock = [item.name for item in items if item.stock > 0]

Both can be explained in a single sentence of English. In that state, a comprehension is the right choice.

Where they do not fit

python
# takes real effort to decode
result = [transform(x) if check(x) else fallback(x)
          for row in matrix for x in row if x is not None]

Once the nesting reaches two levels, or a conditional has crept into the expression itself, go back to an ordinary for loop. It takes more lines, but the odds of you understanding it in three months' time go up sharply.

Dictionaries and sets have the same form

python
by_id = {user.id: user for user in users}
unique_tags = {tag for post in posts for tag in post.tags}

The rule of thumb

If you can explain it out loud in one sentence, use a comprehension. The moment you want to say "first do this, and then", use a for loop.