为什么我在此网络刮擦中进行的循环仅印刷活动的第一个?我希望它打印所有标题,链接,位置,日期和描述



我正在抓取此网站,但是在运行仅打印第一个事件的代码后我有问题,而for循环没有迭代。

将事件作为列表

附加
class Events(object):
    def __init__(self, title=None,  place=None, date_posted=None, description=None, linkhref=None):
        self.title = title
        self.place = place
        self.date_posted = date_posted
        self.description = description
        self.linkhref = linkhref

我想将其保存在CSV

sv_file = open('scrape2.csv', 'w', encoding="utf-8")
csv_writer = csv.writer(csv_file)
# Columns
csv_writer.writerow(['title', 'link', 'place', 'date_posted', 'description'])

在这一部分中,我想从3页上刮擦网站,并找到每个事件的日期,事件名称,场地和描述等详细信息。

def scrape():
for page in range(0, 2):
    page = page + 1 
    base_url = 'https://allevents.in/malacca/all?ref=cityhome-popular' + str(page)
    source = requests.get(base_url)
    soup = BeautifulSoup(source.text, "html.parser")
    all_event = soup.find_all('div', class_="event-list listview")
    events = []
    for item in all_event:
        title = item.find("h3").text.strip()
        link = item.find("h3")
        linkhref = link.find("a").get('href')   
        place = item.find("p", {"class":"location"}).text.strip()
        date_posted = item.find("div", {"class":"right"}).text.strip()
        description = item.find("p", {"class":"short-desc"}).text.strip()
        csv_writer.writerow([title, link, place, date_posted, description])
        events.append(Events(title, link, place, date_posted, description))

这是迭代列表

的循环
for event in events:
        print("Title: " + event.title)
        print("Link: " + event.linkhref)
        print("Place: " + str(event.place))
        print("Date: " + event.date_posted)
        print("Description: " + event.description)
        print("-----------------------------------")
    csv_file.close()
    return 1
if __name__ == "__main__":
    print(scrape())

您可以以不同的方式获取和写入结果。此外,您可以利用命名tuple来摆脱冗长的速度。这就是我要做的。

import csv
import requests
from bs4 import BeautifulSoup
from collections import namedtuple
class Events(object):
    def __init__(self):
        self.base_url = 'https://allevents.in/malacca/all?ref=cityhome-popular'
        self.items = namedtuple('itemDocument', ['title','linkhref','place','date_posted','description'])
    def scrape(self):
        source = requests.get(self.base_url)
        soup = BeautifulSoup(source.text,"lxml")
        for item in soup.find_all('div', class_="event-item"):
            title = item.find("h3").text.strip()
            linkhref = item.find("h3").find("a").get('href')   
            place = ' '.join(item.find("p", {"class":"location"}).text.split())
            date_posted = item.find("div", {"class":"right"}).text.strip()
            description = item.find("p", {"class":"short-desc"}).text.strip()
            yield self.items(title,linkhref,place,date_posted,description)
if __name__ == "__main__":
    scraper = Events()
    with open("outputFile.csv","w",newline="",encoding="utf-8") as f:
        writer = csv.writer(f)
        writer.writerow(['title','linkhref','place','date_posted','description'])
        for item in scraper.scrape():
            writer.writerow([item.title,item.linkhref,item.place,item.date_posted,item.description])

现在,您可以使用上述脚本中遍历不同页面的逻辑,因为我为简短而踢了。

,因为'查找'关键字仅返回它找到的第一个标记元素。要返回所有带有指定标签的元素,例如" H3",我不确定,但它是" Find_all"关键字。请先检查一下。如果解决您的问题,则将此答案标记为有用。

你几乎在那里;只需更改代码的中间部分,即all_event的分配开始:

all_event = soup.find_all('h3')
events = []
for item in all_event:
    title = item.a.text
    linkhref = item.a['href']
    place = item.findNext('span').text.strip()
    date_posted = item.findNext('div', class_="right").text.strip()
    description = item.findNext('p', class_="short-desc").text.strip()

它应该从那里起作用,也许有一些修改。

相关内容

最新更新