使用csv reader从文件中删除行并列出python

时间:2017-07-25 12:22:50

标签: python csv

对此有类似的问题,但没有一个涉及我要求的具体细节。

我有以下代码,它试图根据指定的用户输入删除文件中的行。方法是

  1. 将文件读入列表
  2. 删除列表中的相关行(理想情况下,在列表中读取时?)
  3. 覆盖文件。
  4. 我希望有一些指导和关于最佳解决方案的评论(对于初学者,用于教学/学习目的),用csv阅读器在python中进行这种简单的删除/编辑。

    代码

    """ ==============TASK
    1. Search for any given username
    2. Delete the whole row for that particular user
    
    e.g.
    Enter username: marvR
    >>The record for marvR has been deleted from file.
    """
    
    import csv
    
    #1. This code snippet asks the user for a username and deletes the user's record from file.
    
    updatedlist=[]
    with open("fakefacebook.txt",newline="") as f:
      reader=csv.reader(f)
      username=input("Enter the username of the user you wish to remove from file:")
      for row in reader: #for every row in the file
          if username not in updatedlist:
            updatedlist=row #add each row, line by line, into a list called 'udpatedlist'
            print(updatedlist)
    
     #delete the row for the user from the list?
    #overwrite the current file with the updated list?
    

    文件内容:

    username,password,email,no_of_likes
    marvR,pass123,marv@gmail.com,400
    smithC,open123,cart@gmail.com,200
    blogsJ,2bg123,blog@gmail.com,99
    

    更新

    根据下面的答案,我有这个,但是当它覆盖文件时,它不会正确地更新列表,不确定原因。

    import csv
    def main():
        #1. This code snippet asks the user for a username and deletes the user's record from file.
        updatedlist=[]
        with open("fakefacebook.txt",newline="") as f:
          reader=csv.reader(f)
          username=input("Enter the username of the user you wish to remove from file:")
          for row in reader: #for every row in the file
              if row[0]!=username: #as long as the username is not in the row .......
                updatedlist=row #add each row, line by line, into a list called 'udpatedlist'
                print(updatedlist)
        updatefile(updatedlist)
    
    def updatefile(updatedlist):
        with open("fakefacebook.txt","w",newline="") as f:
            Writer=csv.writer(f)
            Writer.writerow(updatedlist)
            print("File has been updated")
    
    
    main()
    

    它似乎正确打印更新的文件(作为列表),因为它删除了输入的用户名。但是在将此文件写入文件时,它只会在文件中输入一个用户名。

    有任何想法,我可以接受最终答案吗?

5 个答案:

答案 0 :(得分:3)

if username not in updatedlist:

对我来说应该是:

if row[0] != username:

然后在第二个循环中,将更新列表写入csv文件。 我会在读取时将所有内容写入另一个文件中,然后最后删除旧文件并将其替换为新文件,这使其只有一个循环。

编辑:

updatedlist=row替换为updatedlist.append(row):第一个意味着用一行覆盖updatedlist,而第二个意味着再添加一行。

writerow写一行,然后给它一个行列表。 使用writerows代替您的写作功能。

你差不多完成了所有这一切,这是我的目标。 其他一些答案已经为你提供了更好(更快,更清洁......)的方法,所以我不会。

答案 1 :(得分:1)

使用csv模块,你应该这样做。由于您使用已定义的列构建了表格数据,因此您应使用DictReaderDictWriter来读取/写入文件;

import csv

with open('fakefacebook.txt', 'r+') as f:
    username = input("Enter the username of the user you wish "
                         "to remove from file:")
    columns = ['username', 'password', 'email', 'no_of_likes']

    reader = csv.DictReader(f, columns)
    filtered_output = [line for line in reader if line['username'] != username]

    f.seek(0)
    writer = csv.DictWriter(f, columns)
    writer.writerows(filtered_output)
    f.truncate()

这将打开输入文件,过滤掉用户名等于要删除的所需用户名的任何条目,并将剩余的条目写入输入文件,覆盖已经存在的内容。< / p>

答案 2 :(得分:1)

我推荐这种方法:

with open("fakefacebook.txt", 'r+') as f:
    lines = f.readlines()
    f.seek(0)

    username = input("Enter the username of the user you wish to remove from file: ")
    for line in lines:
        if not username in line.split(',')[0]:  # e.g. is username == 'marvR', the line containing 'marvR' will not be written
            f.write(line)

    f.truncate()

文件中的所有行都会被读入lines。然后我用f.seek(0)返回文件的起始位置。此时,系统会要求用户输入用户名,然后用户在写回文件之前检查每一行。如果该行包含指定的用户名,则不会写入,因此“删除”它。最后,我们使用f.truncate()删除任何多余的内容。我希望这有帮助,如果您有任何问题请不要犹豫!

答案 3 :(得分:1)

我试图坚持你的代码:(编辑:不优雅,但尽可能接近OP代码)

""" ==============TASK
1. Search for any given username
2. Delete the whole row for that particular user

e.g.
Enter username: marvR
>>The record for marvR has been deleted from file.
"""

import csv

#1. This code snippet asks the user for a username and deletes the user's record from file.

updatedlist=[]
with open("fakefacebook.txt",newline="") as f:
  reader=csv.reader(f)
  username=input("Enter the username of the user you wish to remove from file:")
  content = []
  for row in reader: #for every row in the file 
     content.append(row)

# transpose list  
content = list(map(list, zip(*content)))
print(content)
index = [i for i,x in enumerate(content[0]) if x == username]
for sublist in content:
  sublist.pop(index[0])

print(content)

# transpose list  
content = list(map(list, zip(*content)))

#write back
thefile = open('fakefacebook.txt', 'w')
for item in content:
  thefile.write("%s\n" % item)

但我建议使用numpy或pandas

答案 4 :(得分:1)

另一个答案是:写一个新文件,然后重命名它!

import csv
import os

def main():
    username = input("Enter the username of the user you wish to remove from file:")
    # check it's not 'username'!

    #1. This code snippet asks the user for a username and deletes the user's record from file.
    with open("fakefacebook.txt", newline="") as f_in, \
            open("fakefacebook.txt.new", "w", newline="") as f_out:
        reader = csv.reader(f_in)
        writer = csv.writer(f_out)
        for row in reader: #for every row in the file
            if row[0] != username: # as long as the username is not in the row
                writer.writerow(row)
    # rename new file
    os.rename("fakefacebook.txt.new", "fakefacebook.txt")

main()