抓取的主要目标是从非结构化源(通常是网页)中提取结构化数据
ScrapySpider可以以python字典的形式返回提取的数据,这很方便和熟悉
但python dicts缺乏结构,很容易在字段名中输入错误或返回不一致的数据,特别是在有许多spider的大型项目中

若要定义公共输出数据格式,scrapy提供了Item类
Item对象是用于收集抓取的数据的简单容器,它提供了一个类似于字典的API,该API语法方便简洁,用于声明可用字段

很多Scrapy的其他组件会使用Item提供的抓取信息,如
  1) exporters会查看声明的字段来确定要导出的列
  2) 使用Item的字段元数据自定义序列化
  3) trackref会跟踪Item实例以帮助查找内存泄漏

可以为每个字段指明任何类型的元数据
Field 对象对接受的值没有任何限制,因此文档也无法提供所有可用的元数据的键(key)参考列表
Field 对象中保存的每个键可以由多个组件使用,并且只有这些组件知道这个键的存在
可根据需求,定义使用其他的 Field 键。
设置 Field 对象的主要目的就是在一个地方定义好所有的元数据。
一般来说,那些依赖某个字段的组件肯定使用了特定的键(key),必须查看组件相关的文档,查看其用了哪些元数据键(metadata key)

  声明Item

  声明的scrapy项与django模型类似,只是scrapy项要简单得多,因为没有不同字段类型的概念

  Item对象
    class scrapy.item.Item([arg]) #通过指定可选的参数返回一个Item对象
    Item对象复制了标准的dict API,包括constructor,除了标准的dict API,额外提供的只有属性fields
    该对象可以理解为一个字典,该字典包含了所有声明的fields,包括设定过值和没设定过值的fields
    其中,key就是Item对象里定义的fields,values就是Item对象里定义的Field对象

  Field对象
    class scrapy.item.Field([arg])
    Field类实际上就是内置的python字典类型,它不提供额外的属性和方法

import scrapy

class Product(scrapy.Item):
name = scrapy.Field()
price = scrapy.Field()
stock = scrapy.Field()
last_updated = scrapy.Field(serializer=str) #serializer就是字段last_updated的metadata key

  使用Item

    product = Product(name='Desktop PC', price=1000)  #创建Item

    product['name']  #输出:Desktop PC
product['price'] #输出:1000
product['last_updated'] #报错,not set product.get('name') #输出:Desktop PC
product.get('last_updated') #输出:not set
product.get('lala') #报错,没有该key 'name' in product #输出:True,判断name是否设定了值
'last_updated' in product #输出:False,判断last_updated是否设定了值
'last_updated' in product.fields #输出:True,判断last_updated是否被声明
'lala' in product.fields #输出:False,判断lala是否被声明 product['last_updated'] = 'today' #设定值
product['lala'] = 'test' #报错,lala字段没有被声明 product.keys() #输出:['price', 'name']
product.items() #输出:[('price', 1000), ('name', 'Desktop PC')] product2 = Product(product) #复制product item
product3 = product2.copy() #复制product2 item dict(product) #输出:{'price': 1000, 'name': 'Desktop PC'},通过item复制dict
Product({'name': 'Laptop PC', 'price': 1500}) #通过dict创建item

  扩展Item

    class ExtendedProduct(Product):
discount_percent = scrapy.Field(serializer=str) #追加新的字段
discount_expiration_date = scrapy.Field() #追加新的字段
#修改既存字段,保持原来name字段的元数据不变,并追加了serializer metadata key
name = scrapy.Field(Product.fields['name'], serializer=my_serializer)

Item的更多相关文章

  1. 为.NET Core项目定义Item Template

    作为这个星球上最强大的IDE,Visual Studio不仅仅提供了很多原生的特性,更重要的是它是一个可定制的IDE,比如自定义Project Template和Item Template就是一个非常 ...

  2. [转]NopCommerce How to add a menu item into the administration area from a plugin

    本文转自:http://docs.nopcommerce.com/display/nc/How+to+code+my+own+shipping+rate+computation+method Go t ...

  3. ListView中item定位

    ListView 实现定位特定 item 最近在项目中需要使 ListView 能跳转到特定的 item,查阅文档后,发现 ListView 有以下几种方法可供使用: smoothScrollToPo ...

  4. android 在 ListView 的 item 中插入 GridView 仿微信朋友圈图片显示。

    转载请声明出处(http://www.cnblogs.com/linguanh/) 先上张效果图: 1,思路简述 这个肯定是要重写 baseAdapter的了,这里我分了两个数据适配器,一个是自定义的 ...

  5. Listview的Item中有CheckBox、Button等的焦点处理

    ListView的item布局中有CheckBox.Button等会获取焦点的控件会抢走焦点,造成ListView的item点击事件相应不了. 解决方法:控件设置 android:clickable= ...

  6. ListView之多种类型Item

    一.概述 一般而言,listview每个item的样式是一样的,但也有很多应用场景下不同位置的item需要不同的样式. 拿微信举例,前者的代表作是消息列表,而后者的典型则是聊天会话界面. 本文重点介绍 ...

  7. C# 在Repeater 的ItemDataBound 如何转换e.Item.DataItem 的类型

    1.使用DataSet和DataTable绑定数据源时,用 DataRowView view = (DataRowView)e.Item.DataItem; 2.DataReader绑定数据源时,用 ...

  8. zabbix利用api批量添加item,并且批量配置添加graph

    关于zabbix的API见,zabbixAPI 1item批量添加 我是根据我这边的具体情况来做的,本来想在模板里面添加item,但是看了看API不支持,只是支持在host里面添加,所以我先在一个ho ...

  9. RN中listView的每个item等高

    今天写ListView的每个Item的布局的时候发现,当文字太长时被截掉了不能完全显示,检查了很久发现没有设置固定高度都是可伸缩的为什么没有伸缩呢.看了很久才发现每个item是等高的,于是仔细检查才看 ...

  10. ListView只更新某个item

    方案1:针对需要更新的item调用public View getView(int position, View convertView, ViewGroup parent)即可.如: public c ...

随机推荐

  1. SQL 通配符及其使用

    Sql Server中通配符的使用 通配符_ "_"号表示任意单个字符,该符号只能匹配一个字符."_"可以放在查询条件的任意位置,且只能代表一个字符.一个汉字只 ...

  2. 项目Beta冲刺(团队1/7)

    项目Beta冲刺(团队1/7) 团队名称: 云打印 作业要求: 项目Beta冲刺(团队) 作业目标: 完成项目Beta版本 团队队员 队员学号 队员姓名 个人博客地址 备注 221600412 陈宇 ...

  3. 杭电1596find the safest road(spfa)

    find the safest road Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Ot ...

  4. 2016/06/02 网摘记录 svn 服务器端 客户端 安装使用

    http://www.cnblogs.com/xiaobaihome/archive/2012/03/20/2408089.html http://www.cnblogs.com/xiaobaihom ...

  5. Codeforces Round #422 (Div. 2) A. I'm bored with life 暴力

    A. I'm bored with life     Holidays have finished. Thanks to the help of the hacker Leha, Noora mana ...

  6. 仿udhcpd配置文件读取的一段代码

    前段时间看udhcpd的源代码,后来因为没直接应用,也就放弃了.网上有文章udhcpd详解(搜索一下有很多),其中在介绍udhcpd的配置相关代码时,有如下一句话,学习了这段代码后,以后用到需要读配置 ...

  7. linux内存操作--ioremap和mmap

    最近在做视频输出相关的东西,对于预留给framebuffer的内存使用不是很清楚,现在找到一些资料整理一下,以备使用.if (想看使用方法)  goto   使用方法: 对于一个系统来讲,会有很多的外 ...

  8. 【Java】DateUtil(1)

    import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.Calendar; impor ...

  9. [原创]java调用PageOffice生成word

    一.在开发OA办公或与文档相关的Web系统中,难免会遇到动态生成word文档的需求,为了解决工作中遇到导出word文档的需求,前一段时间上网找了一些资料,在word导出这方面有很多工具可以使用,jac ...

  10. codeforces 669C C. Little Artem and Matrix(水题)

    题目链接: C. Little Artem and Matrix time limit per test 2 seconds memory limit per test 256 megabytes i ...