【问题标题】:Merge two dataframe in pandas合并熊猫中的两个数据框
【发布时间】:2017-09-02 07:41:12
【问题描述】:

我正在使用以下代码合并两个 csv(数据框):

import pandas as pd
a = pd.read_csv(file1,dtype={'student_id': str})
df = pd.read_csv(file2)
c=pd.merge(a,df,on='test_id',how='left')
c.to_csv('test1.csv', index=False)

我有以下 CSV 文件

文件1:

test_id, student_id
1, 01990
2, 02300
3, 05555

文件2:

test_id, result
1, pass
3, fail

合并后

test_id, student_id , result
1, 1990, pass
2, 2300,
3, 5555, fail

如果您注意到 student_id 在开头附加了 0 并且它应该被视为文本,但在合并并使用 to_csv 函数后,它会将其转换为数字并删除前导 0。

即使在 to_csv 之后,我如何才能将列保持为“文本”?

我认为它的 to_csv 函数可以再次保存为数字 在读取 csv 时添加了 dtype={'student_id': str} .. 但在将其保存为 to_csv .. 它再次将其转换为数字

【问题讨论】:

    标签: python csv pandas merge


    【解决方案1】:
    a = pd.read_csv(file1, dtype={'test_id': object})
    df = pd.read_csv(file2, dtype={'test_id': object})
    

    ================================================ ===============

    In[28]: pd.merge(a, b, on='test_id', how='left')
    Out[28]: 
      test_id   student_id  result
    0      01         1990    pass
    1      02         2300     NaN
    2     003         5555    fail
    

    【讨论】:

      【解决方案2】:

      它不是在merge 上删除前导零,而是在read_csv 上删除它。您可以通过在导入时指定该列是字符串来解决此问题:

      a = pd.read_csv('file1.csv', dtype={'student_id': str}, skipinitialspace=True)
      

      重要的部分是dtype 参数。您是在告诉 pandas 将此列作为字符串导入。 skipinitialspace参数设置为True,因为列标题是用空格定义的,所以我们去掉它:

      test_id, student_id
              ^ The student_id starts here, at the space
      

      最终代码如下所示:

      a = pd.read_csv('file1.csv', dtype={'student_id': str}, skipinitialspace=True)
      df = pd.read_csv('file2.csv')
      results = a.merge(df, how='left', on='test_id')
      

      results 数据框如下所示:

          test_id     student_id  result
      0   1           01990       pass
      1   2           02300       NaN
      2   3           05555       fail
      

      那么当你运行to_csv 你的结果应该是:

      test_id,student_id, result
      1,01990, pass
      2,02300,
      3,05555, fail
      

      【讨论】:

      • 我尝试了您的解决方案。添加了“a = pd.read_csv('file1.csv', dtype={'student_id': str})”。但是在将其保存为 c.to_csv('test1.csv', index=False).. 如果你打开这个 test1.csv 文件......你会看到前导零消失了。所以我认为它的 to_csv 函数删除了前导零。并将其视为数字
      • @MadhuraMhatre,你确定吗?在文本编辑器中打开 CSV 文件,而不是在 Excel 中。 Excel 在骗你。 Excel displayText Display。请记住,CSV 不是 Excel 文档。
      【解决方案3】:

      使用join 的解决方案,首先需要read_csv 和参数dtypestudent_id 转换为string 并通过skipinitialspace 删除空格:

      df1 = pd.read_csv(file1, dtype={'student_id': str}, skipinitialspace=True)
      df2 = pd.read_csv(file2, skipinitialspace=True)
      
      df = df1.join(df2.set_index('test_id'), on='test_id')
      print (df)
         test_id student_id  result
      0        1      01990    pass
      1        2      02300     NaN
      2        3      05555    fail
      

      【讨论】:

      • 尝试了您的解决方案。添加了“a = pd.read_csv('file1.csv', dtype={'student_id': str})”。但是在将其保存为 c.to_csv('test1.csv', index=False).. 如果你打开这个 test1.csv 文件......你会看到前导零消失了。所以我认为它的 to_csv 函数删除了前导零。并将其视为数字
      • 如果使用dtype={'student_id': str} 则强制列为字符串类型。我总是测试to_csv,它工作得很好。你的熊猫是什么版本的?
      • @jezrael,我怀疑他们正在 Excel 中查看 CSV。 Excel 在前导零的问题上向他们撒谎。在我的回答中,我在comment 上提供了一个快速截图。
      • 嗯。我总是用文本编辑器测试,也许这可能是个问题。
      【解决方案4】:

      警告请使用mergejoin。提供此答案是为了让您了解 pandas 为您提供的灵活性以及有多少种不同的方法可以回答同一个问题。

      a = pd.read_csv('file1.csv', converters=dict(student_id=str), skipinitialspace=True)
      df = pd.read_csv('file2.csv')
      results = pd.concat(
          [d.set_index('test_id') for d in [a, df]],
          axis=1, join='outer'
      ).reset_index()
      

      【讨论】:

      • 呸,我觉得这太复杂了,你怎么看?
      • 教育...对完成工作的多种方式的看法。
      猜你喜欢
      • 2017-06-11
      • 2016-01-01
      • 2021-05-30
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多