You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

谷歌地图地图集抓取技术求助:如何获取加拿大曼尼托巴省大麻零售商名称与地址并导出至Excel

问题分析

你的代码返回空列表的核心原因是这个Google My Map页面的内容是通过JavaScript动态渲染的:requests.get()只能获取到页面的静态HTML骨架,那些包含商家名称和地址的元素(fO2voc-jRmmHf-MZArnb-Q7Zjwb、qqvbed-p83tee-lTBxed)是页面加载后由JS动态生成的,静态HTML里根本没有这些元素,所以BeautifulSoup自然找不到。

下面给你两种符合需求的解决方案,优先推荐你熟悉的JSON数据提取思路:


方法1:提取页面隐藏的JSON数据(推荐,适配你的JSON请求习惯)

Google My Map通常会把所有标记数据打包在页面的某个<script>标签里,你可以直接提取这个JSON数据,不需要解析零散的HTML元素:

示例代码

import requests
import re
import json
import pandas as pd

# 请求目标页面
url = "https://www.google.com/maps/d/u/0/viewer?mid=1jTYtNQgB0CVC27Bn_xIsFGeVuCh_KCdR&ll=49.85504530000007%2C-97.11150419999998&z=8"
response = requests.get(url)
html_content = response.text

# 匹配存储地图数据的script标签
pattern = re.compile(r'var window\.__gmWizData__ = (.*?);\s*</script>', re.DOTALL)
match = pattern.search(html_content)

if match:
    # 解析JSON格式的地图数据
    gm_data = json.loads(match.group(1))
    # 提取所有标记点的核心数据
    markers = gm_data['viewerData']['map']['features']
    
    # 整理商家名称与地址
    retailer_data = []
    for marker in markers:
        name = marker['properties']['title']
        # 地址通常在snippet字段中,部分带有HTML换行,这里做简单提取
        raw_address = marker['properties']['snippet']
        address = raw_address.split('<br>')[0] if '<br>' in raw_address else raw_address
        
        retailer_data.append({
            'Name': name,
            'Address': address
        })
    
    # 导出到Excel文件
    df = pd.DataFrame(retailer_data)
    df.to_excel('manitoba_cannabis_retailers.xlsx', index=False)
    print("数据已成功导出到Excel!")
else:
    print("未找到地图数据,请检查页面结构是否有更新。")

注意事项

如果window.__gmWizData__变量找不到,可以在页面源码里搜索类似的关键字(比如__INITIAL_STATE__),Google偶尔会调整数据存储的变量名。


方法2:使用浏览器自动化工具(Selenium)

如果JSON数据结构频繁变化,或者你不想处理正则匹配,可以用Selenium模拟浏览器加载页面,等待动态元素渲染完成后再提取数据:

示例代码

from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
import pandas as pd

# 初始化Chrome浏览器(需提前下载对应版本的chromedriver)
driver = webdriver.Chrome()
url = "https://www.google.com/maps/d/u/0/viewer?mid=1jTYtNQgB0CVC27Bn_xIsFGeVuCh_KCdR&ll=49.85504530000007%2C-97.11150419999998&z=8"
driver.get(url)

# 等待页面动态元素加载完成
wait = WebDriverWait(driver, 10)
wait.until(EC.presence_of_element_located((By.CLASS_NAME, "qqvbed-p83tee-lTBxed")))

# 提取商家名称与地址
names = driver.find_elements(By.CLASS_NAME, "qqvbed-p83tee-lTBxed")
addresses = driver.find_elements(By.CLASS_NAME, "fO2voc-jRmmHf-MZArnb-Q7Zjwb")

# 整理数据并导出
retailer_data = [{'Name': n.text, 'Address': a.text} for n, a in zip(names, addresses)]
df = pd.DataFrame(retailer_data)
df.to_excel('manitoba_cannabis_retailers.xlsx', index=False)

# 关闭浏览器
driver.quit()
print("数据已成功导出到Excel!")

注意事项

  • 需要下载与浏览器版本匹配的驱动(比如Chrome的chromedriver)
  • 频繁请求可能触发Google的反爬机制,建议添加请求间隔或使用代理

额外建议

  • 无论用哪种方法,都建议在请求时添加浏览器类型的headers,模拟真实用户请求,降低被封禁的风险
  • 提取数据后可以先打印几条样本,确认名称和地址的格式是否正确,部分商家的地址可能需要额外的文本清洗

内容的提问来源于stack exchange,提问作者John_Muir

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.30 05:12:34