Beautiful Soupを使用して、Zillowから住宅価格のデータを取得しようとしています。
プロパティIDでWebページを取得します。 http://www.zillow.com/homes/for_sale/18429834_zpid/
find_all()
関数を試しても結果が得られません。
results = soup.find_all('div', attrs={"class":"home-summary-row"})
ただし、HTMLを取得して、必要なビットだけに切り詰めると、次のようになります。
<html>
<body>
<div class=" status-icon-row for-sale-row home-summary-row">
</div>
<div class=" home-summary-row">
<span class=""> $1,342,144 </span>
</div>
</body>
</html>
2つの結果が得られます。両方とも<div>
sクラスhome-summary-row
。だから、私の質問は、ページ全体を検索するとなぜ結果が得られないのですか?
作業例:
from bs4 import BeautifulSoup
import requests
zpid = "18429834"
url = "http://www.zillow.com/homes/" + zpid + "_zpid/"
response = requests.get(url)
html = response.content
#html = '<html><body><div class=" status-icon-row for-sale-row home-summary-row"></div><div class=" home-summary-row"><span class=""> $1,342,144 </span></div></body></html>'
soup = BeautifulSoup(html, "html5lib")
results = soup.find_all('div', attrs={"class":"home-summary-row"})
print(results)
W3.org Validator によると、HTMLには、閉じた閉じタグや複数行に分割されたタグなど、多くの問題があります。例えば:
<a
href="http://www.zillow.com/danville-ca-94526/sold/" title="Recent home sales" class="" data-za-action="Recent Home Sales" >
この種類のマークアップは、BeautifulSoupがHTMLを解析することをはるかに困難にする可能性があります。
各行の末尾から改行や末尾のスペースを削除するなど、HTMLをクリーンアップするために何かを実行してみてください。 BeautifulSoupは、HTMLツリーをクリーンアップすることもできます。
from BeautifulSoup import BeautifulSoup
tree = BeautifulSoup(bad_html)
good_html = tree.prettify()
あなたのHTMLは整形式ではありません。このような場合、適切なパーサーを選択することが重要です。 BeautifulSoup
には、現在3つの利用可能なHTMLパーサーがあり機能し、壊れたHTMLを異なる方法で処理します:
html.parser
(組み込み、追加モジュールは不要)lxml
(最速、lxml
のインストールが必要)html5lib
(最も緩い、html5lib
のインストールが必要)パーサー間の違い のドキュメントページでは、違いについて詳しく説明しています。あなたのケースでは、違いを示すために:
>>> from bs4 import BeautifulSoup
>>> import requests
>>>
>>> zpid = "18429834"
>>> url = "http://www.zillow.com/homes/" + zpid + "_zpid/"
>>> response = requests.get(url)
>>> html = response.content
>>>
>>> len(BeautifulSoup(html, "html5lib").find_all('div', attrs={"class":"home-summary-row"}))
0
>>> len(BeautifulSoup(html, "html.parser").find_all('div', attrs={"class":"home-summary-row"}))
3
>>> len(BeautifulSoup(html, "lxml").find_all('div', attrs={"class":"home-summary-row"}))
3
ご覧のとおり、あなたのケースでは、html.parser
とlxml
の両方が仕事をしますが、html5lib
はしません。
import requests
from bs4 import BeautifulSoup
zpid = "18429834"
url = "http://www.zillow.com/homes/" + zpid + "_zpid/"
r = requests.get(url)
soup = BeautifulSoup(r.content, "lxml")
g_data = soup.find_all("div", {"class": "home-summary-row"})
print g_data[1].text
#for item in g_data:
# print item("span")[0].text
# print '\n'
私もこれを機能させました-しかし、誰かが私を倒したようです。
とにかく投稿します。