最近有些需求是要用到 Excel;根据我的喜好,肯定是数据往大了整!
就是要头发更少。。。
xls是微软私有的文件格式标准,以二进制方式直接保存文件,最大支持行数65536行、列数256列,而xlsx是基于Office Open XML标准的格式,实质是以zip压缩包保存文件,只是扩展名使用了xlsx,可以用解压软件查看压缩包内容,最大支持1048576行、16384列。
因为我手上的需求 只用到xlsx格式,所以 这期分享都是xlsx格式相关
此外,后面所有代码 只是 读取或写入数据,完全不关心单元格的style;
需求A:
Excel内容 有2种: 1.单个sheet 20w内数据(少) 2.多个sheet 每个sheet 5w内的数据 (多)
过程:Excel上传后,系统进行对账操作,给出对账结果;
故我看 是3个步骤:准备数据生成Excel (上传到系统);我解析此Excel,拿此数据 和表的记录做对账;将我的结果 和 系统的结果做对比;
需求B:
Excel内容:单个sheet 不超过最大限制(100w)
过程:Excel上传后,系统检查内容,无误存表;
故我看 是2个步骤:准备数据生成Excel (上传到系统);我解析此Excel,连库读取表里数据,对比,保证每条记录的准确性、完整性
一般我造的数据量大概100w,Excel大概60M,若只读取一次,我就不care实际花的时间了。若多次读取这样的Excel,就要考虑 读取Excel的时间了。
我找了些资料,最后确定的思路:转Excel为CSV文件。通过脚本,把Excel读取的数据 存入CSV文件【每个Excel的内容 我改动地可能性近乎为0,因为再生成一份 也不是很难的事儿 = = 】。
实际跑脚本时,会先找寻是否有对应的CSV文件,有 -> 会读取对应的CSV文件,拿到数据;没有 ->先读取Excel数据,新生成CSV文件,再读取对应的CSV文件,拿到数据。再去下一步操作。
需求B: 单一个sheet
def get_excel_data(self, file):
import xlrd
all_data = list()
Log.info('开始获取Excel的数据。。。')
book = xlrd.open_workbook(file)
one_sheet = book.sheet_by_index(0)
Log.info('sheet :{}'.format(book.sheet_names()))
hang = range(0, one_sheet.nrows)
for h in hang:
ele = one_sheet.row_values(h)
all_data.append((ele[0], ele[1], ele[2], ele[9], ele[10]))
# all_data.append(ele)
# all_data.append(tuple(ele))
Log.info(all_data) # 包含 表头
all_data.append() 写了3行,其实是 看实际要用的字段 和 需要的格式;
需求A:多个sheet
def get_excel_data_sssss(self, file):
import xlrd
Log.info('开始获取Excel的数据。。。')
book = xlrd.open_workbook(file)
all_sheets = book.sheets()
all_data = list()
for s in all_sheets:
s_index = all_sheets.index(s)
sheet = book.sheet_by_name(s.name)
Log.info('sheet:{}, {}'.format(sheet, s.name))
if s_index == 0:
hang = range(0, sheet.nrows)
Log.info('取值:{}'.format(hang))
else:
# 表头内容 是一样的
hang = range(1, sheet.nrows)
Log.info('取值:{}'.format(hang))
for c in hang:
if file.find('zyooooxie_csdn') != -1:
ele = sheet.row_values(c)
all_data.append((ele[1], ele[3], ele[8], ele[9], ele[10], ele[-1]))
else:
ele = sheet.row_values(c)
all_data.append((ele[8], ele[3], ele[11], ele[0]))
Log.info('当前sheet 读取完成')
Log.info('Excel文档 读取完毕')
Log.info(all_data)
def insert_excel_new(self, all_data, header):
"""
Excel 写数据
:param all_data: 是个list,里面的元素也是list (此list是每张sheet内容的)
:param header: 表头
:return:
"""
import xlsxwriter
cur_time = time.strftime("_%Y%m%d_%H%M%S")
w = r'D:\work\gys\test_' + cur_time + '.xlsx'
workbook = xlsxwriter.Workbook(w, {'constant_memory': True})
for abc in range(len(all_data)):
sheet = workbook.add_worksheet(str(abc))
all_data[abc].insert(0, header)
Log.info('sheet {} 准备新建'.format(abc))
for i in range(1, len(all_data[abc]) + 1):
rc = ''.join(['A', str(i)])
sheet.write_row(rc, data=all_data[abc][i - 1])
Log.info('当前sheet 已生成')
workbook.close()
(利用 xlutils 复制后 再保存的方式,我很不信任)
Excel_name = ‘test_20200516_150921.xlsx’
def addExcelData(self, file, all_data):
"""
在某个文件现有sheet('test_zyooooxie')再继续添加内容
:param file: 文件
:param all_data: [ele1, ele2, ele3]
:return:
"""
import openpyxl
import os
Log.info('此Excel add')
wb = openpyxl.load_workbook(file)
# sheet_names = wb.get_sheet_names()
# wb_sheet = wb.get_sheet_by_name(sheet_names[0])
wb_sheet = wb.get_sheet_by_name('csdn_zyooooxie')
for ABC in range(len(all_data)):
wb_sheet.append(all_data[ABC])
new_time = time.strftime("_%Y%m%d_%H%M%S")
search_result = re.search(r'_2020\d{4}_([01]\d|2[0-4])([0-5]\d)([0-5]\d).xlsx$', os.path.basename(file))
new_file = os.path.basename(file)[0:search_result.start()] + new_time + '.xlsx'
w = ''.join([os.path.dirname(file), '\\', new_file])
wb.save(w)
其实这一篇分享只是讲我现在是咋做的,其他我爬的坑 就放在第二篇了。
交流技术 欢迎+QQ 153132336 zy
个人博客 https://blog.csdn.net/zyooooxie