【问题标题】:How to delete columns in a CSV file?如何删除 CSV 文件中的列?
【发布时间】:2011-11-27 04:26:11
【问题描述】:

我已经能够使用该站点上多个用户的输入使用 python 创建一个 csv,我希望对您的帖子表示感谢。我现在很困惑,将发布我的第一个问题。

我的 input.csv 如下所示:

day,month,year,lat,long
01,04,2001,45.00,120.00
02,04,2003,44.00,118.00

我正在尝试删除“年份”列及其所有条目。总共有 40 多个条目,范围从 1960 年到 2010 年。

【问题讨论】:

  • 这是awk 的亮点:$ awk -F, 'BEGIN {OFS=","} {print $1,$2,$4,$5}' ex.csv
  • @Eric Wilson:幸运的是,这个 CSV 文件没有引号,允许 AWK 工作。
  • @S.Lott 我同意,当 CSV 格式变得更加复杂时,Python 的 csv 是要走的路。我只在 awk 明显有效时才使用它,而且只有一行。

标签: python csv row-removal


【解决方案1】:

我将为这个问题添加另一个答案。由于 OP 没有说他们需要使用 Python 来执行此操作,因此删除列的最快方法(特别是当输入文件有数十万行时)是使用 awk

这是 awk 擅长的问题类型:

$ awk -F, 'BEGIN {OFS=","} {print $1,$2,$4,$5}' input.csv

(如果您需要将输出保存到文件中,请随时将> output.csv 附加到上述命令中)

100% 归功于 @eric-wilson,他在 10 年前提供了这个很棒的答案,作为对原始问题的评论,几乎没有任何功劳。

【讨论】:

    【解决方案2】:

    我会使用带有列号的 Pandas

    f = pd.read_csv("test.csv", usecols=[0,1,3,4])

    f.to_csv("test.csv", index=False)

    【讨论】:

      【解决方案3】:

      试试:

      result= data.drop('year', 1)
      result.head(5)
      

      【讨论】:

        【解决方案4】:
        import csv
        with open("source","rb") as source:
            rdr= csv.reader( source )
            with open("result","wb") as result:
                wtr= csv.writer( result )
                for r in rdr:
                    wtr.writerow( (r[0], r[1], r[3], r[4]) )
        

        顺便说一句,for 循环可以删除,但并没有真正简化。

                in_iter= ( (r[0], r[1], r[3], r[4]) for r in rdr )
                wtr.writerows( in_iter )
        

        此外,您可以按照超文字的方式来满足删除列的要求。我发现这通常是一个糟糕的策略,因为它不适用于删除多个列。当您尝试删除第二个时,您会发现所有位置都发生了变化,并且结果行并不明显。但仅对于一列,这有效。

                    del r[2]
                    wtr.writerow( r )
        

        【讨论】:

        • 这个工作几乎完美无缺,出现了语法错误。应该从 wtr=csv.writer(result) 中删除冒号 感谢您对此的输入,它有帮助,它也很方便,因为它适用于我可能需要删除的任意数量的列。
        • 您可以通过首先删除最高列来轻松地将第二种方法用于多列,例如'del r[8] del r[6] del r[2] wtr.writerow(r)'
        • 您可以通过将 (r[0], r[1], r[3], r[4]) 替换为 tuple(r[ii] for ii in range(len(r)) if ii != 2) 之类的内容来节省一些写入更大的 CSV 文件
        • 要在最后一点删除多于 1 列,您不能只使用经典的 delete 'em 向后解决方法吗?
        【解决方案5】:

        你可以直接用just删除列

        del variable_name['year']
        

        【讨论】:

          【解决方案6】:

          使用 Pandas 模块会容易得多。

          import pandas as pd
          f=pd.read_csv("test.csv")
          keep_col = ['day','month','lat','long']
          new_f = f[keep_col]
          new_f.to_csv("newFile.csv", index=False)
          

          这里有一个简短的解释:

          >>>f=pd.read_csv("test.csv")
          >>> f
             day  month  year  lat  long
          0    1      4  2001   45   120
          1    2      4  2003   44   118
          >>> keep_col = ['day','month','lat','long'] 
          >>> f[keep_col]
              day  month  lat  long
          0    1      4   45   120
          1    2      4   44   118
          >>>
          

          【讨论】:

          • 即使您的 csv 在行上的字符串中有换行符,这仍然有效 - 许多其他 linux 命令(如 cut)在行的字段有换行符时无法删除列并保持数据完整性作为 csv 内容的一部分
          • 在我的例子中,整数被转换为浮点数。
          • @Gunarathinam 您可以通过将dtype=str 传递给read_csv 来防止在较新的熊猫版本中发生这种情况
          【解决方案7】:

          使用 dict 来抓取标题,然后循环遍历可以获得您需要的内容。

          import csv
          ct = 0
          cols_i_want = {'cost' : -1, 'date' : -1}
          with open("file1.csv","rb") as source:
              rdr = csv.reader( source )
              with open("result","wb") as result:
                  wtr = csv.writer( result )
                  for row in rdr:
                      if ct == 0:
                        cc = 0
                        for col in row:
                          for ciw in cols_i_want: 
                            if col == ciw:
                              cols_i_want[ciw] = cc
                          cc += 1
                      wtr.writerow( (row[cols_i_want['cost']], row[cols_i_want['date']]) )
                      ct += 1
          

          【讨论】:

            【解决方案8】:

            在我的脑海中,这将在没有任何类型的错误检查或配置任何内容的情况下完成。那就是“留给读者”。

            outFile = open( 'newFile', 'w' )
            for line in open( 'oldFile' ):
               items = line.split( ',' )
               outFile.write( ','.join( items[:2] + items[ 3: ] ) )
            outFile.close()
            

            【讨论】:

              【解决方案9】:

              您可以使用csv 包迭代您的 csv 文件并将您想要的列输出到另一个 csv 文件。

              以下示例未经测试,应说明解决方案:

              import csv
              
              file_name = 'C:\Temp\my_file.csv'
              output_file = 'C:\Temp\new_file.csv'
              csv_file = open(file_name, 'r')
              ## note that the index of the year column is excluded
              column_indices = [0,1,3,4]
              with open(output_file, 'w') as fh:
                  reader = csv.reader(csv_file, delimiter=',')
                  for row in reader:
                     tmp_row = []
                     for col_inx in column_indices:
                         tmp_row.append(row[col_inx])
                     fh.write(','.join(tmp_row))
              

              【讨论】:

              • 放弃tmp_rowjoin,使用csv.writer和一个生成器表达式:for row in reader: wtr.writerow(row[i] for i in column_indices)。它更安全(自动处理引用)、更简洁、更快。
              • 为什么不使用csv 来写作呢?
              【解决方案10】:

              这取决于您如何存储解析后的 CSV,但通常您需要 del 运算符。

              如果你有一个字典数组:

              input = [ {'day':01, 'month':04, 'year':2001, ...}, ... ]
              for E in input: del E['year']
              

              如果你有一个数组数组:

              input = [ [01, 04, 2001, ...],
                        [...],
                        ...
                      ]
              for E in input: del E[2]
              

              【讨论】:

                猜你喜欢
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 2014-03-26
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 2016-05-08
                • 2023-03-05
                相关资源
                最近更新 更多