Pythonを使用したHTMLの解析


185

Pythonリスト/辞書/オブジェクトの形式でタグを取得するのに役立つPython用のHTMLパーサーモジュールを探しています。

次の形式のドキュメントがある場合:

<html>
<head>Heading</head>
<body attr1='val1'>
    <div class='container'>
        <div id='class'>Something here</div>
        <div>Something else</div>
    </div>
</body>
</html>

次に、HTMLタグの名前またはIDを介してネストされたタグにアクセスする方法を提供します。これにより、基本的に、divタグclass='container'内に含まれているbodyタグ内のコンテンツ/テキスト、または類似のものを取得するように要求できます。

Firefoxの「要素の検査」機能(HTMLの表示)を使用している場合は、ツリーのように入れ子になった方法ですべてのタグが提供されることがわかります。

ビルトインモジュールの方がいいと思いますが、少し質問しすぎるかもしれません。


私はStack Overflowとインターネット上のいくつかのブログで多くの質問をしました、そしてそれらのほとんどはBeautifulSoupまたはlxmlまたはHTMLParserを提案しますが、これらのいくつかは機能を詳述し、どちらがより速く/より効率的かについての議論として終わります。


2
他のすべての回答者と同様に、BeautifulSoupは壊れたHTMLファイルの処理に非常に優れているため、BeautifulSoupをお勧めします。
Pascal Rosin 2012

回答:


195

bodyタグ内に含まれるclass = 'container'を含むdivタグのコンテンツ/テキストを取得するように要求できるようにするため、または類似したもの。

try: 
    from BeautifulSoup import BeautifulSoup
except ImportError:
    from bs4 import BeautifulSoup
html = #the HTML code you've written above
parsed_html = BeautifulSoup(html)
print(parsed_html.body.find('div', attrs={'class':'container'}).text)

私が推測するパフォーマンスの説明は必要ありません。BeautifulSoupの仕組みを読んでください。公式ドキュメントをご覧ください。


2
parsed_htmlオブジェクトとは正確には何ですか?
12

1
parsed_htmlは、BeautifulSoupオブジェクトです。ただし、「body」が最初のBeautifulSoupオブジェクト(基本的にはツリーノードです)を参照する(そしてこの場合、 、のみ)ルート要素のbody要素(この場合はhtml)
Aadaam 2012

18
ただの更新:BeautifulSoup 4以降、インポートラインは現在from bs4 import BeautifulSoup
ベイリーパーカー、

2
一般情報:パフォーマンスが重要な場合は、lxml代わりにライブラリを使用することをお勧めします(以下の回答を参照)。これcssselectも非常に便利で、パフォーマンスは他の利用可能なライブラリよりも10〜100倍優れていることがよくあります。
Lenar Hoyt 2014

注:class属性は特別です:BeautifulSoup(html).find('div', 'container').text
jfs

85

私が探しているのはpyqueryだと思います:

pyquery:Python用のjqueryのようなライブラリ。

あなたが望むものの例は次のようになります:

from pyquery import PyQuery    
html = # Your HTML CODE
pq = PyQuery(html)
tag = pq('div#id') # or     tag = pq('div.class')
print tag.text()

また、FirefoxまたはChromeのinspect要素と同じセレクターを使用します。例えば:

要素セレクターは「div#mw-head.noprint」です

検査される要素セレクターは「div#mw-head.noprint」です。したがって、pyqueryでは、このセレクターを渡すだけです。

pq('div#mw-head.noprint')

2
私はこれのためにあなたを3000愛しています!
progyammer

41

ここでは、PythonのさまざまなHTMLパーサーとそのパフォーマンスについて詳しく読むことができます。記事は少し古くなっていますが、それでもあなたに良い概要を与えます。

Python HTMLパーサーのパフォーマンス

組み込みではありませんが、BeautifulSoupをお勧めします。これらの種類のタスクを簡単に操作できるからです。例えば:

import urllib2
from BeautifulSoup import BeautifulSoup

page = urllib2.urlopen('http://www.google.com/')
soup = BeautifulSoup(page)

x = soup.body.find('div', attrs={'class' : 'container'}).text

2
パフォーマンス/効率ではなく、機能/機能を詳しく説明するものを探していました。編集:時期尚早の答えでごめんなさい、そのリンクは実際に良いです。ありがとう。
12

最初のポイントリストの種類は、特徴と機能を要約しています:)
Qiau

5
BeautifulSoup4(最新バージョン)を使用する場合:from bs4 import BeautifulSoup
フランクダーノンコート

29

他のパーサーライブラリと比較すると、lxml非常に高速です。

また、cssselectHTMLページのスクレイピングにも非常に簡単に使用できます。

from lxml.html import parse
doc = parse('http://www.google.com').getroot()
for div in doc.cssselect('a'):
    print '%s: %s' % (div.text_content(), div.get('href'))

lxml.htmlドキュメント


HTTPSはサポートされていません
セルジオ

@Sergio使用import requests、バッファをファイルに保存:stackoverflow.com/a/14114741/1518921(またはurllib)、保存されたファイルを解析を使用してロードした後doc = parse('localfile.html').getroot()
ギル

特定のデータの巨大なHTMLを解析します。でそれをやってBeautifulSoupかかった1.7秒が、適用lxmlのを代わりに、ほぼそれを後押し*100FASTER回!パフォーマンスを重視する場合、lxmlが最適なオプションです
Alex-Bogdanov

9

HTMLの解析にはlxmlをお勧めします。「lxmlサイトの」「HTMLの解析」を参照してください

私の経験では、Beautiful Soupはいくつかの複雑なHTMLを台無しにしています。Beautiful Soupはパーサーではなく、非常に優れた文字列アナライザーだからです。


3
AIUI美しいスープは最も「バックエンド」のXMLパーサで動作するように行うことができ、lxmlのは、サポートされているパーサの一つであるように思わcrummy.com/software/BeautifulSoup/bs4/doc/#installing-a-parser
ffledgling

@ffledglingただし、BeautifulSoupの一部の機能はかなり遅くなっています。
Lenar Hoyt 2014

2

justextライブラリの使用をお勧めします。

https://github.com/miso-belica/jusText

使用法: Python2:

import requests
import justext

response = requests.get("http://planet.python.org/")
paragraphs = justext.justext(response.content, justext.get_stoplist("English"))
for paragraph in paragraphs:
    print paragraph.text

Python3:

import requests
import justext

response = requests.get("http://bbc.com/")
paragraphs = justext.justext(response.content, justext.get_stoplist("English"))
for paragraph in paragraphs:
    print (paragraph.text)

0

EHPを使用します

https://github.com/iogf/ehp

ここにあります:

from ehp import *

doc = '''<html>
<head>Heading</head>
<body attr1='val1'>
    <div class='container'>
        <div id='class'>Something here</div>
        <div>Something else</div>
    </div>
</body>
</html>
'''

html = Html()
dom = html.feed(doc)
for ind in dom.find('div', ('class', 'container')):
    print ind.text()

出力:

Something here
Something else

5
説明してください。人気のあるBeautifulSoupまたはlxmlよりもEHPをどのように使いますか?
ChaimG 2016
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.