无法重复迭代 "csv.reader" - 第二次迭代结果为空
Unable to iterate "csv.reader" repeatedly - empty result on second iteration
我创建了 list1
以包含来自特定列的唯一值,方法是附加标识为唯一的值以执行某种 "sum if"。
下面是我遇到的情况,内循环,遍历 csv 行只执行一次。是否有一些特殊的特征使得在嵌套循环的内部循环中遍历 csv 文件中的行有问题?
csv 内容:
Field1
row1
row2
row3
代码:
datafile = open(r"my_file.csv", "r")
myreader = csv.reader(datafile, delimiter=",")
list1 = ["A", "B", "C"]
for x in list1[:]:
print(x)
for y in myreader:
print(y)
预期结果:
A
row1
row2
row3
B
row1
row2
row3
C
row1
row2
row3
实际结果:
A
row1
row2
row3<
B
C
似乎只有内部循环的初始迭代在工作。
如果我用另一个列表替换 csv,它工作正常:
datafile = open(r"my_file.csv", "r")
myreader = csv.reader(datafile, delimiter=",")
list1 = ["A", "B", "C"]
list2 = ["row1", "row2", "row2"]
for x in list2[:]:
print(x)
for y in list2:
print(y)
给出了预期的结果
而且我可以在单个循环中遍历 csv 行,下面没有问题:
x = 0
for y in myreader:
x = x + 1
print(y[2] + " INNER")
那为什么不能一起工作呢?
在使用 A
循环后,您的 reader 迭代器位于所有数据的后面。
您必须将其重新定位到开头,但为什么要这样做?
最好将所有数据一次保存到一个列表中,然后再使用它。
myData = list(myreader) # this will iterate the whole file and put all in a list.
myreader
是一个迭代器,会在第一次迭代后耗尽。
将其转换为列表以获得所需的输出。
csv_rows = list(myreader)
for x in list1[:]:
print(x)
for y in csv_rows:
print(y)
迭代器只允许迭代一次。另一方面,列表可以一次又一次地迭代。迭代器的优点是不会一次将所有元素加载到内存中。如果文件很大,这可能很重要。在这种情况下,列表可能会消耗大量内存。
csv.reader
returns 一个 reader
对象,它是一个迭代器。所以,一旦你遍历了整个列表,它就变成了空的。您需要将 reader 保存为 list
以便重复迭代它。
为了实现这个,你需要改变:
myreader = list(csv.reader(datafile, delimiter=","))
# ^ it'll save `myreader` as list
因此,您完整的代码应该是:
datafile = open(r"my_file.csv", "r")
myreader = list(csv.reader(datafile, delimiter=","))
# ^ converting the `iterator` to list type
list1 = ["A", "B", "C"]
# v I removed "[:]" from here because it is not required
# v `list1[:]` creates a copy of the list "list1". You
# v don't need copy here
for x in list1:
print(x)
for y in myreader:
print(y)
我创建了 list1
以包含来自特定列的唯一值,方法是附加标识为唯一的值以执行某种 "sum if"。
下面是我遇到的情况,内循环,遍历 csv 行只执行一次。是否有一些特殊的特征使得在嵌套循环的内部循环中遍历 csv 文件中的行有问题?
csv 内容:
Field1
row1
row2
row3
代码:
datafile = open(r"my_file.csv", "r")
myreader = csv.reader(datafile, delimiter=",")
list1 = ["A", "B", "C"]
for x in list1[:]:
print(x)
for y in myreader:
print(y)
预期结果:
A
row1
row2
row3
B
row1
row2
row3
C
row1
row2
row3
实际结果:
A
row1
row2
row3<
B
C
似乎只有内部循环的初始迭代在工作。
如果我用另一个列表替换 csv,它工作正常:
datafile = open(r"my_file.csv", "r")
myreader = csv.reader(datafile, delimiter=",")
list1 = ["A", "B", "C"]
list2 = ["row1", "row2", "row2"]
for x in list2[:]:
print(x)
for y in list2:
print(y)
给出了预期的结果
而且我可以在单个循环中遍历 csv 行,下面没有问题:
x = 0
for y in myreader:
x = x + 1
print(y[2] + " INNER")
那为什么不能一起工作呢?
在使用 A
循环后,您的 reader 迭代器位于所有数据的后面。
您必须将其重新定位到开头,但为什么要这样做?
最好将所有数据一次保存到一个列表中,然后再使用它。
myData = list(myreader) # this will iterate the whole file and put all in a list.
myreader
是一个迭代器,会在第一次迭代后耗尽。
将其转换为列表以获得所需的输出。
csv_rows = list(myreader)
for x in list1[:]:
print(x)
for y in csv_rows:
print(y)
迭代器只允许迭代一次。另一方面,列表可以一次又一次地迭代。迭代器的优点是不会一次将所有元素加载到内存中。如果文件很大,这可能很重要。在这种情况下,列表可能会消耗大量内存。
csv.reader
returns 一个 reader
对象,它是一个迭代器。所以,一旦你遍历了整个列表,它就变成了空的。您需要将 reader 保存为 list
以便重复迭代它。
为了实现这个,你需要改变:
myreader = list(csv.reader(datafile, delimiter=","))
# ^ it'll save `myreader` as list
因此,您完整的代码应该是:
datafile = open(r"my_file.csv", "r")
myreader = list(csv.reader(datafile, delimiter=","))
# ^ converting the `iterator` to list type
list1 = ["A", "B", "C"]
# v I removed "[:]" from here because it is not required
# v `list1[:]` creates a copy of the list "list1". You
# v don't need copy here
for x in list1:
print(x)
for y in myreader:
print(y)