【问题标题】:IndexError: list index out of range in a loop of readlines()IndexError:在 readlines() 循环中列出超出范围的索引
【发布时间】:2021-01-29 15:38:32
【问题描述】:

我不明白为什么这会给我一个“IndexError: list index out of range”。 我正在读取一个简单的 csv.file 并尝试将值以逗号分隔。

with open('project_twitter_data.csv','r') as twf:

    tw = twf.readlines()[1:] # I dont need the very first line

    for i in tw:
        linelst = i.strip().split(",")

        RT = linelst[1]
        RP = linelst[2]

        rows = "{}, {}".format(RT,RP)

我的输出是这样的


print(tw) # the original strings.
..\nBORDER Terrier puppy. Name is loving and very protective of the people she loves. Name2 is a 3 year old Maltipoo. Name3 is an 8 year old Corgi.,4,6\nREASON they did not rain but they will reign beautifully couldn't asked for a crime 80 years in the Spring Name's Last Love absolutely love,19,0\nHOME surrounded by snow in my Garden. But City Name people musn't: such a good book: RT @twitteruser The Literature of Conflicted Lands after a,0,0\n\n"

print (i)
..
BORDER Terrier puppy. Name is loving and very protective of the people she loves. Name2 is a 3 year old Maltipoo. Name3 is an 8 year old Corgi.,4,6

REASON they did not rain but they will reign beautifully couldn't asked for a crime 80 years in the Spring Name's Last Love absolutely love,19,0

HOME surrounded by snow in my Garden. But City Name people musn't: such a good book: RT @twitteruser The Literature of Conflicted Lands after a,0,0

print(linelst)
..
['BORDER Terrier puppy. Name is loving and very protective of the people she loves. Name2 is a 3 year old Maltipoo. Name3 is an 8 year old Corgi.', '4', '6']
["REASON they did not rain but they will reign beautifully couldn't asked for a crime 80 years in the Spring Name's Last Love absolutely love", '19', '0']
["HOME surrounded by snow in my Garden. But City Name people musn't: such a good book: RT @twitteruser The Literature of Conflicted Lands after a", '0', '0']
['']

print(rows) 
..
4, 6
19, 0
0, 0


# the error
---------------------------------------------------------------------------
IndexError                                Traceback (most recent call last)
<ipython-input-7-f27e87689f41> in <module>
     6         linelst = i.strip().split(",")
     7 #        print(linelst)
----> 8         RT = linelst[1]
     9         RP = linelst[2]
   

IndexError: list index out of range

我做错了什么?

我还注意到,在我使用 strip().split(",") 之后,我的列表末尾出现了一个空列表 [' ']。 我可以用 twf.readlines()[1:][:-1] 删除它,但错误仍然存​​在.. 谢谢你的建议。

【问题讨论】:

    标签: python-3.x string for-loop readlines


    【解决方案1】:

    剥离后的最后一行是空的,因此 split 会生成一个仅包含空字符串的 list

    最简单的解决方案是显式跳过空行:

    with open('project_twitter_data.csv','r') as twf:
    
        next(twf, None)  # Advance past first line without needing to slurp whole file into memory and
                         # slice it, tying peak memory usage to max line size, not size of file
    
        for line in twf:
            line = line.strip()
            if not line:
                continue
            linelst = line.split(",")
    
            # If non-empty, but incomplete lines should be ignored:
            if len(linelst) < 3:
                continue
    
            RT = linelst[1]
            RP = linelst[2]
    
            rows = "{}, {}".format(RT,RP)
    

    或者更简单,使用 EAFP patternsthe csv module,在处理 CSV 文件时应该始终使用它们(格式比“以逗号分隔”要复杂得多):

    import csv
    
    with open('project_twitter_data.csv', 'r', newline='') as twf:  # newline='' needed for proper CSV dialect handling
        csvf = csv.reader(twf)
        next(csvf, None)  # Advance past first row without needing to slurp whole file into memory and
                          # slice it, tying peak memory usage to max line size, not size of file
    
        for row in csvf:
            try:
                RT, RP = row[1:3]
            except ValueError:
                continue  # Didn't have enough elements, incomplete line
     
            rows = "{}, {}".format(RT,RP)
    

    注意:在这两种情况下,我都做了一些小的改进以避免大的临时列表,并调整了一些小东西以提高可读性(命名 str 变量 i 是错误的形式;i 通常用于索引,或者至少是整数,并且您有一个更清晰的名称随时可用,因此即使是像 x 这样的占位符也是不合适的)。

    【讨论】:

    • 是的!神奇的是,这个错误消失了!是空行导致的吗?
    • @bluetail:是的。空行转换为长度为一的list(唯一有效的索引是0)。一旦您尝试在索引1 处建立索引,它就会以IndexError 死掉(切片不会死,但生成的切片可能比预期的要小,当您尝试将其解压缩到时会导致ValueError目标多于元素),我给出的第二个示例依赖于简化代码)。
    • 是的,我明白了。 if len(linelst)
    • 您是否有指向 next() 上提到参数的文档的链接?我试图查找下一个(,无),但只能找到这个。 docs.python.org/3/library/functions.html
    • @bluetail:该链接包含信息 (direct section link)。第一个参数是一个迭代器(类文件对象和csv.reader 是它们的行/行的迭代器)。第二个参数是迭代器耗尽时返回的默认值。 next(someiterator, None) 是一种廉价的方法,可以在有可用值的情况下从迭代器中丢弃单个值,否则什么也不做。它通过丢弃文件中的第一行/行来匹配您的原始代码,如果文件为空(根本没有行),则不会冒异常的风险。
    猜你喜欢
    • 1970-01-01
    • 2019-05-21
    • 1970-01-01
    • 2022-09-23
    • 1970-01-01
    • 2023-02-08
    • 2020-01-28
    • 2011-10-31
    • 2015-06-26
    相关资源
    最近更新 更多