numpy 从ERA5再分析中提取移动中的船舶的时间和空间变量

snz8szmq  于 2022-11-10  发布在  其他
关注(0)|答案(1)|浏览(188)

我想要从一艘移动的船内的一个站点提取测量到的风,我有纬度、经度和时间值,以及空间中每个时间步长的风值。我可以提取所有时间步长在空间中的一个固定点,但我想要提取,例如,当船移动时,x时间步长的风是一个日期、经度和纬度。我如何从下面的代码中做到这一点?

data = xr.open_dataset('C:/Users/William Jacondino/Desktop/Dados/ERA5\\ERA5_2017.nc', decode_times=False)

dir_out = 'C:/Users/William Jacondino/Desktop/MovingShip'
if not os.path.exists(dir_out):
    os.makedirs(dir_out)

print("\nReading the observation station names:\n")

stations = pd.read_csv(r"C:/Users/William Jacondino/Desktop/MovingShip/Date-TIME.csv",index_col=0, sep='\;')

print(stations)

阅读观测站名称:

Latitude  Longitude
Date-Time                            
16/11/2017 00:00  0.219547 -38.247914
16/11/2017 06:00  0.861717 -38.188858
16/11/2017 12:00  1.529534 -38.131039
16/11/2017 18:00  2.243760 -38.067467
17/11/2017 00:00  2.961202 -38.009050
...                    ...        ...
10/12/2017 00:00 -5.775127 -35.206581
10/12/2017 06:00 -5.775120 -35.206598
10/12/2017 12:00 -5.775119 -35.206583
10/12/2017 18:00 -5.775122 -35.206584
11/12/2017 00:00 -5.775115 -35.206590

# variável tempo e unidade

times = data.variables['time'][:]
unit =  data.time.units

# variáveis latitude (lat) e longitude (lon)

lon = data.variables['longitude'][:]
lat = data.variables['latitude'][:]

# variável temperatura em 2 metros em celsius

temp = data.variables['t2m'][:]-275.15

# variável temperatura do ponto de orvalho em 2 metros em celsius

tempdw = data.variables['d2m'][:]-275.15

# variável sea surface temperature (sst) em celsius

sst = data.variables['sst'][:]-275.15

# variável Surface sensible heat flux sshf

sshf = data.variables['sshf'][:]
unitsshf = data.sshf.units

# variável Surface latent heat flux

slhf = data.variables['slhf'][:]
unitslhf = data.slhf.units

# variável Mean sea level pressure

msl = data.variables['msl'][:]/100
unitmsl = data.msl.units

# variável Total precipitation em mm/h

tp = data.variables['tp'][:]*1000

# componente zonal do vento em 100 metros

uten100 = data.variables['u100'][:]
unitu100 = data.u100.units

# componente meridional do vento em 100 metros

vten100  = data.variables['v100'][:]
unitv100 = data.v100.units

# componente zonal do vento em 10 metros

uten  = data.variables['u10'][:]
unitu = data.u10.units

# componente meridional do vento em 10 metros

vten  = data.variables['v10'][:]
unitv = data.v10.units

# calculando a velocidade do vento em 10 metros

ws    = (uten**2 + vten**2)**(0.5)

# calculando a velocidade do vento em 100 metros

ws100  = (uten100**2 + vten100**2)**(0.5)

# calculando os ângulos de U e V para obter a direção do vento em 10 metros

wdir = (180 + (np.degrees(np.arctan2(uten, vten)))) % 360

# calculando os ângulos de U e V para obter a direção do vento em 100 metros

wdir100 = (180 + (np.degrees(np.arctan2(uten100, vten100)))) % 360

for key, value in stations.iterrows():
    #print(key,value[0], value[1], value[2])
    station = value[0]
    file_name = "{}{}".format(station+'_1991',".csv")
    #print(file_name)
    lon_point = value[1]
    lat_point = value[2]
    ########################################

    # Encontrando o ponto de Latitude e Longitude mais próximo das estações

    # Squared difference of lat and lon
    sq_diff_lat = (lat - lat_point)**2
    sq_diff_lon = (lon - lon_point)**2

    # Identifying the index of the minimum value for lat and lon
    min_index_lat = sq_diff_lat.argmin()
    min_index_lon = sq_diff_lon.argmin()
    print("Generating time series for station {}".format(station))

    ref_date   = datetime.datetime(int(unit[12:16]),int(unit[17:19]),int(unit[20:22]))

    date_range   = list()
    temp_data    = list()
    tempdw_data = list()
    sst_data     = list()
    sshf_data    = list()
    slhf_data    = list()
    msl_data     = list()
    tp_data      = list()
    uten100_data = list()
    vten100_data = list()
    uten_data    = list()
    vten_data    = list()
    ws_data      = list()
    ws100_data   = list()
    wdir_data    = list()
    wdir100_data = list()

    for index, time in enumerate(times):
        date_time = ref_date+datetime.timedelta(hours=int(time))
        date_range.append(date_time)
        temp_data.append(temp[index, min_index_lat, min_index_lon].values)
        tempdw_data.append(tempdw[index, min_index_lat, min_index_lon].values)
        sst_data.append(sst[index, min_index_lat, min_index_lon].values)
        sshf_data.append(sshf[index, min_index_lat, min_index_lon].values)
        slhf_data.append(slhf[index, min_index_lat, min_index_lon].values)
        msl_data.append(msl[index, min_index_lat, min_index_lon].values)
        tp_data.append(tp[index, min_index_lat, min_index_lon].values)
        uten100_data.append(uten100[index, min_index_lat, min_index_lon].values)
        vten100_data.append(vten100[index, min_index_lat, min_index_lon].values)
        uten_data.append(uten[index, min_index_lat, min_index_lon].values)
        vten_data.append(vten[index, min_index_lat, min_index_lon].values)
        ws_data.append(ws[index,min_index_lat,min_index_lon].values)
        ws100_data.append(ws100[index,min_index_lat,min_index_lon].values)
        wdir_data.append(wdir[index,min_index_lat,min_index_lon].values)
        wdir100_data.append(wdir100[index,min_index_lat,min_index_lon].values)
    ################################################################################    

    #print(date_range)

    df = pd.DataFrame(date_range, columns = ["Date-Time"])
    df["Date-Time"] = date_range
    df = df.set_index(["Date-Time"])
    df["WS10  ({})".format(unitu)] = ws_data
    df["WDIR10  ({})".format(units.deg)] = wdir_data
    df["WS100  ({})".format(unitu)] = ws100_data
    df["WDIR100  ({})".format(units.deg)] = wdir100_data
    df["Chuva({})".format(units.mm)] = tp_data 
    df["MSLP ({})".format(units.hPa)] = msl_data
    df["T2M ({})".format(units.degC)] = temp_data
    df["Td2M ({})".format(units.degC)] = tempdw_data
    df["Surface Sensible Heat Flux ({})".format(unitsshf)] = sshf_data                      
    df["Surface latent heat flux ({})".format(unitslhf)] = slhf_data 
    df["U10  ({})".format(unitu)] = uten_data
    df["V10  ({})".format(unitv)] = vten_data
    df["U100  ({})".format(unitu100)] = uten100_data
    df["V100  ({})".format(unitv100)] = vten100_data
    df["TSM ({})".format(units.degC)] = sst_data

    print("The following time series is being saved as .csv files")

    df.to_csv(os.path.join(dir_out,file_name), sep=';',encoding="utf-8", index=True)

print("\n! !Successfuly saved all the Time Series the output Directory!!\n{}".format(dir_out))

我提取空间中给定点的固定变量的代码是这样的,但我希望在船舶移动期间提取,例如,在11/12/2017 00:00,纬度-5.775115和经度-35.206590我有一个风值,在下一个时间步长中,对于另一个纬度x经度,我有另一个值。我怎样才能使我的代码适应这种情况呢?

mqkwyuun

mqkwyuun1#

这是XARRAY的高级索引的另一个完美用例!我觉得用户指南的这部分需要一个斗篷和一首主题曲:)
我将使用一个虚构的数据集和一组站点,它们与您的相似(我认为)。第一步是重置日期-时间索引,这样您就可以使用它从xarray.Dataset中提取最接近的时间值,因为您需要一个用于时间、经度和经度的公共索引:

In [14]: stations = stations.reset_index(drop=False)
    ...: stations
Out[14]:
            Date-Time   Latitude   Longitude
0 2017-11-16 00:00:00   0.219547  -38.247914
1 2017-11-16 06:00:00   0.861717  -38.188858
2 2017-11-16 12:00:00   1.529534  -38.131039
3 2017-11-16 18:00:00   2.243760  -38.067467
4 2017-11-17 00:00:00   2.961202  -38.009050
5 2017-12-10 00:00:00  -5.775127  -35.206581
6 2017-12-10 06:00:00  -5.775120  -35.206598
7 2017-12-10 12:00:00  -5.775119  -35.206583
8 2017-12-10 18:00:00  -5.775122  -35.206584
9 2017-12-11 00:00:00  -5.775115  -35.206590

In [15]: ds
Out[15]:
<xarray.Dataset>
Dimensions:  (lat: 40, lon: 40, time: 241)
Coordinates:
  * lat      (lat) float64 -9.75 -9.25 -8.75 -8.25 -7.75 ... 8.25 8.75 9.25 9.75
  * lon      (lon) float64 -44.75 -44.25 -43.75 -43.25 ... -26.25 -25.75 -25.25
  * time     (time) datetime64[ns] 2017-11-01 2017-11-01T06:00:00 ... 2017-12-31
Data variables:
    temp     (lat, lon, time) float64 0.07366 0.3448 0.2456 ... 0.3081 0.4236
    tempdw   (lat, lon, time) float64 0.07366 0.3448 0.2456 ... 0.3081 0.4236
    sst      (lat, lon, time) float64 0.07366 0.3448 0.2456 ... 0.3081 0.4236
    ws       (lat, lon, time) float64 0.07366 0.3448 0.2456 ... 0.3081 0.4236
    ws100    (lat, lon, time) float64 0.07366 0.3448 0.2456 ... 0.3081 0.4236
    wdir     (lat, lon, time) float64 0.07366 0.3448 0.2456 ... 0.3081 0.4236
    wdir100  (lat, lon, time) float64 0.07366 0.3448 0.2456 ... 0.3081 0.4236

使用高级索引规则,如果我们使用DataArray作为索引器从DataSet中进行选择,则结果将被重塑以匹配索引器。这意味着我们可以获取您的站点 Dataframe ,它具有时间、经度和经度,并从xarray数据集中提取最接近的索引

In [16]: ds_over_observations = ds.sel(
    ...:     time=stations["Date-Time"].to_xarray(),
    ...:     lat=stations["Latitude"].to_xarray(),
    ...:     lon=stations["Longitude"].to_xarray(),
    ...:     method="nearest",
    ...: )

现在,我们的数据与您的 Dataframe 具有相同的索引!

In [17]: ds_over_observations
Out[17]:
<xarray.Dataset>
Dimensions:  (index: 10)
Coordinates:
    lat      (index) float64 0.25 0.75 1.75 2.25 ... -5.75 -5.75 -5.75 -5.75
    lon      (index) float64 -38.25 -38.25 -38.25 ... -35.25 -35.25 -35.25
    time     (index) datetime64[ns] 2017-11-16 ... 2017-12-11
  * index    (index) int64 0 1 2 3 4 5 6 7 8 9
Data variables:
    temp     (index) float64 0.1887 0.222 0.6754 0.919 ... 0.1134 0.9231 0.6095
    tempdw   (index) float64 0.1887 0.222 0.6754 0.919 ... 0.1134 0.9231 0.6095
    sst      (index) float64 0.1887 0.222 0.6754 0.919 ... 0.1134 0.9231 0.6095
    ws       (index) float64 0.1887 0.222 0.6754 0.919 ... 0.1134 0.9231 0.6095
    ws100    (index) float64 0.1887 0.222 0.6754 0.919 ... 0.1134 0.9231 0.6095
    wdir     (index) float64 0.1887 0.222 0.6754 0.919 ... 0.1134 0.9231 0.6095
    wdir100  (index) float64 0.1887 0.222 0.6754 0.919 ... 0.1134 0.9231 0.6095

您可以使用.to_dataframe将其转储到Pandas中:

In [18]: df = ds_over_observations.to_dataframe()

In [19]: df
Out[19]:
        lat    lon                time      temp    tempdw       sst        ws     ws100      wdir   wdir100
index
0      0.25 -38.25 2017-11-16 00:00:00  0.188724  0.188724  0.188724  0.188724  0.188724  0.188724  0.188724
1      0.75 -38.25 2017-11-16 06:00:00  0.222025  0.222025  0.222025  0.222025  0.222025  0.222025  0.222025
2      1.75 -38.25 2017-11-16 12:00:00  0.675417  0.675417  0.675417  0.675417  0.675417  0.675417  0.675417
3      2.25 -38.25 2017-11-16 18:00:00  0.919019  0.919019  0.919019  0.919019  0.919019  0.919019  0.919019
4      2.75 -38.25 2017-11-17 00:00:00  0.566266  0.566266  0.566266  0.566266  0.566266  0.566266  0.566266
5     -5.75 -35.25 2017-12-10 00:00:00  0.652490  0.652490  0.652490  0.652490  0.652490  0.652490  0.652490
6     -5.75 -35.25 2017-12-10 06:00:00  0.429541  0.429541  0.429541  0.429541  0.429541  0.429541  0.429541
7     -5.75 -35.25 2017-12-10 12:00:00  0.113352  0.113352  0.113352  0.113352  0.113352  0.113352  0.113352
8     -5.75 -35.25 2017-12-10 18:00:00  0.923058  0.923058  0.923058  0.923058  0.923058  0.923058  0.923058
9     -5.75 -35.25 2017-12-11 00:00:00  0.609493  0.609493  0.609493  0.609493  0.609493  0.609493  0.609493

结果中的指数与站点数据中的指数相同。如果您愿意,可以使用pd.concat([stations, df], axis=1).set_index("Date-Time")合并原始值,以恢复原始索引以及所有天气数据:

In [20]: pd.concat([stations, df], axis=1).set_index("Date-Time")
Out[20]:
                     Latitude  Longitude   lat    lon                time      temp    tempdw       sst        ws     ws100      wdir   wdir100
Date-Time
2017-11-16 00:00:00  0.219547 -38.247914  0.25 -38.25 2017-11-16 00:00:00  0.188724  0.188724  0.188724  0.188724  0.188724  0.188724  0.188724
2017-11-16 06:00:00  0.861717 -38.188858  0.75 -38.25 2017-11-16 06:00:00  0.222025  0.222025  0.222025  0.222025  0.222025  0.222025  0.222025
2017-11-16 12:00:00  1.529534 -38.131039  1.75 -38.25 2017-11-16 12:00:00  0.675417  0.675417  0.675417  0.675417  0.675417  0.675417  0.675417
2017-11-16 18:00:00  2.243760 -38.067467  2.25 -38.25 2017-11-16 18:00:00  0.919019  0.919019  0.919019  0.919019  0.919019  0.919019  0.919019
2017-11-17 00:00:00  2.961202 -38.009050  2.75 -38.25 2017-11-17 00:00:00  0.566266  0.566266  0.566266  0.566266  0.566266  0.566266  0.566266
2017-12-10 00:00:00 -5.775127 -35.206581 -5.75 -35.25 2017-12-10 00:00:00  0.652490  0.652490  0.652490  0.652490  0.652490  0.652490  0.652490
2017-12-10 06:00:00 -5.775120 -35.206598 -5.75 -35.25 2017-12-10 06:00:00  0.429541  0.429541  0.429541  0.429541  0.429541  0.429541  0.429541
2017-12-10 12:00:00 -5.775119 -35.206583 -5.75 -35.25 2017-12-10 12:00:00  0.113352  0.113352  0.113352  0.113352  0.113352  0.113352  0.113352
2017-12-10 18:00:00 -5.775122 -35.206584 -5.75 -35.25 2017-12-10 18:00:00  0.923058  0.923058  0.923058  0.923058  0.923058  0.923058  0.923058
2017-12-11 00:00:00 -5.775115 -35.206590 -5.75 -35.25 2017-12-11 00:00:00  0.609493  0.609493  0.609493  0.609493  0.609493  0.609493  0.609493

相关问题