Полоса\n\t\r в scrapy
Я пытаюсь вырезать символы \r\n\t с помощью scrapy spider, создавая json файл.
У меня есть объект описания, который заполнен новыми строками, и он не выполняет то, что я хочу: сопоставление каждого описания с заголовком.
Я попытался с картой (unicode.strip()), но на самом деле это не работает. Являясь новатором для исследования, я не знаю, есть ли еще один более простой способ или как работает unicode карты.
Это мой код:
def parse(self, response):
for sel in response.xpath('//div[@class="d-grid-main"]'):
item = xItem()
item['TITLE'] = sel.xpath('xpath').extract()
item['DESCRIPTION'] = map(unicode.strip, sel.xpath('//p[@class="class-name"]/text()').extract())
Я попробовал также:
item['DESCRIPTION'] = str(sel.xpath('//p[@class="class-name"]/text()').extract()).strip()
Но это вызвало ошибку. Какой лучший способ?
Ответы
Ответ 1
unicode.strip
использует только пробельные символы в начале и конце строк
Верните копию строки с удалением ведущих и завершающих символов.
не с \n
, \r
, или \t
в середине.
Вы можете использовать собственный метод для удаления этих символов внутри строки (используя модуль регулярных выражений) или даже использовать XPath normalize-space()
возвращает строку аргумента с пробелом, нормализованным путем удаления начального и конечного пробелов и замены последовательностей пробельных символов на единое пространство.
Пример сеанса оболочки python:
>>> text='''<html>
... <body>
... <div class="d-grid-main">
... <p class="class-name">
...
... This is some text,
... with some newlines \r
... and some \t tabs \t too;
...
... <a href="http://example.com"> and a link too
... </a>
...
... I think we're done here
...
... </p>
... </div>
... </body>
... </html>'''
>>> response = scrapy.Selector(text=text)
>>> response.xpath('//div[@class="d-grid-main"]')
[<Selector xpath='//div[@class="d-grid-main"]' data=u'<div class="d-grid-main">\n<p class="clas'>]
>>> div = response.xpath('//div[@class="d-grid-main"]')[0]
>>>
>>> # you'll want to use relative XPath expressions, starting with "./"
>>> div.xpath('.//p[@class="class-name"]/text()').extract()
[u'\n\n This is some text,\n with some newlines \r\n and some \t tabs \t too;\n\n',
u"\n\nI think we're done here\n\n"]
>>>
>>> # only leading and trailing whitespace is removed by strip()
>>> map(unicode.strip, div.xpath('.//p[@class="class-name"]/text()').extract())
[u'This is some text,\n with some newlines \r\n and some \t tabs \t too;', u"I think we're done here"]
>>>
>>> # normalize-space() will get you a single string on the whole element
>>> div.xpath('normalize-space(.//p[@class="class-name"])').extract()
[u"This is some text, with some newlines and some tabs too; and a link too I think we're done here"]
>>>
Ответ 2
Поскольку paul trmbrth предлагает в своем ответе,
div.xpath('normalize-space(.//p[@class="class-name"])').extract()
скорее всего будет тем, что вы хотите. Однако normalize-space
также конденсирует пробелы, содержащиеся в строке, в одно пространство. Если вы хотите удалить только \r
, \n
и \t
, не нарушая другие пробелы, вы можете использовать translate()
для удалить символы.
trans_table = {ord(c): None for c in u'\r\n\t'}
item['DESCRIPTION] = ' '.join(s.translate(trans_table) for s in sel.xpath('//p[@class="class-name"]/text()').extract())
Это все равно оставит пробелы ведущего и конечного пробелов, которые не входят в набор \r
, \n
или \t
. Если вы также хотите избавиться от этого, просто вставьте вызов strip()
:
item['DESCRIPTION] = ' '.join(s.strip().translate(trans_table) for s in sel.xpath('//p[@class="class-name"]/text()').extract())
Ответ 3
Я питон, новичок в scrapy, сегодня у меня была аналогичная проблема, решил это с помощью следующего модуля/функции w3lib. html.replace_escape_chars Я создал процессор ввода по умолчанию для моего загрузчика товаров, и он работает без каких-либо проблем, вы можете связать это с конкретной scrapy.Field() также и хорошо, что он работает с css-селекторами и Экспорт кормов csv:
from w3lib.html import replace_escape_chars
yourloader.default_input_processor = MapCompose(relace_escape_chars)