Fehler mit Schöner Suppe des extract ()
-
21-08-2019 - |
Frage
Ich arbeite an einiger Screen-Scraping-Software und habe sie zu einem Problem mit Schöner Suppe laufen. Ich verwende Python 2.4.3 und schöne Suppe 3.0.7a.
Ich brauche einen <hr>
Tag zu entfernen, aber es kann viele verschiedene Attribute, so dass eine einfache replace () Anruf wird nicht schneiden.
In Anbetracht der folgenden html:
<h1>foo</h1>
<h2><hr/>bar</h2>
Und der folgende Code:
soup = BeautifulSoup(string)
bad_tags = soup.findAll('hr');
[tag.extract() for tag in bad_tags]
for i in soup.findAll(['h1', 'h2']):
print i
print i.string
Die Ausgabe lautet:
<h1>foo</h1>
foo
<h2>bar</h2>
None
Bin ich Missverständnis der Extrakt-Funktion, oder ist das ein Bug mit Schöner Suppe?
Lösung
Es kann ein Fehler sein. Aber zum Glück für Sie, es gibt einen anderen Weg, um die Zeichenfolge zu erhalten:
from BeautifulSoup import BeautifulSoup
string = \
"""<h1>foo</h1>
<h2><hr/>bar</h2>"""
soup = BeautifulSoup(string)
bad_tags = soup.findAll('hr');
[tag.extract() for tag in bad_tags]
for i in soup.findAll(['h1', 'h2']):
print i, i.next
# <h1>foo</h1> foo
# <h2>bar</h2> bar
Andere Tipps
Ich habe das gleiche Problem. Ich weiß nicht, warum, aber ich denke, es mit den leeren Elementen von BS erstellt zu tun hat.
Zum Beispiel, wenn ich den folgenden Code:
from bs4 import BeautifulSoup
html =' \
<a> \
<b test="help"> \
hello there! \
<d> \
now what? \
</d> \
<e> \
<f> \
</f> \
</e> \
</b> \
<c> \
</c> \
</a> \
'
soup = BeautifulSoup(html,'lxml')
#print(soup.find('b').attrs)
print(soup.find('b').contents)
t = soup.find('b').findAll()
#t.reverse()
for c in t:
gb = c.extract()
print(soup.find('b').contents)
soup.find('b').text.strip()
Ich habe folgende Fehlermeldung:
'NoneType' Objekt hat kein Attribut 'next_element'
Auf dem ersten Druck bekam ich:
>>> print(soup.find('b').contents)
[u' ', <d> </d>, u' ', <e> <f> </f> </e>, u' ']
und auf dem zweiten bekam ich:
>>> print(soup.find('b').contents)
[u' ', u' ', u' ']
Ich bin mir ziemlich sicher, dass es das leere Element in der Mitte ist, das Problem zu schaffen.
Eine Abhilfe i gefunden ist, nur die Suppe neu erstellen:
soup = BeautifulSoup(str(soup))
soup.find('b').text.strip()
Jetzt druckt:
>>> soup.find('b').text.strip()
u'hello there!'
Ich hoffe, das hilft.