考虑到Takewhile的最后一次迭代(itertools)

时间:2019-03-28 16:14:27

标签: python csv itertools

我需要遍历.csv,直到名为“ seguir”的布尔值变为False为止。 问题在于,takewhile会丢弃最后一次迭代,而我需要这样做,因为该行中的.csv值与我的问题有关

for line in itertools.takewhile(lambda x: seguir, lectura):

    data3 = strintodate(line[1])
    data4 = strintodate(line[2])
    if data2 < data4:
        seguir = False
    escritura.writerow([programa + 1, data2, data2, line[4]])

有什么建议吗? 谢谢

4 个答案:

答案 0 :(得分:2)

您可以使用for循环,但条件是写行后break s:

for line in lectura:
    data3 = strintodate(line[1])
    data4 = strintodate(line[2])
    escritura.writerow([programa + 1, data2, data2, line[4]])
    if data2 < data4:
        break

答案 1 :(得分:1)

该问题的另一个更优雅的解决方案是更改 您评估data2 < data4:如果您在takewhile()的谓词中这样做,它将允许您在处理中包括“最后一次”迭代。换句话说,如果您的data2 < data4有5行,而第六行有data2 >= data4,则下面的for循环将执行6次,最后一次允许您保留这些值。

代码如下:

data2, data4 = 2, 4
for line in itertools.takewhile(lambda x: data2 < data4, lectura):
    data2 = strintodate(line[1])
    data4 = strintodate(line[2])
    escritura.writerow([programa + 1, data2, data2, line[4]])

答案 2 :(得分:0)

如果不做太多更改,您可以将temp变量保留在用于存储前一行的for循环之外

prevLine = ""
for line in itertools.takewhile(lambda x: seguir, lectura):
    <check that prevLine is not empty string as it will be on first iteration>
    <do oepration involving prevLine>
    data3 = strintodate(line[1])
    data4 = strintodate(line[2])
    if data2 < data4:
        seguir = False
    escritura.writerow([programa + 1, data2, data2, line[4]])
    prevLine = line

答案 3 :(得分:0)

blhsing's解决方案是解决之道,但是还有另一种方法可以使猫变皮-使用itertools.tee创建紧随其后的迭代器

iter1, iter2 = tee(lectura)
for line in itertools.takewhile(lambda x: seguir, iter1):
    next(iter2)
    data3 = strintodate(line[1])
    data4 = strintodate(line[2])
    if data2 < data4:
        seguir = False
    escritura.writerow([programa + 1, data2, data2, line[4]])
line = next(iter2)
data3 = strintodate(line[1])
data4 = strintodate(line[2])
escritura.writerow([programa + 1, data2, data2, line[4]])

总之,丑陋。通过将data2和其他元素的设置以及对writerow的调用提取到单独的函数中,可以在某种程度上进行挽救