web-dev-qa-db-ja.com

XPathを使用してHTML要素のテキストコンテンツを取得しますか?

このhtmlをご覧ください

<div>
    <p>
    <span class="abc">Monitor</span> <b>$300</b>
    </p>
    <a href="/add">Add to cart</a>
</div>
<div>
    <p>
    <span class="abc">Keyboard</span> $20 
    </p>
    <a href="/add">Add to cart</a>
</div>

Xpathを使用して解析したいMonitor $300およびKeyboard $20。私はこのxpathを使用します

 //div[a[contains(., "Add to cart")]]/p/text()

ただし、<span class="abc">Monitor</span> <b>$300</b>。タグは必要ありません。テキストのみを取得するにはどうすればよいですか?

19
Genghis Khan

すべてのdescendantテキストを選択します。子テキストだけではありません:

_//div[a[contains(., "Add to cart")]]/p//text()
_

ptext()の間の二重スラッシュに注意してください。

これにはタグ間の空白も多く含まれる可能性がありますが、クリーンアップする必要があります。 lxmlを使用した例:

_>>> import lxml.etree as ET
>>> tree = ET.fromstring('''<div>
... <div>
...     <p>
...     <span class="abc">Monitor</span> <b>$300</b>
...     </p>
...     <a href="/add">Add to cart</a>
... </div>
... <div>
...     <p>
...     <span class="abc">Keyboard</span> $20 
...     </p>
...     <a href="/add">Add to cart</a>
... </div>
... </div>''')
>>> tree.xpath('//div[a[contains(., "Add to cart")]]/p//text()')
['\n    ', 'Monitor', ' ', '$300', '\n    ', '\n    ', 'Keyboard', ' $20 \n    ']
>>> res = _
>>> [txt for txt in (txt.strip() for txt in res) if txt]
['Monitor', '$300', 'Keyboard', '$20']
_
27
Martijn Pieters