scrapy 从一个页面产生多个项目

laik7k3q  于 2022-11-09  发布在  其他
关注(0)|答案(2)|浏览(166)

我需要从一个页面产生多个项目。项目有一个字段不同。我收集一个项目,然后在循环中创建新项目,即:

for i in new_fields:
    new_item = item
    new_item["new_field"] = i
    yield new_item

但是scrapy只返回n个相同的行,其中n是len(new_fields)。
我做错了什么?

ncecgwcz

ncecgwcz1#

我建议在这种情况下使用项目加载器。你可以在文档页面https://docs.scrapy.org/en/latest/topics/loaders.html上阅读更多关于它的信息。
一般来说,它看起来像这样:

from scrapy.loader import ItemLoader
from myproject.items import Product

def parse(self, response):
    for i in new_fields:
        l = ItemLoader(item=Product(), response=response)
        #  you can add data using CSS, XPath or values
        l.add_xpath('name', '//div[@class="product_name"]')
        l.add_css('stock', 'p#stock')
        l.add_value('last_updated', 'today')
        yield l.load_item()
ifsvaxew

ifsvaxew2#

您的问题是,语句new_item = item不会创建item的副本。newitem将仅是对item的引用,因此当您更新newitem["new_field"]时,您也在更新item["new_field"]
因此,产出的项目始终相同,但每次产出时其状态都不同。因此,以下代码应打印new_field的不同值:

for item in sub_that_yields():
    print(item["new_field"])

另一方面,下面的代码将只打印一个值:

new_items = list(sub_that_yields())
for item in new_items:
    print(item["new_field"])

在第二个例子中,new_items将是同一个项目的n个示例的列表(因为sub总是产生相同的项目,如前所述)。因此,随着对该项目的每次更新,列表中的所有项目都会发生变化。
解决这个问题最简单的方法是把new_item变成item的真实的副本,具体的工作方式取决于item是什么,可能只需要写new_item = item.copy()就可以了,也可能需要使用python的copy模块中的copydeepcopy

相关问题