python解决excel工作薄合并处理(openpyxl处理excel2010以上版本)

原文链接: http://www.cnblogs.com/pinpin/p/10345765.html

前段时间使用xlrd、xlwt对文件进行处理(https://www.cnblogs.com/pinpin/p/10287491.html),但是只能处理excel2010以下版本,所以又写了个处理excel2010以上版本的,所用到的库openpyxl

image

上代码吧,执行结果不写了:

  1 import openpyxl
  2 import pandas as pd
  3 from openpyxl.styles import NamedStyle, Font, Border, Side, Alignment
  4 
  5 highlight_a = NamedStyle(name="highlight_a")  # 首行格式
  6 highlight_a = NamedStyle()  # 首行格式
  7 highlight_a.align = Alignment(horizontal='center', vertical='center')
  8 highlight_a.font = Font(size=18, bold=True)
  9 
 10 highlight_b = NamedStyle(name="highlight_b")  #
 11 highlight_b.font = Font(size=10, bold=True)
 12 
 13 highlight_c = NamedStyle(name="highlight_c")  # 数据列标题格式
 14 highlight_c.font = Font(size=10, bold=True)
 15 bd3 = Side(style='thin',
 16            color="000000")  # style:边框线的风格{'dotted','slantDashDot','dashDot','hair','mediumDashDot',5'dashed','mediumDashed','thick','dashDotDot','medium','double','thin','mediumDashDotDot'}
 17 highlight_c.border = Border(left=bd3, top=bd3, right=bd3, bottom=bd3)
 18 
 19 highlight_d = NamedStyle(name="highlight_d")  # 数据格式
 20 highlight_d.font = Font(size=10)
 21 # highlight.fill = PatternFill("solid", fgColor="DDDDDD")#背景填充
 22 bd4 = Side(style='thin',
 23            color="000000")  # style:边框线的风格{'dotted','slantDashDot','dashDot','hair','mediumDashDot',5'dashed','mediumDashed','thick','dashDotDot','medium','double','thin','mediumDashDotDot'}
 24 highlight_d.border = Border(left=bd4, top=bd4, right=bd4, bottom=bd4)
 25 
 26 
 27 # 时间戳转换为时间
 28 def date(stamp):
 29     delta = pd.Timedelta(str(stamp) + 'D')
 30     real_time = pd.to_datetime('1899-12-30', format="%Y-%m-%d",errors='coerce') + delta  # “1899-12-30”这个是设定好的,也可以自己计算,相当与对比点
 31     return str(real_time.date())
 32 
 33 
 34 list1 = []  # 列表各工作薄相同的头部
 35 list2 = []  # 列表各工作薄的数据部分
 36 list3 = [None, None, None, None, None, None, None, None, None, None, None, None, None]  # 去除列表各工作薄的尾部
 37 list5 = ['审批人:', None, None, None, None, None, None, None, None, None, None, '制单:', ' ']  # 去除列表各工作薄的尾部
 38 list_temp = []  # 将日期列的数据都放如列表进行单独处理
 39 list_column_len = []  # 列表列的宽度
 40 
 41 
 42 def list_base(filename, *args):  # fix_row,com_col,unit_col,out_col,sum_col:6,3,7,8,9,10固定表头行,数据比较列,单位数据列,易玲数据列,共下单列
 43 #def list_base(filename, fix_row, com_col, unit_col, out_col, sum_col,date_col):  # fix_row,com_col,unit_col,out_col,sum_col:6,3,7,8,9,10固定表头行,数据比较列,单位数据列,易玲数据列,共下单列
 44     excel = openpyxl.load_workbook(filename, data_only=True)
 45     sheets = excel.get_sheet_names()
 46     for row in excel[sheets[0]].iter_rows(min_row=1, max_row=args[0]):  # 如果获取所有行列,可直接使用iter.rows()
 47         row1 = ([cell.value for cell in row])
 48         list1.append(row1)
 49     for j in sheets:
 50         for row in excel[j].iter_rows(min_row=args[0] + 1):  # 如果获取所有行列,可直接使用iter.rows()
 51             row2 = ([cell.value for cell in row])
 52             if row2 == list3 or row2 == list5:
 53                 break
 54             list2.append(row2)
 55 
 56     # 将列表2中某项相同的值中的值进行相加:我这里是用规格型号列号计算相同的,并将数量列进行相加
 57     for m in range(len(list2)):  # 将领料为空的置为0,如果有这列中有空值,则将该数据置为0,其他两列是必填的未作此设置
 58         if list2[m][args[3]-1] is None:
 59             list2[m][args[3]-1] = 0
 60     for m in range(len(list2)):
 61         for n in range(len(list2) - 1, m, -1):
 62             if list2[m][args[1]-1] == list2[n][args[1]-1]:
 63                 list2[m][args[2]-1] += list2[n][args[2]-1]
 64                 list2[m][args[3]-1] += list2[n][args[3]-1]
 65                 list2[m][args[4]-1] += list2[n][args[4]-1]
 66                 list2.remove(list2[n])
 67 
 68     # 日期处理,由于日期列变为时间戳,调用了函数date做转换
 69     for x in range(len(list2)):
 70         list_temp.append(list2[x][args[5]-1])
 71         if not (list2[x][args[5]-1] is None):
 72             list2[x][args[5]-1] = date(list2[x][args[5]-1])
 73     return list1, list2
 74 
 75 def new_sheet(filename,new_filename,*args):
 76     list_base(filename, *args)
 77     excel = openpyxl.load_workbook(filename, data_only=True)
 78     mysheet = excel.create_sheet('汇总', 0)  # 在打开的表格的第一位置新建工作薄,并取名称为“汇总”
 79     for i in range(len(list1)):
 80         for j in range(len(list1[i])):
 81             mysheet.cell(row=i + 1, column=j + 1, value=list1[i][j])
 82             if i == 0:
 83                 mysheet[mysheet.cell(row=i + 1, column=j + 1).coordinate].style = highlight_a
 84             elif i < len(list1) - 1:
 85                 mysheet[mysheet.cell(row=i + 2, column=j + 1).coordinate].style = highlight_b
 86             else:
 87                 mysheet[mysheet.cell(row=i + 1, column=j + 1).coordinate].style = highlight_c
 88 
 89     mysheet.merge_cells('A1:M1')  # 单元格合并
 90     mysheet['A1'] = "标准BOM"
 91     mysheet['A1'].alignment = highlight_a.align
 92     mysheet['I4'] = ""
 93 
 94     for x in range(len(list2)):
 95         list2[x][0] = x + 1
 96         for y in range(len(list2[x])):
 97             mysheet.cell(row=x + 7, column=y + 1, value=list2[x][y])
 98             mysheet[mysheet.cell(row=x + 7, column=y + 1).coordinate].style = highlight_d
 99 
100     # 表格单元格宽高设置
101     rowHeights = [mysheet.row_dimensions[i + 1].height for i in range(mysheet.max_row)]  # 计算行数
102     rowHeights = [22 if rh is None else rh for rh in rowHeights]  # 生成行数对应的高列表
103     for i in range(len(rowHeights)):  # 具体行高赋值
104         mysheet.row_dimensions[i].height = rowHeights[i]
105 
106     for row in mysheet.columns:  # 生成列的宽度列表,宽度为列单元格最大字符长度+5
107         list_column_len.append(max([len(str(cell.value)) for cell in row[5:]]) + 5)
108     for z in range(len(list_column_len)):  # 具体列宽赋值
109         mysheet.column_dimensions[mysheet.cell(row=6, column=z + 1).column].width = list_column_len[z]
110     excel.save(new_filename)  # 保存表格
111 
112 if __name__ == '__main__':
113     import tkinter
114     # new_filename = 'new_openfile1.xlsx'
115     # filename = '原始.xlsx'
116     # fix_row, com_col, unit_col, out_col, sum_col, date_col = 6, 3, 7, 8, 9, 10
117     # new_sheet(new_filename)
118     root = tkinter.Tk()
119     root.geometry("350x260")
120     root.title('表格合并处理')
121     test_content = ['原excel文件', '新excel文件地址加名称', '表格头部相同的行数', '对比的列', '求和计算列1', '求和计算列2', '求和计算列3','日期列']
122     v_list = []  #获取输入的结果列表
123     v = []  #添加的tkinter.StringVar()
124     args = [] #传入的不定参数
125     for i in range(len(test_content)):
126         tkinter.Label(root, text=test_content[i]).grid(row=i, column=0)
127         v.append(tkinter.StringVar())
128         ent = tkinter.Entry(root, textvariable=v[i])
129         ent.grid(row=i, column=2)
130     print(len(v))
131 
132     def show():
133         for i in range(len(test_content)):
134             v_list.append(v[i].get())
135         filename,new_filename,fix_row, com_col, unit_col, out_col, sum_col, date_col = v_list
136         args = int(fix_row), int(com_col), int(unit_col), int(out_col), int(sum_col), int(date_col)
137         print(fix_row, com_col, unit_col, out_col, sum_col, date_col)
138         print(type(fix_row), type(com_col), type(unit_col), type(out_col), type(sum_col), type(date_col))
139         new_sheet(filename,new_filename,*args)
140 
141     tkinter.Button(root, text='获取信息', command=show).grid(row=8, column=0)
142     tkinter.Button(root, text='取消', command=root.quit).grid(row=8, column=1)
143     root.mainloop()
144 

转载于:https://www.cnblogs.com/pinpin/p/10345765.html

猜你喜欢

转载自blog.csdn.net/weixin_30735391/article/details/94790153