【问题标题】:Ignore the first space in CSV忽略 CSV 中的第一个空格
【发布时间】:2022-01-21 13:15:21
【问题描述】:

我有一个这样的 CSV 文件:

Time              Latitude Longitude
2021-09-12 23:13    44.63     -63.56
2021-09-14 23:13    43.78     -62
2021-09-16 23:14    44.83     -54.6

2021-09-12 23:13Time 列下。

我想用 pandas 打开它。但是第一列有问题。它包含一个空格。如果我使用以下方式打开它:

import pandas as pd
points = pd.read_csv("test.csv", delim_whitespace=True) 

我明白了

Time Latitude Longitude
2021-09-12 23:13 44.630 -63.560
2021-09-14 23:13 43.780 -62.000
2021-09-16 23:14 44.830 -54.600

但我想跳过 CSV 中第一列中的空格(2021-09-12 23:13 应该在 Time 列下),例如:

Time Latitude Longitude
0 2021-09-12 23:13 44.630 -63.560
1 2021-09-14 23:13 43.780 -62.000
2 2021-09-16 23:14 44.830 -54.600

使用pd.read_csv时如何忽略第一个空格?

请不要拘泥于这个 csv 文件。这是跳过(不考虑作为分隔符)第一列中的第一个空格的一般问题。因为大家都知道第一个空格是时间值的一部分,不是分隔符。

【问题讨论】:

  • 列是用空格还是制表符分隔的?如果分隔符是一个制表符,那么您可以使用sep=\t 而不是delim_whitespace=True。那么列值中的空格就无关紧要了。
  • 都是空格。
  • 对于此类字符敏感问题,请包含分隔文件的原始文本。 Markdown 表很漂亮,但隐藏了解决此问题的真正相关信息。

标签: python pandas csv


【解决方案1】:

加载文件后尝试修复列和索引:

import pandas as pd

points = pd.read_csv('test.csv', delim_whitespace=True)

points = points.assign(Time=pd.to_datetime(df.index + ' ' + df['Time'])) \
               .reset_index(drop=True)

输出:

>>> points
                 Time  Latitude  Longitude
0 2021-09-12 23:13:00     44.63     -63.56
1 2021-09-14 23:13:00     43.78     -62.00
2 2021-09-16 23:14:00     44.83     -54.60

【讨论】:

  • 不工作,同样的结果。
  • 如果它不起作用,可能是你关闭得太快了
  • @KadirŞahbaz。我尝试了另一种解决方案,您可以检查一下吗?
  • 我想忽略pd.read_csv。我知道如何在加载 csv 后进行编辑。
  • 如果它看起来像一个分隔符,我认为这是不可能的。
【解决方案2】:

您的数据有两种不同的格式:

  • 您的标题行在'Latitude''Longitude' 之间有一个空格。
  • “数据”行看起来被多个空格分隔。

您可以编辑数据并在 lat 和 long 之间添加第二个空格,或者通过单独提供列标题来欺骗它:

创建文件:

with open("test.csv","w") as f:
    f.write("""Time              Latitude Longitude
2021-09-12 23:13    44.63     -63.56
2021-09-14 23:13    43.78     -62
2021-09-16 23:14    44.83     -54.6""")

解析文件:

import pandas as pd

# ignore files headers, supply own, use multiple spaces as seperator
df = pd.read_csv("test.csv", delimiter = "   ", 
                 header=0, names = ["Time","Latitude","Longitude"])

print (df)

输出:

               Time  Latitude  Longitude
0  2021-09-12 23:13     44.63     -63.56
1  2021-09-14 23:13     43.78     -62.00
2  2021-09-16 23:14     44.83     -54.60

【讨论】:

    【解决方案3】:

    您显示的不是 csv 文件。句号。 Pandas read_csv 确实用途广泛,可以找到允许处理它的解决方法。但它实际上是一个固定宽度的字段文件,应该用pd.read_fwf读取:

    pd.read_fwf(file_name, [(0,16), (16,26), (26, 40)])
    

    直接给出:

                   Time  Latitude  Longitude
    0  2021-09-12 23:13     44.63     -63.56
    1  2021-09-14 23:13     43.78     -62.00
    2  2021-09-16 23:14     44.83     -54.60
    

    根据您的编辑,您只想告诉read_csv 将第一个空格视为非分隔符。我知道没有简单的方法可以做到这一点。困难的方法是读取文件,用不同的字符替换每一行中的第一个空格。然后,您将更改后的文件提交到read_csv,并为第一列使用自定义转换器将特殊字符改回空格:

    with open('test.csv') as fdin, open('test2.csv', 'w') as fdout):
        fdout.write(next(fdin)    # do not process the header line
        for line in fdin:
            fdout.write(line.replace(' ', '_', 1)
    
    df = pd.read_csv('test2.csv', delim_whitespace=True,
                     converters = {'Time': lambda x: x.replace('_', ' ')})
    

    它也给了:

                   Time  Latitude  Longitude
    0  2021-09-12 23:13     44.63     -63.56
    1  2021-09-14 23:13     43.78     -62.00
    2  2021-09-16 23:14     44.83     -54.60
    

    【讨论】:

    • 请不要拘泥于问题中的csv。如果它们之间的空间不同怎么办。例如; Time Latitude Longitude2021-09-12 23:13 44.63 -63.56,我只是希望熊猫不要将第一个空格视为分隔符。
    • @KadirŞahbaz:我知道这没有简单的方法。对于困难的方式,请参阅我的编辑...
    【解决方案4】:

    理想情况下,您应该将前两部分解析为日期时间。通过使用空格作为分隔符,这意味着标题有三列。日期后的空格被视为额外的列。

    一种解决方法是完全跳过标题并提供您自己的列名。 parse_dates 参数可用于告诉 Pandas 将前两列解析为单个组合的日期时间对象。

    例如:

    import pandas as pd
    
    points = pd.read_csv("test.csv", delimiter=" ", 
        skipinitialspace=True, skiprows=1, index_col=None, 
        parse_dates=[[0, 1]], names=["Date", "Time", "Latitude", "Longitude"])
    
    print(points)
    

    应该给你以下数据框:

                Date_Time  Latitude  Longitude
    0 2021-09-12 23:13:00     44.63     -63.56
    1 2021-09-14 23:13:00     43.78     -62.00
    2 2021-09-16 23:14:00     44.83     -54.60
    

    【讨论】:

      【解决方案5】:

      pd.read_csv(..., skipinitialspace=True)^1怎么样?

      skipinitialspacebool,默认为False

      在分隔符后跳过空格。

      Python csv 模块还有一个skip-initial-space 选项^2(不确定Pandas 是自己编的还是包装了这个):

      方言.skipinialspace

      当为 True 时,紧跟在分隔符后面的空格将被忽略。默认为 False。

      即使它明确声明“在分隔符之后”,它也会做明智的事情并忽略任何列/单元格中的前导空格。

      鉴于以下 input.csv,它在所有第 1 列和第 2 列中都有前导空格:

       H1  H2
       A  1
       B  2
       C  3
      

      当我运行这个时:

      import csv
      
      with open('input.csv', newline='') as f:
          reader = csv.reader(f, delimiter=' ', skipinitialspace=True)
          for row in reader:
              print(row)
      

      我明白了:

      ['H1', 'H2']
      ['A', '1']
      ['B', '2']
      ['C', '3']
      

      即使 Pandas 不支持此功能,至少您可以将其用作初步转换并输入到 Pandas 中。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多