《Python编程从入门到实践 第二版》第十六章练习

Python编程:比较锡特卡与死亡谷的气候数据
本篇博客探讨了如何利用Python分析锡特卡和死亡谷的气候数据,包括降雨量的可视化、温度的比较以及气象数据的自动索引和重构。通过对CSV文件的处理,提取了TMIN和TMAX列,并创建了图表以便于直观比较两地区的温度范围。此外,还讨论了如何从JSON文件中提取地震数据,生成动态标题以及展示全球火灾分布的散点图。
部署运行你感兴趣的模型镜像

16-1 锡特卡的降雨量 锡特卡属于温带雨林,降水量非常丰富。在数据文件sitka_weather_2018_simple.csv中,文件头PRCP表示的是每日降水量。请对这列数据进行可视化。如果你想知道沙漠的降水量有多低,可针对死亡谷完成同样的练习。

import csv

import matplotlib.pyplot as plt

from datetime import datetime

filename = 'D:/Sublime Text/python_test/16/sitka_weather_2018_simple.csv'

with open(filename) as f:
	reader = csv.reader(f)
	header_row = next(reader)

	# 从文件中获取每日降水量
	prcps = []
	for row in reader:
		prcp = float(row[3])
		prcps.append(prcp)

# 根据每日降水量绘制图形
plt.style.use('seaborn')
fig,ax = plt.subplots()
ax.plot(prcps,c='red')

# 设置图形格式
ax.set_title('锡特卡的降雨量',fontsize=24)
ax.set_xlabel('',fontsize=16)
ax.set_ylabel('PRCP',fontsize=16)

# 显示表格
plt.show()

16-2 比较锡特卡和死亡谷的温度 在有关锡特卡和死亡谷的图表中,温度刻度反映了数据范围的不同。为准确比较锡特卡和死亡谷的温度范围,需要在y轴上使用相同的刻度。
为此,请修改图16-5和图16-6所示图表的y轴设置,对锡特卡和死亡谷的温度范围进行直接比较(也可对任何两个地方的温度范围进行比较)。

import csv 

import matplotlib.pyplot as plt

from datetime import datetime

def weather_data(filename,dates,highs,lows,t_date,t_high,t_low):
	
	with open(filename) as f:
		reader = csv.reader(f)
		header_row = next(reader)

		# 从文件中获取日期、最高温度和最低温度
		for row in reader:
			current_date = datetime.strptime(row[t_date],'%Y-%m-%d')
			try:
				high = int(row[t_high])
				low = int(row[t_low])
			except ValueError:
				print(f'Missing data for {current_date}')
			else:
				dates.append(current_date)
				highs.append(high)
				lows.append(low)


# 获得锡特卡的温度
filename = 'D:/Sublime Text/python_test/16/sitka_weather_2018_simple.csv'
dates,highs,lows = [],[],[]
weather_data(filename,dates,highs,lows,t_date=2,t_high=5,t_low=6)

# 根据锡特卡的数据绘制图形
plt.style.use('seaborn')
fig,ax = plt.subplots()
ax.plot(dates,highs,c='red',alpha=0.7)
ax.plot(dates,lows,c='green',alpha=0.7)
plt.fill_between(dates,highs,lows,facecolor='green',alpha=0.1)

# 获得死亡谷的温度
filename = 'D:/Sublime Text/python_test/16/death_valley_2018_simple.csv'
dates,highs,lows = [],[],[]
weather_data(filename,dates,highs,lows,t_date=2,t_high=4,t_low=5)

# 根据死亡谷的数据绘制图形
ax.plot(dates,highs,c='red',alpha=0.7)
ax.plot(dates,lows,c='blue',alpha=0.7)
plt.fill_between(dates,highs,lows,facecolor='blue',alpha=0.1)

# 设置图形的格式
ax.set_title('Sitaka and Death Vally temperatures',fontsize=24)
ax.set_xlabel('',fontsize=16)
ax.set_ylabel('temperature(F)',fontsize=16)
ax.tick_params(axis='both',which='major',labelsize=16)
# 设置y轴上下限
plt.ylim(10,130)

# 显示表格
plt.show()

16-4 自动索引 本节以硬编码的方式指定了TMIN 和TMAX 列的索引。请根据文件头行确定这些列的索引,让程序同时适用于锡特卡和死亡谷。另外,请根据气象站的名称自动生成图表的标题。

import csv 

import matplotlib.pyplot as plt

from datetime import datetime

filename = 'D:/Sublime Text/python_test/16/sitka_weather_2018_simple.csv'
filename = 'D:/Sublime Text/python_test/16/death_valley_2018_simple.csv'
place_name = ''
	
with open(filename) as f:
	reader = csv.reader(f)
	header_row = next(reader)
	t_name = header_row.index('NAME')
	t_date = header_row.index('DATE')
	t_high = header_row.index('TMAX')
	t_low = header_row.index('TMIN')

	# 从文件中获取日期、最高温度和最低温度
	dates,highs,lows = [],[],[]
	for row in reader:
		# 如果没有气象站名字,就获取它
		if not place_name:
			place_name = row[t_name]
			print(place_name)

		current_date = datetime.strptime(row[t_date],'%Y-%m-%d')
		try:
			high = int(row[t_high])
			low = int(row[t_low])
		except ValueError:
			print(f'Missing data for {current_date}')
		else:
			dates.append(current_date)
			highs.append(high)
			lows.append(low)

# 根据最高气温和最低气温绘制图形
plt.style.use('seaborn')
fig,ax = plt.subplots()
ax.plot(dates,highs,c='red',alpha=0.7)
ax.plot(dates,lows,c='green',alpha=0.7)
plt.fill_between(dates,highs,lows,facecolor='green',alpha=0.1)


# 设置图形的格式
ax.set_title('Sitaka and Death Vally temperatures',fontsize=24)
ax.set_xlabel('',fontsize=16)
ax.set_ylabel('temperature(F)',fontsize=16)
ax.tick_params(axis='both',which='major',labelsize=16)

# 显示表格
plt.show()

16-6 重构 在从all_eq_dicts 中提取数据的循环中,使用了变量来指向震级、经度、纬度和标题,再将这些值分别附加到相应列表的末尾。这旨在清晰地演示如何从JSON文件中提取数据,但并非必须这样做。你也可以不使用这些临时变量,而是直接从eq_dict 中提取这些值,并将其附加到相应的列表末尾。这样做将缩短这个循环的循环体,使其只包含4行代码。

import json

# 探索数据的结构
filename = 'D:/Sublime Text/python_test/16/eq_data_1_day_m1.json'
with open(filename) as f:
	all_eq_data = json.load(f)

all_eq_dicts = all_eq_data['features']

mags = [eq_dict['properties']['mag'] for eq_dict in all_eq_dicts]
titles = [eq_dict['properties']['title'] for eq_dict in all_eq_dicts]
lons = [eq_dict['geometry']['coordinates'][0] for eq_dict in all_eq_dicts]
lats = [eq_dict['geometry']['coordinates'][1] for eq_dict in all_eq_dicts]

print(mags[:10])
print(titles[:2])
print(lons[:5])
print(lats[:5])

16-7 自动生成标题 本节定义my_layout 时以手工方式指定标题,这意味着每次变更源文件时,都需要修改标题。你可以不这样做,而是使用JSON文件中元数据(metadata)部分的数据集标题。为此,可提取这个值,将其赋给一个变量,并在定义my_layout 时使用这个变量来指定散点图的标题。

import plotly.express as px

import pandas as pd

import json

# 探索数据的结构
filename = 'D:/Sublime Text/python_test/16/eq_data_1_day_m1.json'
with open(filename) as f:
	all_eq_data = json.load(f)

all_eq_dicts = all_eq_data['features']


# 在"geometry" 键关联的字典中,有一个"coordinates" 键,它关联到一个列表,而列表中的前两个值为经度和纬度。
mags,titles,lons,lats = [],[],[],[]
for eq_dict in all_eq_dicts:
	mag = eq_dict['properties']['mag']
	title = eq_dict['properties']['title']
	lon = eq_dict['geometry']['coordinates'][0]
	lat = eq_dict['geometry']['coordinates'][1]
	mags.append(mag)
	titles.append(title)
	lons.append(lon)
	lats.append(lat)

data = pd.DataFrame(
	data=zip(lons,lats,titles,mags),columns=["经度","纬度","位置","震级"]
)
data.head()

fig = px.scatter(
	data,
	x="经度",
	y="纬度",
	range_x=[-200,200],
	range_y=[-90,90],
	width=800,
	height=800,
	title=all_eq_data['metadata']['title'],
	size="震级",
	size_max=10,
	color="震级",
	hover_name="位置",

)
fig.write_html("global_earthquakes.html")
fig.show()

if __name__ == '__main__':
	print(mags[:10])
	print(titles[:2])
	print(lons[:5])
	print(lats[:5])

16-8 最近发生的地震 请在本书配套资源中找到关于最近1小时、1天、7天和30天内地震信息的数据文件(截至本书出版时,参见文件夹chapter_16/Excercise16-8)。请使用其中一个数据集,绘制一幅散点图来展示最近发生的地震。

import plotly.express as px

import pandas as pd

import json

# 探索数据的结构
filename = 'D:/Sublime Text/python_test/16/all_day.geojson'
with open(filename) as f:
	all_eq_data = json.load(f)

all_eq_dicts = all_eq_data['features']

mags = [eq_dict['properties']['mag'] for eq_dict in all_eq_dicts]
titles = [eq_dict['properties']['title'] for eq_dict in all_eq_dicts]
lons = [eq_dict['geometry']['coordinates'][0] for eq_dict in all_eq_dicts]
lats = [eq_dict['geometry']['coordinates'][1] for eq_dict in all_eq_dicts]

data = pd.DataFrame(
	data=zip(lons,lats,titles,mags),columns=["经度","纬度","位置","震级"]
)
data.head()

fig = px.scatter(
	data,
	x="经度",
	y="纬度",
	range_x=[-200,200],
	range_y=[-90,90],
	width=800,
	height=800,
	title=all_eq_data['metadata']['title'],
	size="震级",
	size_max=10,
	color="震级",
	hover_name="位置",

)
fig.write_html("global_earthquakes.html")
fig.show()

if __name__ == '__main__':
	print(mags[:10])
	print(titles[:2])
	print(lons[:5])
	print(lats[:5])

16-9 全球火灾 在本章的配套资源中,有一个名为world_fires_1_day.csv的文件。它包含了有关全球各地发生的火灾信息,包括经度、纬度和火灾强度(brightness)。使用16.1节介绍的数据处理技术以及16.2节介绍的散点图绘制技术,绘制一幅散点图来展示全球哪些地方发生了火灾。

import csv

import plotly.graph_objects as go

import pandas as pd

data = pd.read_csv('D:/Sublime Text/python_test/16/world_fires_1_day.csv')
data.head()

fig = go.Figure(go.Densitymapbox(lat=data['latitude'],
								 lon=data['longitude'],
								 z=data['brightness'],
								 radius=4))
fig.update_layout(mapbox_style="open-street-map")

fig.show()

您可能感兴趣的与本文相关的镜像

Python3.10

Python3.10

Conda
Python

Python 是一种高级、解释型、通用的编程语言,以其简洁易读的语法而闻名,适用于广泛的应用,包括Web开发、数据分析、人工智能和自动化脚本

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值