2016-06-10 57 views
1

這裏我想比較兩個excel文件。 Server_report有42列,Email_report有19列(其中5列與server_report完全不匹配)。每列中有14列匹配,但標題不同。當我打開這兩個文件時,我會對三列進行排序,以便將數據排列爲「交貨」,「選擇數量」,「批次」(按server_report排序)和「交貨」,「採購數量」,「批量選擇」(根據email_report排序)。使用Pandas DataFrames比較兩個不同頭文件但使用相同行數據的Excel文件

我需要的是將排序後的email_report與server_report進行比較(每個文件具有相同的行數並且可以在'Delivery'列進行索引)。如果server_report上存在「缺失」信息,則需要使用從email_report獲取的信息來填充該信息。

之後,需要生成兩個新文件。

  1. 一個新的server_report,其中包含所有原始42列,並且具有來自email_report的更改。

  2. 一個包含比較過程中所做更改的新文件。

我的問題在這裏是這篇文章的標題。如何比較具有不同列/標題的兩個文件(不是所有可以映射到另一個的文件)

+0

這兩個報告是否有相同的行數?兩個報告中通用的每行是否有唯一的ID? – andrew

+0

這應該是每個工作表具有相同數量的行的情況。每個工作表共享第一個A列的完全相同的標題名稱(Index?)和編號(數據)。 –

回答

0

在此解決方案中,我假設兩個報告具有相同數量的行和索引。

import copy 
import pandas as pd 
import numpy as np 

# Example reports 
email_report = pd.DataFrame({'a':np.arange(6), 'b':np.arange(6), 'c':['A', 'B', 

email_report 

>>> 
'C', 'D', 'E', 'F'], 'extra_col':np.zeros(6)}) 
    a b c extra_col 
0 0 0 A  0.0 
1 1 1 B  0.0 
2 2 2 C  0.0 
3 3 3 D  0.0 
4 4 4 E  0.0 
5 5 5 F  0.0 

server_report = pd.DataFrame({'d':np.append(np.random.random_integers(0,5,5),5), 
    'e':np.append(np.random.random_integers(0, 5, 5),5), 
    'f':['A', 'B', 'C', 'D', 'E', 'F'], 
    'g':['a', 'b', 'c', 'd', 'e', 'f']}) 

server_report 
>>> 
    d e f g 
0 0 2 A a 
1 1 0 B b 
2 3 3 C c 
3 1 3 D d 
4 5 4 E e 
5 5 5 F f 

# Identify the columns of interest in both reports and map between them 
col_map = {'d':'a', 'e':'b', 'f':'c'} 
server_report_cols = ['d', 'e', 'f'] 
email_report_cols = [col_map[c] for c in server_report_cols] 

現在我們運行差異..

# Run the diff report 
def report_diff(x): 
    return x[0] if x[0] == x[1] else '{} ---> {}'.format(*x) 

def make_diff(df1, df2, df1_cols, df2_cols): 
    """ 
    I am assuming that df1_cols and df2_cols are both sorted in the same order. 
    """ 
    temp = pd.concat([df1[df1_cols], df2[df2_cols]], axis=1) 
    diff_rows = [] 
    for row in temp.iterrows(): 
     diff_rows.append([report_diff((row[1][x[0]], row[1][x[1]])) for x in zip(df1_cols, df2_cols)]) 
    diff = copy.deepcopy(df2) 
    diff[df2_cols] = pd.DataFrame(diff_rows, columns=df2_cols) 
    return diff 

diff = make_diff(email_report, server_report, email_report_cols, server_report_cols) 
print diff 
>>> 
      d   e f g 
0 0 ---> 2 0 ---> 5 A a 
1 1 ---> 0 1 ---> 4 B b 
2 2 ---> 1 2 ---> 0 C c 
3 3 ---> 0 3 ---> 2 D d 
4 4 ---> 5   4 E e 
5   5   5 F f 

並創建兩個輸出文件。

# Get a boolean series indicating which rows will be changed 
change_check = ~(email_report[email_report_cols] == server_report[server_report_cols]. 
    rename(columns=col_map)).all(axis=1) 

# Output_1: Corrected "server report" 
server_report[server_report_cols] = email_report[email_report_cols] # Overwrite the server report 
server_report.to_excel('my-diff-sap.xlsx',index=False) 

# Output_2: Record of corrections using the headers from the server report 
diff[change_check].to_excel('changed_rows.xlsx', index=False) 

print server_report 
>>> 
    d e f g 
0 0 0 A a 
1 1 1 B b 
2 2 2 C c 
3 3 3 D d 
4 4 4 E e 
5 5 5 F f 

print diff[change_check] 
>>> 
      d   e f g 
0 0 ---> 2 0 ---> 1 A a 
1 1 ---> 0 1 ---> 5 B b 
2 2 ---> 0   2 C c 
3 3 ---> 5 3 ---> 4 D d 
4 4 ---> 1   4 E e 
相關問題