ERA5风场速度提取(某区域某时间段),u/v合成风向计算,python绘图。

【风场数据下载】

ERA5 monthly averaged data on single levels from 1940 to present (copernicus.eu)

勾选所需的数据和时间,下载NC文件。

(我这里下载了02-20年的10m风场的u分量+v分量+风速大小)

【提取NC文件的风速值】

拿到NC文件首先看看它的相关信息。

import netCDF4 as nc

file_path = "/mnt/g/aaa/wind/02_20.nc"
wind_data = nc.Dataset(file_path)

print(wind_data)
print(wind_data.variables['u10'])
print(wind_data.variables['si10'])

主要是看数据的维度。(维度就是帮助我们将数据分层分类,以便更好的进行索引,以前的文章中有详细解释,可以看看)

 代码如下,如何提取研究区的经纬度可以参考(8条消息) ArcGIS提取栅格格网点经纬度,导出为CSV/TXT(面转栅格,再栅格转点)_arcgis 导出csv_胡修修的博客-CSDN博客

import os
import matplotlib
import numpy as np
from datetime import datetime
from datetime import timedelta
import netCDF4 as nc
import glob
import json
import matplotlib.pyplot as plt
from osgeo import gdal
import pandas as pd
from scipy import interpolate
from scipy import ndimage
from nansat import Nansat
import common_lib as clib
import pandas

ERA5_BASE_TIME = datetime(year=1900, month=1, day=1)

#提取NC文件中的相应数据
file_path = "/mnt/g/aaa/wind/02_20.nc"    
wind_data = nc.Dataset(file_path)

lon_arr = wind_data.variables['longitude'][:]
lat_arr = wind_data.variables['latitude'][:]
wind_time = wind_data.variables['time'][:]
u10 = wind_data.variables['u10'][:]
v10 = wind_data.variables['v10'][:]
si10 = wind_data.variables['si10'][:]

#将经纬度转为grid格式,并用flatten()把它从二维变为一维
lon_grid, lat_grid = np.meshgrid(lon_arr, lat_arr)
lon_grid = lon_grid.flatten()
lat_grid = lat_grid.flatten()

#读取研究区域的经纬度文件"/mnt/g/aaa/gate_shape/MIZ_lon_lat_arr.csv"
miz_extent_data = np.loadtxt("/mnt/g/aaa/gate_shape/MIZ_lon_lat_arr.csv",skiprows=1, delimiter=",")
lon_arr_miz = miz_extent_data[:,0]
lat_arr_miz = miz_extent_data[:,1]

#循环计算出在NC文件上,离研究区域的每个点最近的经纬度的index,就可以利用index索引研究区域的数据。
for i in range(len(lon_arr_miz)):
    lon = lon_arr_miz[i]
    lat = lat_arr_miz[i]
    distance = (lon_grid - lon)**2 + (lat_grid - lat)**2
    index = np.argmin(distance)
    pass

sub_u10 = []
sub_v10 = []
sub_si10 = []
monthly_time = []
for i in range(len(wind_time)):
    key = ERA5_BASE_TIME + timedelta(hours=int(wind_time[i]))
    monthly_time.append(key)
    sub_u10.append(u10[i].flatten()[index])
    sub_v10.append(v10[i].flatten()[index])
    sub_si10.append(si10[i].flatten()[index])

sub_lon, sub_lat = lon_grid[index], lat_grid[index]
    
#下面开始算风速方向
deg = 180.0/np.pi
monthly_time_p = []
sub_si10_p = []
wdir = []

#用循环将每年12月的风速一个个输出到sub_si10_p[],并将12月平均风向一个个加到wdir[]
for i, t in enumerate(monthly_time):
    if t.month == 12:
        monthly_time_p.append(t)
        sub_si10_p.append(np.nanmean(sub_si10[i]))
#利用u/v计算风速方向
        wdir.append(180.0 + np.arctan2(np.nanmean(sub_u10[i]), np.nanmean(sub_v10[i]))*deg)

#将结果输出为csv
dataframe = pandas.DataFrame({"time": monthly_time_p, "wspd": sub_si10_p, "wdir":wdir})
dataframe.to_csv(f"wind_0220.csv", index=False)

 到这里就完成了风速和风向角度的提取啦,可以在EXCEL里面绘图。

注意,这里计算风向角度用的公式是按照气象学上的定义。

气象上定义正北方向为0°(即风从北吹向南,是数学坐标系中的 -90°), 顺时针转动角度增大。

风向Dir=0°(或360°), u=0, v<0, 正北风;

风向Dir=90°, u<0, v=0,正东风;

风向Dir=180°, u=0, v>0,正南风;

风向Dir=270°, u>0, v=0,正西风。

当然也可以用PYTHON,粗糙代码和结果图如下:

fig, ax = plt.subplots(figsize=(10, 4))
ax.plot(monthly_time_p, sub_si10_p, alpha=1, marker='o')
    
ax.set_ylim(0, 17.5)
ax.set_ylabel('Wind (m/s)', fontsize=18)
ax.set_xlabel('Time', fontsize=8)
ax.set_xticks(monthly_time_p[::1])
ax.set_xticklabels([datetime.strftime(t, '%Y') for t in monthly_time_p[::1]])
matplotlib.dates.DateFormatter('%Y-%m')

ax.grid(True)

fig.tight_layout()
plt.savefig(f'wind.png')

 

风向的计算参考:(8条消息) u, v风和风速风向的相互转换_风的u分量和v分量计算风速_气海同途的博客-CSDN博客

猜你喜欢

转载自blog.csdn.net/Mluoo/article/details/130115308