You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python代码在Jupyter Notebook中两次迭代报错问题咨询

问题拆解与解决方案

嘿,这个问题我熟!咱们先说说为啥会报错:

核心问题根源

你用的csv.reader()返回的是个迭代器(iterator),这玩意儿有个特性——只能从头到尾遍历一次!当你第一个for row in reader循环跑完所有行之后,这个迭代器的“指针”就停在文件末尾了,再跑第二个for each in reader循环时,已经没东西可读了,循环根本不会执行。而且你第二个循环里还误用了第一个循环的row变量,这要么会拿到上一次循环最后一行的值,要么直接报变量未定义的错,雪上加霜😂

几种靠谱的解决办法

1. 把所有行存成列表,想遍历多少次都行

先把迭代器转成列表,列表是可以反复遍历的序列,这样两次循环就都能拿到数据了:

import csv
csvfile = open("sales_rank.csv")
reader = csv.reader(csvfile)
header = next(reader)
# 把所有行存进列表,以后随便用
all_rows = list(reader)

category = {}
rank = {}

# 第一次遍历处理category
for row in all_rows:
    category.setdefault(row[1], []).append(row[4])

# 第二次遍历处理rank,注意这里要用当前循环的变量each,别再用row了!
for each in all_rows:
    rank.setdefault(each[3], []).append(each[0])

# 别忘了关文件哦
csvfile.close()

2. 一次循环搞定两个字典,高效又省心

其实没必要分两次循环,在同一个循环里同时处理category和rank就好,既省内存又避免迭代器的坑:

import csv
category = {}
rank = {}

# 用with语句自动管文件,不用手动close,超安全
with open("sales_rank.csv") as csvfile:
    reader = csv.reader(csvfile)
    header = next(reader)
    # 一次循环同时填充两个字典
    for row in reader:
        category.setdefault(row[1], []).append(row[4])
        rank.setdefault(row[3], []).append(row[0])

这种方式是我最推荐的,代码更简洁,效率也更高,还不会有迭代器的问题。

3. 重置文件指针(不推荐,凑数用的)

如果你非要分开两次循环,那可以在第一次循环后把文件指针移回开头,再重新跳过表头,但这种方法有点啰嗦,大文件的话效率也不高:

import csv
csvfile = open("sales_rank.csv")
reader = csv.reader(csvfile)
header = next(reader)

category = {}
for row in reader:
    category.setdefault(row[1], []).append(row[4])

# 把文件指针移回开头,然后再跳过一次表头
csvfile.seek(0)
next(reader)

rank = {}
for each in reader:
    rank.setdefault(each[3], []).append(each[0])

csvfile.close()

最后提个小坑

你第二次循环里写的rank.setdefault(row[3],[]).append(row[0])绝对要改!这里的row是第一个循环的变量,到第二个循环里它要么是第一个循环最后一行的内容,要么直接报错,一定要改成each[3]和each[0],对应你第二个循环的变量名~

内容的提问来源于stack exchange,提问作者Jefferson

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.26 09:16:36