In Python, you cannot access values inside a _csv.reader
object using indexing syntax.
The reader()
method from the csv
module returns a _csv.reader
object, which is an iterable containing the lines of the file.
We can solve this error by converting the _csv.reader
object to a list using the built-in list method.
For example,
import csv with open('pizzas.csv', newline='') as f: reader = list(csv.reader(f)) print(reader[1])
We can also iterate over the lines in the _csv.reader
object using a for
loop.
This tutorial will go through the error in detail with code examples.
TypeError: ‘_csv.reader’ object is not subscriptable
Let’s break up the error message to understand what the error means. TypeError occurs whenever you attempt to use an illegal operation for a specific data type. The part “_csv.reader object” tells us the error concerns an illegal operation for the _csv.reader
object.
The part “is not subscriptable” tells us we cannot access an element of the _csv.reader
object using the subscript operator, which is square brackets []
.
A subscriptable object is a container for other objects and implements the __getitem__()
method. Examples of subscriptable objects include strings, lists, tuples, and dictionaries.
We can check if an object implements the __getitem__()
method by listing its attributes with the dir
function. Let’s call the dir
function and pass a _csv.reader
object and a str
object to see their attributes. We will read in a file called pizzas.csv
containing the following data:
pizza,price margherita,£7.99 pepperoni,£8.99 four cheeses,£10.99 funghi,£8.99
import csv with open('pizzas.csv', newline='') as f: reader = csv.reader(f) print(dir(reader))
['__class__', '__delattr__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__iter__', '__le__', '__lt__', '__ne__', '__new__', '__next__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', 'dialect', 'line_num']
We can see that __getitems__
is not present in the list of attributes for the _csv.reader
object.
string = "Python" print(dir(string))
['__add__', '__class__', '__contains__', '__delattr__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__getitem__', '__getnewargs__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__iter__', '__le__', '__len__', '__lt__', '__mod__', '__mul__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__rmod__', '__rmul__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', 'capitalize', 'casefold', 'center', 'count', 'encode', 'endswith', 'expandtabs', 'find', 'format', 'format_map', 'index', 'isalnum', 'isalpha', 'isascii', 'isdecimal', 'isdigit', 'isidentifier', 'islower', 'isnumeric', 'isprintable', 'isspace', 'istitle', 'isupper', 'join', 'ljust', 'lower', 'lstrip', 'maketrans', 'partition', 'replace', 'rfind', 'rindex', 'rjust', 'rpartition', 'rsplit', 'rstrip', 'split', 'splitlines', 'startswith', 'strip', 'swapcase', 'title', 'translate', 'upper', 'zfill']
If we want to check if a specific attribute belongs to an object, we can check for membership using the in
operator.
import csv with open('pizzas.csv', newline='') as f: reader = csv.reader(f) print(type(reader)) print('__getitem__' in dir(reader))
<class '_csv.reader'> False
The variable reader
is an object of the _csv.reader
class. We can see that __getitem__
is not an attribute of the _csv.reader
class.
string = "Python" print(type(string)) print('__getitem__' in dir(string))
<class 'str'> True
We can see that __getitem__
is an attribute of the str
class.
Example
Let’s look at an example of trying to access an element of a _csv.reader
object using indexing.
First, we will define a file called pizzas.csv
, which contains the names and prices of pizzas in CSV
format:
pizza,price margherita,£7.99 pepperoni,£8.99 four cheeses,£10.99 funghi,£8.99
Next, import the csv
module, read the file into our program using a context manager, and then create a reader object using the csv.reader()
method. We will then try to access the second element of the reader object using the subscript operator, []
.
import csv with open('pizzas.csv', newline='') as f: reader = csv.reader(f) print(reader[1])
Let’s run the code to see what happens:
--------------------------------------------------------------------------- TypeError Traceback (most recent call last) Input In [4], in <cell line: 3>() 3 with open('pizzas.csv', newline='') as f: 5 reader = csv.reader(f) ----> 7 print(reader[1]) TypeError: '_csv.reader' object is not subscriptable
The error occurs because the reader variable is a _csv.reader
object, which is an iterable containing the lines of the CSV
file, which we can access using a for
loop or calling the next()
method. We are trying to access values in the _csv.reader
object as though it were a list
or another subscriptable object.
Solution
We can solve this error by converting the _csv.reader
object to a list
using the built-in list()
method.
Let’s look at the revised code:
import csv with open('pizzas.csv', newline='') as f: reader = list(csv.reader(f)) print(reader[1])
Let’s run the code to see the result:
['margherita', '£7.99']
We successfully retrieved the first line of the CSV
file. Each line returned by the reader object is a list containing the comma separated values.
The common way to read a CSV
file with the reader
object is to use a for
loop. Let’s look at the revised code:
import csv with open('pizzas.csv', newline='') as f: reader = csv.reader(f) next(reader) for line in reader: print(': '.join(line))
In the above code, we call the next()
method to skip the field names in the CSV
file, then use a for
loop to iterate over the lines of the CSV
file. We use the string join()
method to join the items in the list into a single string. Let’s run the code to see the result:
margherita: £7.99 pepperoni: £8.99 four cheeses: £10.99 funghi: £8.99
Each line is a list of values and we can access each value using the subscript operator, []
. Let’s look at getting the first value of each line:
import csv with open('pizzas.csv', newline='') as f: reader = csv.reader(f) next(reader) for line in reader: print(line[0])
Let’s run the code to get the result:
margherita pepperoni four cheeses funghi
We successfully retrieved the first value of each line in the CSV
file.
Summary
Congratulations on reading to the end of this tutorial!
For further reading on AttributeErrors, go to the articles:
- How to Solve Python TypeError: ‘zip’ object is not subscriptable
- How to Solve Python TypeError: ‘dict_items’ object is not subscriptable
To learn more about Python for data science and machine learning, you can go to the online courses page on Python for the most comprehensive courses.
Have fun and happy researching!
Suf is a senior advisor in data science with deep expertise in Natural Language Processing, Complex Networks, and Anomaly Detection. Formerly a postdoctoral research fellow, he applied advanced physics techniques to tackle real-world, data-heavy industry challenges. Before that, he was a particle physicist at the ATLAS Experiment of the Large Hadron Collider. Now, he’s focused on bringing more fun and curiosity to the world of science and research online.