openpyxl报错求助
本帖最后由 极客4321 于 2022-1-29 12:04 编辑从网上爬取几百页网页信息(数据量可能有点大)存入excel表中,可以运行一段时间,也保存了十几页的网页内容。
但是运行着就会报:PermissionError: Permission denied: '***.xlsx'的错误。
从网上也搜索了,有说是openpyxl没有自动回收内存的,我也弄手动回收了(应该)。
常规写法报错,我还搞了openpyxl的“只写模式”,也不能解决问题
还有说是因为打开文件后没有关闭excel导致的,但是为什么程序是在保存了几个.xlsx文件后才报错的?
而且每一次运行后保存的.xlsx文件的数量是不一样的,即不是在同一个地方报错。
我是爬取网页的一个栏目。并且把这个栏目当成我的execl文件名,这个栏目的前22页都能正常保存到execl里面
报错后程序生成的execl里面也有前22页的内容
报错代码:http://img7.ng8855.com/ima/2022/01/29/j0q8hy.png
下面是我保存execl的代码,麻烦各位大佬看看写法有哪些问题?
def save_excel(i,title,name,star,count,sold,min,max):
if i != 0:
wb = openpyxl.load_workbook('./{}.xlsx'.format(title))
ws = wb.active
long = len(name)
for i in range(long):
ws.append(), star, count, sold,
str(min / 10000) + '~' + str(max / 10000)])
wb.save('{}.xlsx'.format(title))
wb.close()
del wb, ws
gc.collect()
else:
wb = openpyxl.Workbook(write_only = True)
ws = wb.create_sheet()
ws.append(['商品名称','评分','评价数量','销量','售价'])
col = ws.column_dimensions['A']
col.width = 50
col = ws.column_dimensions['B']
col.width = 15
col = ws.column_dimensions['C']
col.width = 15
col = ws.column_dimensions['D']
col.width = 15
col = ws.column_dimensions['E']
col.width = 25
long = len(name)
for i in range(long):
ws.append(),star,count,sold,str(min/10000)+'~'+str(max/10000)])
wb.save('{}.xlsx'.format(title))
wb.close()
del wb, ws
gc.collect()
方便贴一下完整的报错信息吗? 本帖最后由 hrp 于 2022-1-29 11:52 编辑
新建xlsx前增加一个环节,验证要做文件名的字符串是否符合系统的命名规则(是否全部都是可用做文件名的字符),以下字符在windows上不能用做文件名:< > / \ | : " * ? isdkz 发表于 2022-1-29 11:45
方便贴一下完整的报错信息吗?
http://img7.ng8855.com/ima/2022/01/29/j0q8hy.png 极客4321 发表于 2022-1-29 11:50
你那个Permission denied的文件在你的操作系统里面确实能创建成功的吗?你试试手动建一个这样的文件看看能不能成功 hrp 发表于 2022-1-29 11:47
新建xlsx前增加一个环节,验证要做文件名的字符串是否符合系统的命名规则(是否全部都是可用做文件名的字符)
应该不是这个问题,因为我是把网页的栏目名称当成文件名,一个栏目比如说有30页,前20页它都能正常保存下来,21页就报错了
极客4321 发表于 2022-1-29 11:54
应该不是这个问题,因为我是把网页的栏目名称当成文件名,一个栏目比如说有30页,前20页它都能正常保存下 ...
这个原因有点多,有可能是爬取的页数多了爬到不数据,返回了特殊字符,导致用特殊字符做文件名创建文件失败,都是有可能的,你可以先调试一下看看第21返回了什么。不管怎么说,创建文件前验证文件名的合法性都是有必要的,文件名不合法就得给他指定一个新文件名。 isdkz 发表于 2022-1-29 11:54
你那个Permission denied的文件在你的操作系统里面确实能创建成功的吗?你试试手动建一个这样的文件看看 ...
可以的,虽然报错了但程序已经把前22页的内容保存在里面了
本帖最后由 isdkz 于 2022-1-29 12:08 编辑
或者是你要保存的那个表格文件你用其它的excel软件打开了,比如wps之类的,这些软件获取到文件句柄就会抓着不放直到软件关闭的 hrp 发表于 2022-1-29 11:59
这个原因有点多,有可能是爬取的页数多了爬到不数据,返回了特殊字符,导致用特殊字符做文件名创建文件失 ...
文件名这个是没问题的,因为title是我自己定死的
不过是否爬取多了返回的数据不对得去看看 isdkz 发表于 2022-1-29 12:06
或者是你要保存的那个表格文件你用其它的excel软件打开了,比如wps之类的,这些软件获取到文件句柄就会抓着 ...
我电脑都没wps{:5_100:}
我确定在爬取过程中没有动过电脑打开文件
我就怀疑是不是我的代码里面有问题,比如写入第20页的内容execl还没有关闭,而第21页的时候又要打开execl,造成了资源竞争{:10_266:} 极客4321 发表于 2022-1-29 12:17
我电脑都没wps
我确定在爬取过程中没有动过电脑打开文件
确实有可能,sleep等一会看看有没有效果 本帖最后由 isdkz 于 2022-1-29 12:41 编辑
极客4321 发表于 2022-1-29 12:17
我电脑都没wps
我确定在爬取过程中没有动过电脑打开文件
这个不会,openpyxl会自动释放资源的,只能是其它软件跟它竞争,
你可以在命令提示符自己测试一下,打开多个进程用openpyxl同时对同一个文件进行操作,
你也可以打开openpyxl的源码看一下,凡是有写操作的地方它都自动关闭文件了 翼是孤独 发表于 2022-1-29 12:25
确实有可能,sleep等一会看看有没有效果
sleep了没有效果
难道是有本地软件在读取我的execl{:10_277:} 极客4321 发表于 2022-1-29 13:40
sleep了没有效果
难道是有本地软件在读取我的execl
找到一个测试文件是否被占用的代码,写23页之前测试一下,看看是不是被占用了
>>> import win32file
>>> def is_used(file_name):
try:
vHandle = win32file.CreateFile(file_name, win32file.GENERIC_READ, 0, None, win32file.OPEN_EXISTING, win32file.FILE_ATTRIBUTE_NORMAL, None)
return int(vHandle) == win32file.INVALID_HANDLE_VALUE
except:
return True
finally:
try:
win32file.CloseHandle(vHandle)
except:
pass
>>> fn = r'D:\temp\csdn\t.py'
>>> is_used(fn)
False
>>> fp = open(fn, 'a+')
>>> is_used(fn)
True
>>> fp.close()
>>> is_used(fn)
False
翼是孤独 发表于 2022-1-29 16:06
找到一个测试文件是否被占用的代码,写23页之前测试一下,看看是不是被占用了
谢谢大佬,已经解决了。
是因为上面我怀疑的资源抢占,由于我电脑性能拉跨,用sleep(10)就不会报错了 极客4321 发表于 2022-1-29 19:41
谢谢大佬,已经解决了。
是因为上面我怀疑的资源抢占,由于我电脑性能拉跨,用sleep(10)就不会报错了
查到到底是什么占用了没{:5_106:} 翼是孤独 发表于 2022-1-29 23:28
查到到底是什么占用了没
有点好奇
页:
[1]