【scrapy爬虫】将item内容按照指定顺序输出到csv相应字段中

将item按照指定顺序输出到csv相应字段中

手动反爬虫:原博地址

 知识梳理不易,请尊重劳动成果,文章仅发布在CSDN网站上,在其他网站看到该博文均属于未经作者授权的恶意爬取信息

如若转载,请标明出处,谢谢!

解决:

将返回的Item字典数据类型通过有序字典转换即可(dict → OrderedDIct),只需要修改的代码为pipeline.py文件下的process_item函数内容,修改如下:

from scrapy.exporters import CsvItemExporter
import json  #需要导入的
from collections import OrderedDict #需要导入的

class NewsPipeline(object):

	def __init__(self):
		self.file = open('news_data1.csv', 'wb')
		self.exporter = CsvItemExporter(self.file, encoding = 'gbk')
		self.exporter.start_exporting()

	def close_spider(self,spider):
		self.exporter.finish_exporting()
		self.file.close()
	
	#只用修改这个函数即可
	def process_item(self, item, spider):
		print('默认的字段数据:{}\n'.format(item))
		item = OrderedDict(item)
		item = json.dumps(item,ensure_ascii=False)
		print('调整后的字段数据:{}\n'.format(item))
		self.exporter.export_item(eval(item))
		return item

1. 问题背景

最近通过scrapy生成csv文件的时候,发现系统不按照我指定的item下的字段顺序生成,就显着很烦,网上给出的都是在spiders文件下新建一个文件,然后修改settings里面参数,测试证明这种方式无效

2. 网上无效的方式

就拿百度搜索返回的第一个为例,Scrapy输出CSV指定列顺序

首先先把版本的问题解决了,代码里面头两行都不能执行,如下,.conf和.contrib模块在scrapy的1.7版本就被舍弃了,现在就我个人使用的1.8.3版本的,所以这两行语句就必须要换掉

from scrapy.conf import settings
from scrapy.contrib.exporter import CsvItemExporter

还有一处就是修改一下settings文件中的工程项目名称,换成自己的,这里就拿上一个博客中爬取过程举例

修改之后的两个文件的代码截图如下,其中spiders文件夹下新建的文件内容修改如下
在这里插入图片描述
settings文件内容修改如下
在这里插入图片描述
最后执行程序运行指令,结果输出了目标csv文件,但是打开后字段名称仍然是按照原来的顺序如下:
在这里插入图片描述
这里进行一个猜想:输出的字段顺序可以理解为按照字典键的首字母进行排序输出

那么接下来测试一下crawl自动化模板爬取网易新闻里面的字段,这个项目中的item字段内容较多,看一下默认的输出,可以发现字段也是按照首字母的顺序进行排序的,当前面的字母一致的,对比的字母就会往后移一位,直到比出大小
在这里插入图片描述

3. 亲测有效的方法

既然是字典默认进行排序,然后就可以将字典中的顺序再变回去,因此也就用到了有序字典的方法,只需要修改pipeline.py文件中的内容即可,代码如下

from scrapy.exporters import CsvItemExporter
import json
from collections import OrderedDict

class XmlfeedDemoPipeline(object):

	def __init__(self):
		self.file = open('news.csv', 'wb')
		self.exporter = CsvItemExporter(self.file, encoding = 'gbk')
		self.exporter.start_exporting()

	def close_spider(self,spider):
		self.exporter.finish_exporting()
		self.file.close()

	def process_item(self, item, spider):
		print('默认的字典数据:{}\n'.format(item))
		item = OrderedDict(item)
		item = json.dumps(item, ensure_ascii = False)
		print('调整后的字典数据:{}\n'.format(item))
		self.exporter.export_item(eval(item))
		return item

→ 输出的结果为:(可以看出默认是字段首字母为:d、l、p、t顺序结构,在有序化之后变成了t、l、d、p,既不属于正序也不属于倒序)
在这里插入图片描述
既然经过有序字典转化后正序和倒序都不属于,那么一定是存在某种对应关系,查看爬虫文件后就有了发现:向item中添加数据的顺序就是输出数据的顺序,最后也就是生成csv字段的顺序
在这里插入图片描述
带着上面的发现,然后我把item里面添加数据的顺序打乱之后再运行,看看是不是真的很发现一致,代码和执行结果如下
在这里插入图片描述
甚至还觉得有点巧合,那么就再进一步进行验证,就拿crawl自动化模板爬取网易新闻项目测试,前面已经列出了,没有进行代码修改前运行输出的csv文件,那么接下来就开始动手了

左侧为修改过后的pipeline.py文件,右侧是爬虫模板文件
在这里插入图片描述
cmd运行爬虫指令,输出的结果界面及csv文件如下,最后可以看出csv文件中的字段信息是和调整后的信息一致,而默认的输出还是按照首字母顺序进行输出的
在这里插入图片描述
至此,就验证了最开始的猜想:默认输出的字段顺序可以理解为按照字典键的首字母进行排序输出,当前面的字母一致的,对比的字母就会往后移一位,直到比出大小

经过有序字典转化之后:向item中添加数据的顺序就是输出数据的顺序,最后也就是生成csv字段的顺序

猜你喜欢

转载自blog.csdn.net/lys_828/article/details/106908518