使用Python和Beautiful Soup分割抓取的文本

2024-06-01 00:39:31 发布

您现在位置:Python中文网/ 问答频道 /正文

我从this website里抄下了时间表。 我得到的结果是:

"ROUTE": "NAPOLI PORTA DI MASSA \u00bb ISCHIA"

但我想:

"DEPARTURE PORT": "NAPOLI PORTA DI MASSA"
"ARRIVAL PORT": "ISCHIA"

我该如何划分字符串? 代码如下:

medmar_live_departures_table = list(soup.select('li.tratta'))
departure_time = []
for li in medmar_live_departures_table:
    next_li = li.find_next_sibling("li")
    while next_li and next_li.get("data-toggle"):
        if next_li.get("class") == ["corsa-yes"]:         
          #  departure_time.append(next_li.strong.text)
            medmar_live_departures_data.append({
            'ROUTE' : li.text
           })

Tags: livetimeporttableliroutenextdi
1条回答
网友
1楼 · 发布于 2024-06-01 00:39:31

试试这个:

medmar_live_departures_table = list(soup.select('li.tratta'))
departure_time = []
for li in medmar_live_departures_table:
    next_li = li.find_next_sibling("li")
    while next_li and next_li.get("data-toggle"):
        if next_li.get("class") == ["corsa-yes"]:         
          #  departure_time.append(next_li.strong.text)
            medmar_live_departures_data.append({
            'DEPARTURE PORT' : li.text.split("\ u00bb")[0],
            'ARRIVAL PORT' : li.text.split("\ u00bb")[1]
           })

网友
2楼 · 发布于 2024-06-01 00:39:31

两件事

1.由于“»”是一个非ascii字符,python将返回非ascii字符,例如“\u00bb”,因此通过使用非ascii代码(例如)拆分文本来解析字符串将起作用:

parse=li.get_text().split('\u00bb')

此外,您还可以使用re-library来解析非ascii字符(如选择此路径,则需要添加re-library):

import re

non_ascii = li.get_text()
parse = re.split('[^\x00-\x7f]', non_ascii)
#[^\x00-\x7f] will select non-ascii characters as pointed out by Moinuddin Quadri in https://stackoverflow.com/questions/40872126/python-replace-non-ascii-character-in-string

但是,通过这样做,python将从parse中创建一个部分列表,但并非“li”html标记中的所有文本都带有“»”字符(就是说在网站上表格的末尾写上“pozzoli-PROCIDA”,所以我们必须考虑到这一点,否则我们会遇到一些问题。你知道吗

2.字典可能是一个糟糕的数据结构选择,因为您正在解析的数据将具有相同的键。你知道吗

例如,POUZZOULI»CASAMICCIOLA和POUZOULI»PROCIDA。COSMICCIOLA和PROCIDA将拥有相同的密钥。Python将简单地覆盖/更新POUZZOULI键的值。所以POUZZOULI:CASAMICCIOLA将变成POUZZOULI:PROCIDA,而不是将POUZZOULI:CASAMICCIOLA添加为字典条目,将POUZZOULI:PROCIDA添加为另一个字典条目。你知道吗

我建议将解析的每个部分作为元组添加到列表中,如下所示:

single_port= []
ports=[]

medmar_live_departures_table = list(bs.select('li.tratta'))
departure_time = []
for li in medmar_live_departures_table:
    next_li = li.find_next_sibling("li")
    while next_li and next_li.get("data-toggle"):
        if next_li.get("class") == ["corsa-yes"]:
            #  departure_time.append(next_li.strong.text)
            non_ascii = li.get_text()
            parse = re.split('[^\x00-\x7f]', non_ascii)

            # The if statement takes care of table data strings that don't have the non-ascii character "»" 
            if len(parse) > 1:
                ports.append((parse[0], parse[1]))

            else:
                single_port.append(parse[0])


# This will print out your data in your desired manner
for i in ports:
    print("DEPARTURE: "+i[0])
    print("ARRIVAL: "+i[1])

for i in single_port:
    print(i)

我还在运行的测试代码中使用了split方法:

import requests
from bs4 import BeautifulSoup
import re

url="https://www.medmargroup.it/"
response=requests.get(url)
bs=BeautifulSoup(response.text, 'html.parser')


timeTable=bs.find('section', class_="primarystyle-timetable")

medmar_live_departures_table=timeTable.find('ul')
single_port= []
ports=[]


for li in medmar_live_departures_table.find_all('li', class_="tratta"):
    parse=li.get_text().split('\u00bb')

    if len(parse)>1:
        ports.append((parse[0],parse[1]))

    else:
        single_port.append(parse[0])


for i in ports:
    print("DEPARTURE: "+i[0])
    print("ARRIVAL: "+i[1])

for i in single_port:
    print(i)

我希望这有帮助!你知道吗

相关问题 更多 >