搞数据的人大多听过“全量采集”和“增量采集”这两个词。
前者就像每次做家务都要把整个屋子从头到尾扫一遍,不管脏没脏;
后者更聪明一点——只打扫新落的灰,只盯着“新发生的变化”。
在爬虫领域,这就是增量采集的思路:
我们不需要每天重新抓一遍今日头条、也不用反复爬新浪新闻的旧稿库,只要获取“过去24小时的新内容”就够了。
这样做的好处显而易见:
既能保证数据新鲜,又不会浪费资源。
尤其是新闻这种更新频率高的网站,全量爬取不仅效率低,还很容易被封禁。
一句话总结:
增量采集=只关心新增和更新的部分,用更少的请求换来同样完整的数据。
想象你在一家新闻编辑部工作。每天凌晨,主编让你统计过去一天发布的新稿件。
你肯定不会从2012年的旧新闻开始看吧?你只会打开“当天的稿件列表”,看哪些是新发的、哪些是改过标题的。
这就是时间窗口。
我们人为地划定一个范围——比如过去6小时或过去1天——系统只会去抓落在这个窗口内的新闻。
再聪明一点,如果网站有“消息推送机制”(比如RSS、WebSocket、消息队列等),那我们可以让系统“被动触发”:
一旦有新新闻发布,它自己启动采集任务。
这就是事件驱动。
就像新闻部有个实习生,一旦有新稿件上线,他立刻拍你肩膀说:“快看,这篇刚发的!”
如果只靠定时任务,可能会错过突发新闻;
如果只靠事件触发,又可能因为网络延迟或推送错误漏掉一些内容。
所以比较成熟的做法是两者结合:
这种架构很像一个高效率的采编系统:定时有例行检查,同时有人随时“报料”。
新闻网站的更新节奏快得像风,只有这两种机制配合,才能既不漏掉热点,也不浪费算力。
说理论没意思,我们来点代码。
下面这个小示例展示了如何用 Python 去抓取今日头条热点和新浪新闻国内频道的最新文章,只采集最近24小时内的内容。
requests:发请求BeautifulSoup:解析网页datetime:计算时间范围import requests
from bs4 import BeautifulSoup
from datetime import datetime, timedelta
# ======== 亿牛云代理配置(示例) ========
proxy_host = "proxy.16yun.cn"
proxy_port = "3100"
proxy_user = "16YUN"
proxy_pass = "16IP"
proxies = {
"http": f"http://{proxy_user}:{proxy_pass}@{proxy_host}:{proxy_port}",
"https": f"http://{proxy_user}:{proxy_pass}@{proxy_host}:{proxy_port}",
}
# ======== 设置时间窗口:抓过去24小时的内容 ========
time_window = datetime.now() - timedelta(hours=24)
# ======== 目标网站 ========
toutiao_url = "https://www.toutiao.com/hot_event_list/"
sina_url = "https://news.sina.com.cn/china/"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64)",
"Accept-Language": "zh-CN,zh;q=0.9",
}
# ======== 今日头条热点 ========
def crawl_toutiao():
print("📡 正在采集:今日头条热点")
resp = requests.get(toutiao_url, headers=headers, proxies=proxies, timeout=10)
soup = BeautifulSoup(resp.text, "html.parser")
for item in soup.select(".hotnews-item"):
title = item.get_text(strip=True)
link = item.get("href")
pub_time = datetime.now() # 示例中暂用当前时间
if pub_time >= time_window:
print(f"【头条】{title}\n链接:{link}\n")
# ======== 新浪新闻国内频道 ========
def crawl_sina():
print("📡 正在采集:新浪新闻国内频道")
resp = requests.get(sina_url, headers=headers, proxies=proxies, timeout=10)
soup = BeautifulSoup(resp.text, "html.parser")
for item in soup.select("div.news-item h2 a"):
title = item.get_text(strip=True)
link = item.get("href")
pub_time = datetime.now() # 示例中暂用当前时间
if pub_time >= time_window:
print(f"【新浪】{title}\n链接:{link}\n")
if __name__ == "__main__":
crawl_toutiao()
crawl_sina()datetime.now() - timedelta(hours=24) 来过滤新闻,只要发布时间晚于这个时间就会被打印出来。crawl_toutiao()和crawl_sina()可以独立运行,之后你完全可以加上定时任务或消息队列,让系统自动跑起来。等你掌握了基础逻辑,可以试试以下进阶玩法:
last_crawl_time,每次启动时从上次停止的时间点接着跑。Celery + Redis或Kafka把任务拆分给多台机器,像工厂流水线一样分工采集。原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。