2017-06-01 6 views
0

キーテキストのラッパーを取得しますか?例えば、HTMLで:Python + BeautifulSoup:テキストに基づいてHTMLからラッパーを取り除くには?

… 
<div class=“target”>chicken</div> 
<div class=“not-target”>apple</div> 
… 

によってテキスト「鶏」に基づいて、バック<div class=“target”>chicken</div>を取得したいと思います。

import requests 
from bs4 import BeautifulSoup 

req = requests.get(url).txt 
soup = BeautifulSoup(r, ‘html.parser’) 

そして、ちょうど私が探していますラッパーを見つけるために、利用可能なすべてのdivを通じてsoup.find_all(‘div’,…)とループを行うに持つ:

は現在、HTMLを取得するために、次があります。

divをループせずに、定義されたテキストに基づいてHTMLでラッパーをフェッチする適切かつ最適な方法は何でしょうか?

ありがとうございます。受け入れてください/ upvote答えてください!

+0

https://stackoverflow.com/a/31959218/4387299 – internety

+0

@internety Gave 'soup.find_all( 'div'、string = 'chicken')'は試みますが、空の配列を返します。 –

+0

中括弧を使用しない –

答えて

1
# coding: utf-8 

html_doc = """ 
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> 
<html xmlns="http://www.w3.org/1999/xhtml"> 
    <head> 
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> 
    <title> Last chicken leg on stock! Only 500$ !!! </title> 
    </head> 
    </body> 
    <div id="layer1" class="class1"> 
     <div id="layer2" class="class2"> 
      <div id="layer3" class="class3"> 
       <div id="layer4" class="class4"> 
        <div id="layer5" class="class5"> 
         <p>My chicken has <span style="color:blue">ONE</span> leg :P</p> 
         <div id="layer6" class="class6"> 
          <div id="layer7" class="class7"> 
           <div id="chicken_surname" class="chicken">eat me</div> 
           <div id="layer8" class="class8"> 
           </div> 
          </div> 
         </div> 
        </div> 
       </div> 
      </div> 
     </div> 
    </div> 
    </body> 
</html>""" 

from bs4 import BeautifulSoup as BS 
import re 
soup = BS(html_doc, "lxml") 


# (tag -> text) direction is pretty obvious that way 
tag = soup.find('div', class_="chicken") 
tag2 = soup.find('div', {'id':"chicken_surname"}) 
print('\n###### by_cls:') 
print(tag) 
print('\n###### by_id:') 
print(tag2) 

# but can be tricky when need to find tag by substring 
tag_by_str = soup.find(string="eat me") 
tag_by_sub = soup.find(string="eat") 
tag_by_resub = soup.find(string=re.compile("eat")) 
print('\n###### tag_by_str:') 
print(tag_by_str) 
print('\n###### tag_by_sub:') 
print(tag_by_sub) 
print('\n###### tag_by_resub:') 
print(tag_by_resub) 

# there are more than one way to access underlying strings 
# both are different - see results 
tag = soup.find('p') 

print('\n###### .text attr:') 
print(tag.text, type(tag.text)) 

print('\n###### .strings generator:') 
for s in tag.strings: # strings is an generator object 
    print s, type(s) 

# note that .strings generator returns list of bs4.element.NavigableString elements 
# so we can use them to navigate, for example accessing their parents: 
print('\n###### NavigableString parents:') 
for s in tag.strings: 
    print s.parent 

# or even grandparents :) 
print('\n###### grandparents:') 
for s in tag.strings: 
    print s.parent.parent 
+0

私の質問は、あなたが探している文字列のための同じタグの複数の場合です、私はターゲットタグを見つけるためにそれらをすべて調べなければなりません。 2つの 'p'タグがあるとしたら、' tag = soup.find( 'p') 'は必ずしも機能しません。私が探しているのは、すべてを解析することなく、文字列のタグを一度に見つけ出す方法です。 –

+0

@Jo Ko:「すべて解析する必要なし」 IMO HTML文書内の各要素を検索するには、文書全体を解析する必要があります:) 部分的にしか利用できない文書(つまり、長いプールのHTTP)そのメソッドの詳細については、[parse HTML incrementally](http://lxml.de/parsing.html#incremental-event-parsing)を参照してください。 – internety

関連する問題