2013-04-07 2 views
4

Я новичок в Nokogiri и Ruby в целом.Что XPath можно использовать для получения всех текстовых узлов после и после первого узла абзаца?

Я хочу получить текст всех узлов в документе, начиная с и до первого узла абзаца.

Я попытался следующие с XPath, но я не получаю нигде:

puts page.search("//p[0]/text()[next-sibling::node()]") 

Это не работает. Что мне нужно изменить?

+0

Важно предоставить небольшой образец рассматриваемого XML. –

+0

http://www.zeit.de/wirtschaft/2013-04/produkte-schwachstellen-garantie-hersteller – user1895623

+0

Нет, не ссылка на ваш образец, поместите образец его в вопрос, достаточно большой, чтобы продемонстрировать проблему и не больше. Ссылка заставляет нас преследовать информацию, необходимую нам, чтобы помочь вам, и, поскольку мы делаем это добровольно, в наше свободное время, вы заставляете нас делать дополнительную работу, чтобы помочь вам. Не делай этого. Кроме того, перерыв ссылок, что делает ваш вопрос бесполезным для людей, которые ищут тот же вопрос в будущем. –

ответ

4

Вы должны найти узел <p/> и вернуть все text() узлы, как внутри, так и после. В зависимости от того, какие возможности XPath Nokogiri имеет, используйте один из следующих запросов:

//p[1]/(descendant::text() | following::text()) 

Если он не работает, используйте это, что нужно найти первый абзац в два раза и может быть немного, но, вероятно, незаметно, медленнее:

(//p[1]/descendant::text() | //p[1]/following::text()) 

, вероятно, не поддерживается в XPath 2.0 альтернативой было бы:

//text()[//p[1] << .] 

что означает «все текстовые узлы, которым предшествует первой <p/> узел в документе ".

+0

+1, но обратите внимание, что только ваше второе выражение работает с Nokogiri. – Phrogz

+0

Это то, чего я ожидал, поэтому я предоставил несколько. Я не уверен, что первый допустимый XPath 1.0, но не поддерживается на nokogiri или это XPath 2.0. Поскольку последняя является самой элегантной версией для написания этого запроса, я включил ее в любом случае. –

+0

@JensErat ,, спасибо тонну чувак, он работал как шарм. Еще одна вещь, задача, которую я имею, - это проанализировать эти немецкие веб-страницы, а затем в основном разделить содержимое статьи на предложения, а затем слова, моя проблема связана с регулярным выражением. Я могу выполнить эту работу на английском языке, но я не знаю, что делать на немецком языке, какова наилучшая практика при расщеплении немецких персонажей. (мое регулярное выражение сбрасывается с умлаутами и eszets), я пробовал оба модификатора \ p {l} и \ X в php, но не повезло. Если вы или кто-то еще почувствует, что они могут мне помочь, я бы предоставил полный пример. Nnx – user1895623

2

Это работает с Nokogiri (который стоит на вершине libxml2 и поддерживает XPath 1.0 выражения):

//p[1]//text() | //p[1]/following::text() 

Доказательство:

require 'nokogiri' 

html = '<body><h1>A</h1><p>B <b>C</b></p><p>D <b>E</b></p></body>' 
doc = Nokogiri.HTML(html) 

p doc.xpath('//p[1]//text() | //p[1]/following::text()').map(&:text) 
#=> ["B ", "C", "D ", "E"] 

Обратите внимание, что только выделив текст сами узлы возвращает NodeSet из Nokogiri::XML::Text, и поэтому, если вы хотите только их текстовое содержимое, вы должны сопоставить их с помощью методов .text (или .content).

+0

Это выглядит правильно, но я не думаю, что нужно [1] – pguardiario

+0

@Phrogz, +1, спасибо, что это работает. пожалуйста, не могли бы вы помочь с моим другим вопросом (ive добавил его в качестве комментария, ниже ответа jens erat) – user1895623

+0

@ user1895623 Задайте его как [новый вопрос] (http://stackoverflow.com/questions/ask). – Phrogz

Смежные вопросы