头歌平台数据可视化-第五关时间空间数据的可视化——等高线图

写下来主要是作为自己的笔记

数据读取

全球海温数据下载后是 .nc 格式的文件,它就是 Netcdf 文件。 NetCDF 全称为 Network Common Data Format,中文译法为“网络通用数据格式”。

Netcdf 文件开始的目的是用于存储气象科学中的数据,现在已经成为许多数据采集软件的生成文件的格式。

从数学上来说,Netcdf 存储的数据就是一个多自变量的单值函数。用公式来说就是f(x,y,z,…)=value 。

函数的自变量 x,y,z 等在 Netcdf 中叫做维(dimension)坐标轴(axix)。

函数值 value 在 Netcdf 中叫做变量(Variables)。

自变量和函数值在物理学上的一些性质,在 Netcdf 中就叫属性(Attributes)。

一个 Netcdf 文件的结构包括以下对象:

  • 变量(Variables) :变量对应着真实的物理数据。
  • 维(dimension):一个维对应着函数中的某个自变量,或者说函数图象中的一个坐标轴,在线性代数中就是一个N维向量的一个分量。
  • 属性(Attribute) :属性对变量值和维的具体物理含义的注释或者说解释。
  • 所以需要使用特定的读取功能库 —— netCDF4,安装命令为:pip install netcdf4

 读取全球海温数据并查看其所有属性:

from netCDF4 import Dataset
nc_obj = Dataset('ERsst.mnmean.nc')
for i in nc_obj.variables:
    print(i)
# 查看 sst 变量的信息
print(nc_obj.variables['sst'])

输出如下,为文件的各类信息:

lat
lon
time_bnds
time
sst

float32 sst(time, lat, lon)
    long_name: Monthly Means of Sea Surface Temperature
    units: degC
    var_desc: Sea Surface Temperature
    level_desc: Surface
    statistic: Mean
    missing_value: -9.96921e+36
    dataset: NOAA Extended Reconstructed SST V5
    parent_stat: Individual Values
    actual_range: [-1.8     42.32636]
    valid_range: [-1.8 45. ]
unlimited dimensions: time
current shape = (1973, 89, 180)
filling on, default _FillValue of 9.969209968386869e+36 used

 可以看出 sst 变量,在访问数据时需要传入三个参数,时间、纬度、经度。

查看 1958 年的全球海温数据:

from netCDF4 import Dataset
nc_obj = Dataset('ERsst.mnmean.nc')
temperature = nc_obj.variables['sst'][1958, :, :]
print(temperature)
print(temperature.shape)

输出结果:

[[-1.7999999523162842 -1.7999999523162842 -1.7999999523162842 ...
  -1.7999999523162842 -1.7999999523162842 -1.7999999523162842]
 [-1.7999999523162842 -1.7999999523162842 -1.7999999523162842 ...
  -1.7999999523162842 -1.7999999523162842 -1.7999999523162842]
 [-1.7999999523162842 -1.7999999523162842 -1.7999999523162842 ...
  -1.7999999523162842 -1.7999999523162842 -1.7999999523162842]
 ...
 [-- -- -- ... -- -- --]
 [-- -- -- ... -- -- --]
 [-- -- -- ... -- -- --]]
(89, 180)

可以看出,该数据只记载了海洋的温度,而大陆的温度由 -- 表示。

绘制全球海温等高线

绘制热力图

绘制全球海温时,首先要在图像上绘制出,全球海温各地数值,所以需先绘制全球海温的热力图。

from netCDF4 import Dataset
import matplotlib.pyplot as plt
import numpy as np
nc_obj = Dataset('ERsst.mnmean.nc')
temperature = nc_obj.variables['sst'][1958, :, :]
lat, lon = temperature.shape
plt.figure(figsize=(10, 5))
plt.imshow(temperature, cmap='Spectral_r')
x = plt.colorbar()
x.set_label('Temperature')
plt.show()

可视化效果如下:

头歌平台数据可视化-第五关时间空间数据的可视化——等高线图_第1张图片

图一 全球海温数据绘制热力图 

参数分析

plt.imshow() 其实就是将数组的值以图片的形式展示出来,数组的值对应着不同的颜色深浅,而数值的横纵坐标就是数组的索引,比如一个 1000X1000 的数组,图片里的点也就有 1000X1000 个,比如第一个行第一个点的坐标就是 (0,0),它的值会通过 colorbar (也就是 cmap 参数)反映出来,也就可以说 plt.imshow() 函数的功能就是把数值展示成热图。

cmap 参数是指绘制图像的颜色参考系,还有众多的颜色模板可以进行设置,如下图:

头歌平台数据可视化-第五关时间空间数据的可视化——等高线图_第2张图片

图二 颜色模板 

本次选用的就是 Spectral,相对而已比较符合温度的代表色彩,而 Spectral_r 后面的 _r 则表示颜色取反。

plt.colorbar() 就是创建一个子图,在绘制图像的旁边,用于显示数值与颜色的对应关系。

绘制等高线

绘制全球海温,可不只有热力图的绘制,还可以绘制等高线,来很直观的展示具有相同温度的海域,有较重要的研究意义。

from netCDF4 import Dataset
import matplotlib.pyplot as plt
import numpy as np
nc_obj = Dataset('ERsst.mnmean.nc')
temperature = nc_obj.variables['sst'][1958, :, :]
lat, lon = temperature.shape
X, Y = np.meshgrid(range(lon), range(lat))
plt.figure(figsize=(10, 5))
# 画出 8 个级别的线,并将颜色设置为黑色
contour = plt.contour(X, Y, temperature, 8, colors='k')
# 等高线上标明z(即高度)的值,字体大小是7,颜色分别是黑色
plt.clabel(contour, fontsize=7, colors='k')
plt.show()

可视化效果如下:

头歌平台数据可视化-第五关时间空间数据的可视化——等高线图_第3张图片

 图三 全球海温数据绘制等高线图

函数分析: 生成坐标矩阵

语法:X,Y = numpy.meshgrid(x, y)

参数 说明
x,y 网格点的横纵坐标列向量(非矩阵)
X,Y 坐标矩阵

X, Y = np.meshgrid(range(lon), range(lat)) 是用于生成网格点坐标矩阵的,具体将生成数组效果如下

lon = 180
lat = 89
X, Y = np.meshgrid(range(lon), range(lat))
print(X.shape, Y.shape)
print(X)
print(Y)
(89, 180) (89, 180)
[[  0   1   2 ... 177 178 179]
 [  0   1   2 ... 177 178 179]
 [  0   1   2 ... 177 178 179]
 ...
 [  0   1   2 ... 177 178 179]
 [  0   1   2 ... 177 178 179]
 [  0   1   2 ... 177 178 179]]
[[ 0  0  0 ...  0  0  0]
 [ 1  1  1 ...  1  1  1]
 [ 2  2  2 ...  2  2  2]
 ...
 [86 86 86 ... 86 86 86]
 [87 87 87 ... 87 87 87]
 [88 88 88 ... 88 88 88]]

输出中的 X 是将 [0, lon) 纵向复制 lat 份, Y 是将 [0, lat) 横向复制 lon 份,所以 XY 的矩阵形状都是一样的为 (89, 180)。将 X,Y 数据矩阵对应组合就会形成网格坐标,绘制等高线时需要网格进行线条的绘制。

绘制等高线语法:plt.contour([X, Y,] Z, [levels], **kwargs)

参数说明:

参数 作用
X,Y array-like,可选值 Z 的坐标。X 和 Y 必须都是 2-D,且形状与 Z 相同,或者它们必须都是 1-d,这样 len(X)== M 是 Z 中的列数,len(Y)== N 是 Z 中的行数 。
Z array-like(N,M)绘制等高线的高度值。
levels int 或类似数组,可选确定等高线/区域的数量和位置。如果int Ñ,使用 Ñ 数据间隔; 即绘制 n + 1 个等高线。水平高度自动选择。如果是数组,则在指定的级别绘制等高线。值必须按递增顺序排列。

编程要求

根据提示,在右侧编辑器补充代码,结合热力图以及等高线的绘制方法,绘制全球海温。

测试说明

平台会对你编写的代码进行测试。 效果图如下:

头歌平台数据可视化-第五关时间空间数据的可视化——等高线图_第4张图片

图四 绘制完成最终效果图 

import matplotlib as mpl
# linux终端下没有GUI,进行设置
mpl.use('Agg')
from netCDF4 import Dataset
import matplotlib.pyplot as plt
import numpy as np

nc_obj = Dataset('step5/ERsst.mnmean.nc')

########## Begin ##########
# 获取 1970 年的全球海温数据
temperature = nc_obj
temperature = temperature.variables['sst'][1970,:,:]
########## End ##########

lat, lon = temperature.shape

# 生成网格点坐标矩阵
X, Y = np.meshgrid(range(lon), range(lat))

# 添加画布,画布尺寸宽为 10,长为 5
plt.figure(figsize=(10, 5))

########## Begin ##########
# 传入海温数据绘制热力图,cmap 参数选择 coolwarm
plt.imshow(temperature, cmap='coolwarm')

########## End ##########

# 绘制色彩子图
x = plt.colorbar()

########## Begin ##########
# 设置子图标签,为 Temperature
x.set_label('Temperature')

########## End ##########

########## Begin ##########
# 画出 7 条线,并将颜色设置为红色
contour = plt.contour(X, Y, temperature,7, colors='r')

########## End ##########

# 等高线上标明z(即高度)的值,字体大小是7,颜色分别是红色
plt.clabel(contour, fontsize=7, colors='r')

# 保存图像
plt.savefig('step5/image1/test.png')

你可能感兴趣的:(头歌平台,大数据,信息可视化)