Как подсказал @Herman, вы должны использовать Tag.text
, чтобы найти соответствующий текст для тега, который вы сейчас анализируете.
Немного подробнее о том, почему Tag.find()
не сделал того, что вы хотите* BeautifulSoup Tag.find()
очень похож на Tag.findAll()
, фактически его реализация Tag.find()
просто вызывает Tag.findAll()
с пределом аргумента ключевого слова, установленным на 1 .Tag.findAll()
затем рекурсивно спускается вниз по дереву тегов и возвращается, как только находит текст, который удовлетворяет аргументу text
.Поскольку для text
установлено значение True
, символ "u" "технически удовлетворяет этому условию и, таким образом, является тем, что возвращается Tag.find()
.
Фактически вы можете видеть, что годвозвращается, если вы распечатываете td.findAll(text=True, limit=2)
.Вы также можете установить text
в регулярное выражение, чтобы игнорировать пробелы, поэтому вы можете сделать td.find(text=re.compile('[\S\w]'))
.
Я также заметил, что вы используете store.append('|'.join(filter(None, row)))
.Я думаю, что вы должны использовать CSV модуль , особенно csv.writer .Модуль CSV обрабатывает все проблемы, с которыми вы можете столкнуться, если у вас есть какой-то канал в проанализированных html-файлах, и делает ваш код намного чище.
Вот пример:
import csv
import re
from cStringIO import StringIO
from BeautifulSoup import BeautifulSoup
html = ('<html><body><table><tr><td> <p>year</p></td><td><p>salary</p></td>'
'<td>bonus</td></tr><tr><td>2005</td><td>100,000</td><td>50,000</td>'
'</tr><tr><td>2006</td><td>120,000</td><td>80,000</td></tr></table>'
'</html>')
soup = BeautifulSoup(html)
table = soup.find('table')
rows = table.findAll('tr')
output = StringIO()
writer = csv.writer(output, delimiter='|')
for tr in rows:
cols = tr.findAll('td')
row = []
for td in cols:
row.append(td.text)
writer.writerow(filter(None, row))
print output.getvalue()
И вывод:
year|salary|bonus
2005|100,000|50,000
2006|120,000|80,000