Python爬虫获取的天气数据是JS动态加载的,如何录入Excel?
http://tianqi.2345.com/t/wea_history/js/56294_20112.js
Python爬虫获取的天气数据是JS动态加载的,如何录入Excel?
掐头去尾就是 json
用requests直接拿到的HTML里没天气数据对吧?那是JS动态加载的。得用Selenium或Playwright这类工具模拟浏览器执行JS,等数据加载完再抓取。
这里给你个完整示例,用Selenium配合pandas,从中国天气网抓取北京7天预报并写入Excel:
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
from datetime import datetime
# 设置Selenium(需提前下载对应浏览器的driver)
options = webdriver.ChromeOptions()
options.add_argument('--headless') # 无头模式,不显示浏览器窗口
driver = webdriver.Chrome(options=options)
try:
# 访问中国天气网北京7天预报
url = 'http://www.weather.com.cn/weather/101010100.shtml'
driver.get(url)
# 显式等待,直到天气数据所在的容器加载出来
wait = WebDriverWait(driver, 10)
weather_container = wait.until(
EC.presence_of_element_located((By.ID, '7d'))
)
# 提取7天数据
days = weather_container.find_elements(By.CSS_SELECTOR, 'li')
weather_data = []
for day in days:
try:
# 提取日期、天气、温度
date = day.find_element(By.TAG_NAME, 'h1').text
weather = day.find_element(By.CLASS_NAME, 'wea').text
temp = day.find_element(By.CLASS_NAME, 'tem').text
weather_data.append({
'日期': date,
'天气': weather,
'温度': temp.replace('\n', ' ') # 处理温度中的换行
})
except:
continue # 跳过提取失败的项目
# 转换为DataFrame
df = pd.DataFrame(weather_data)
# 写入Excel
filename = f'北京天气_{datetime.now().strftime("%Y%m%d")}.xlsx'
df.to_excel(filename, index=False, engine='openpyxl')
print(f"数据已保存到: {filename}")
print(f"共抓取{len(df)}条数据")
finally:
driver.quit() # 确保关闭浏览器
关键点说明:
- Selenium:模拟真实浏览器,让JS完全执行
- 显式等待:用
WebDriverWait确保数据加载完成再抓取,比sleep更可靠 - 数据提取:通过CSS选择器定位具体元素
- pandas:用
DataFrame整理数据,to_excel一键写入
如果网站反爬严重,可以:
- 加
user-agent头 - 用
time.sleep()随机延迟 - 考虑
Playwright,它对动态页面支持更好
一句话总结:用Selenium等工具处理JS渲染,再用pandas写Excel。
python 直接写 xls。。
先把首尾的 var weather_str=、分号去掉,变成 json,再存入表格里吗
好久没用过把入门级的那点知识也忘了差不多了
json 解码之后,再按照 xls 格式去写
谢谢 虽然看不懂啊 ,业余非专业,现在去找找别人的代码看怎么处理类似情况的。
#1 然而单引号……好在数据里应该不会出现单双引号,所以无脑 replace 大概也没问题……
保存 csv 不就行了?
table 标签嘛
直接用字符串模板写 cvs 逗号分隔, 好像 /d/n 换行来着
找了个 csv 案例,
import csv
with open(‘names.csv’,‘w’) as csvfile:
fieldnames = [‘first_name’,‘last_name’]
writer = csv.DictWriter(csvfile, fieldnames=fieldnames)
writer.writeheader()
writer.writerow({‘first_name’: ‘Baked’, ‘last_name’: ‘Beans’})
writer.writerow({‘first_name’: ‘Lovely’, ‘last_name’: ‘Spam’})
writer.writerow({‘first_name’: ‘Wonderful’, ‘last_name’: ‘Spam’})
但是,天气那个 js 数据怎么每一天数据单独写入一行啊?
fieldnames = [‘Ymd’,‘ bWendu’,’ yWendu’,’ fengxiang’,'fengli ’]
然后继续把每个日期的数据像字典这样放进吗?
‘ ymd:‘2011-02-01’,’ bWendu ‘:‘9℃’,’ yWendu ‘:‘0℃’,’ tianqi ‘:‘多云’,’ fengxiang ‘:‘北风’,’ fengli ‘:'微风’
就是不知道如何完全自动化。。。
可以正则提取成 csv
明显不是 json ,而是 jsonp.
正则提取 json,然后写入就行了。。。
python 直接用 xlwt 写就行了
掐头去尾 json+1
import xlwt
#创建 workbook 和 sheet 对象
workbook = xlwt.Workbook() #注意 Workbook 的开头 W 要大写
sheet1 = workbook.add_sheet(‘sheet1’,cell_overwrite_ok=True)
sheet2 = workbook.add_sheet(‘sheet2’,cell_overwrite_ok=True)
#向 sheet 页中写入数据
sheet1.write(0,0,‘this should overwrite1’)
sheet1.write(0,1,‘aaaaaaaaaaaa’)
sheet2.write(0,0,‘this should overwrite2’)
sheet2.write(1,2,‘bbbbbbbbbbbbb’)
但实际上数据输入不可能是手一个一个录入啊,http://tianqi.2345.com/t/wea_history/js/56294_20112.js ,那么多数据,真不知道怎么自动化输入,这种挫败感让人很让人伤心加恼火。。。
一组数据往里添一行就行了,不用定坐标
那么多的天气 API 非要用这个啊?
搞成 json 用 python 写进 excel
这不就是 json 吗?
两个命令用管道连接一下即可
ConvertFrom-Json | ConvertTo-Csv
然后 Excel 打开,另存为 xls(x) 即可。
如果想直接弄成 xls(x),可以用 Excel.Application 对象操作 Excel https://msdn.microsoft.com/en-us/vba/excel-vba/articles/application-object-excel
手动几次生成了时间列表
[20111, 20112, 20113, 20114, 20115, 20116, 20117, 20118, 20119, 201110, 201111, 201112,20121, 20122, 20123, 20124, 20125, 20126, 20127, 20128, 20129, 201210, 201211, 201212,20131, 20132, 20133, 20134, 20135, 20136, 20137, 20138, 20139, 201310, 201311, 201312,20141, 20142, 20143, 20144, 20145, 20146, 20147, 20148, 20149, 201410, 201411, 201412,20151, 20152, 20153, 20154, 20155, 20156, 20157, 20158, 20159, 201510, 201511, 201512,20161, 20162,201603, 201604, 201605, 201606, 201607, 201608, 201609, 201610, 201611, 201612,201701, 201702, 201703, 201704, 201705, 201706, 201707, 201708, 201709]
跑起来,以 csv 格式写到文件里

