Python TypeError: 'tuple' object is not callable when using list comprehension inside for loop

Question:

I’m trying to generate a list of strings using a list comprehension, where the string is formatted using f-strings:

features = [("month", (1, 12)), ("day_of_year", (1, 365))]
for feature, range in features:
  cols= [f"transformed_{feature}_period_{i:02d}" for i in range(12)]

If I run this code, I get an error:

---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
Cell In[4], line 3
      1 features = [("month", (1, 12)), ("day_of_year", (1, 365))]
      2 for feature, range in features:
----> 3     cols= [f"transformed_{feature}_period_{i:02d}" for i in range(12)]

TypeError: 'tuple' object is not callable

I still get the error even if I remove the variables from the string:

for feature, range in features:
  cols= ["transformed_feature_period" for i in range(12)]

I don’t understand why the interpreter is complaining that I’m trying to call a tuple. I’m able to perform other operations, such as actual function calling and asserts inside the outer for loop, but I keep bumping into this error when trying to use a list comprehension.

Thanks in advance for any help.

Asked By: RicardoC

||

Answers:

If you don’t actually use the range,

for feature, _ in features:
    ...

If you only care about the endpoints of the range,

for feature, (start, stop) in features:
    ...

If you really need a reference to the tuple as a whole, pick a name that doesn’t shadow the built-in type you use later:

for feature, feature_range in features:
    ...

I don’t recommend using builtins.range to access the shadowed type when it’s simpler to provide a more accurate name for the index variable in the first place.

Answered By: chepner

Make sure you change your Jupyter notebook or anyother idle you are using because the range() function will become tuple as it will override the buitin range .

features = [("month", (1, 12)), ("day_of_year", (1, 365))]
for feature, r in features:
    print(feature, range(int(r[0]),int(r[1])))

#output

month range(1, 12)
day_of_year range(1, 365)

So, this will be the final code:

features = [("month", (1, 12)), ("day_of_year", (1, 365))]
for feature, r in features:
  cols= [f"transformed_{feature}_period_{i:02d}" for i in range(int(r[0]),int(r[1]))]

print(cols)
['transformed_day_of_year_period_01',
 'transformed_day_of_year_period_02',
 'transformed_day_of_year_period_03',
 'transformed_day_of_year_period_04',
 'transformed_day_of_year_period_05',
  ....
 'transformed_day_of_year_period_364']
Answered By: God Is One
Categories: questions Tags: , ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.