0001 function data = get_NCEP_forcing(Mobj, modelTime)
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045
0046
0047
0048
0049
0050
0051
0052
0053
0054
0055
0056 subname = 'get_NCEP_forcing';
0057
0058 global ftbverbose;
0059 if(ftbverbose);
0060 fprintf('\n')
0061 fprintf(['begin : ' subname '\n'])
0062 end
0063
0064
0065 if ~Mobj.have_lonlat
0066 error('Need spherical coordinates to extract the forcing data')
0067 else
0068
0069
0070 [dx, dy] = deal(2.5, 2.5);
0071 extents = [min(Mobj.lon(:))-(2*dx), max(Mobj.lon(:))+(2*dx), min(Mobj.lat(:))-dy, max(Mobj.lat(:))+dy];
0072 end
0073
0074 if modelTime(end) - modelTime(1) > 365
0075 error('Can''t (yet) process more than a year at a time.')
0076 end
0077
0078 yearStart = mjulian2greg(modelTime(1));
0079 yearEnd = mjulian2greg(modelTime(end));
0080 if yearEnd ~= yearStart
0081 error('Can''t (yet) process across a year boundary.')
0082 else
0083 year = yearEnd;
0084 end
0085
0086
0087 ncep.uwnd = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface_gauss/uwnd.10m.gauss.',num2str(year),'.nc'];
0088 ncep.vwnd = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface_gauss/vwnd.10m.gauss.',num2str(year),'.nc'];
0089 ncep.nlwrs = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface_gauss/nlwrs.sfc.gauss.',num2str(year),'.nc'];
0090 ncep.nswrs = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface_gauss/nswrs.sfc.gauss.',num2str(year),'.nc'];
0091 ncep.air = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface_gauss/air.2m.gauss.',num2str(year),'.nc'];
0092 ncep.rhum = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface/rhum.sig995.',num2str(year),'.nc'];
0093 ncep.prate = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface_gauss/prate.sfc.gauss.',num2str(year),'.nc'];
0094 ncep.slp = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface/slp.',num2str(year),'.nc'];
0095 ncep.lhtfl = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface_gauss/lhtfl.sfc.gauss.',num2str(year),'.nc'];
0096 ncep.shtfl = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface_gauss/shtfl.sfc.gauss.',num2str(year),'.nc'];
0097 ncep.pevpr = ['http://www.esrl.noaa.gov/psd/thredds/dodsC/Datasets/ncep.reanalysis/surface_gauss/pevpr.sfc.gauss.',num2str(year),'.nc'];
0098
0099 fields = fieldnames(ncep);
0100
0101 for aa=1:length(fields)
0102 data.(fields{aa}).data = [];
0103 data.(fields{aa}).time = [];
0104 data.(fields{aa}).lat = [];
0105 data.(fields{aa}).lon = [];
0106 data_attributes.(fields{aa}) = [];
0107
0108
0109 data_time = loaddap([ncep.(fields{aa}),'?time']);
0110 data_attributes.(fields{aa}) = loaddap('-A',[ncep.(fields{aa})]);
0111 timevec = datevec((data_time.time)/24+365);
0112 data.time = greg2mjulian(timevec(:,1), timevec(:,2), timevec(:,3), ...
0113 timevec(:,4), timevec(:,5), timevec(:,6));
0114
0115 data_time_mask = data.time >= modelTime(1) & data.time <= modelTime(end);
0116 data_time_idx = 1:size(data.time,1);
0117 data_time_idx = data_time_idx(data_time_mask);
0118 data.time = data.time(data_time_mask);
0119
0120
0121
0122
0123
0124
0125 data_lon = loaddap([ncep.(fields{aa}),'?lon']);
0126
0127
0128
0129
0130 clear index_lon index_lat
0131 if extents(1) < 0 && extents(2) < 0
0132
0133 extents(1) = extents(1) + 360;
0134 extents(2) = extents(2) + 360;
0135 index_lon = find(data_lon.lon > extents(1) & data_lon.lon < extents(2));
0136 elseif extents(1) < 0 && extents(2) > 0
0137
0138
0139
0140 index_lon{1} = find(data_lon.lon >= extents(1) + 360);
0141 index_lon{2} = find(data_lon.lon <= extents(2));
0142 else
0143
0144
0145 index_lon = find(data_lon.lon > extents(1) & data_lon.lon < extents(2));
0146 end
0147
0148
0149 data_lat = loaddap([ncep.(fields{aa}),'?lat']);
0150 index_lat = find(data_lat.lat > extents(3) & data_lat.lat < extents(4));
0151
0152
0153 if iscell(index_lon)
0154
0155 eval(['data1_west.(fields{aa}) = loaddap(''', ncep.(fields{aa}),'?',...
0156 fields{aa},'[', num2str(min(data_time_idx)-1),':',...
0157 num2str(max(data_time_idx)-1), '][',...
0158 num2str(min(index_lat)-1), ':', num2str(max(index_lat)-1),...
0159 '][', num2str(min(index_lon{1})-1), ':',...
0160 num2str(length(data_lon.lon)-1), ']'');']);
0161 eval(['data1_east.(fields{aa}) = loaddap(''', ncep.(fields{aa}),'?',...
0162 fields{aa}, '[', num2str(min(data_time_idx)-1),':',...
0163 num2str(max(data_time_idx)-1), '][',...
0164 num2str(min(index_lat)-1), ':', num2str(max(index_lat)-1),...
0165 '][', '0', ':', num2str(max(index_lon{2})-1), ']'');']);
0166
0167 structfields = fieldnames(data1_west.(fields{aa}).(fields{aa}));
0168 for ii=1:length(structfields)
0169 switch structfields{ii}
0170 case 'lon'
0171
0172
0173
0174 data1.(fields{aa}).(fields{aa}).(structfields{ii}) = ...
0175 [data1_west.(fields{aa}).(fields{aa}).(structfields{ii});data1_east.(fields{aa}).(fields{aa}).(structfields{ii})];
0176 case fields{aa}
0177
0178 data1.(fields{aa}).(fields{aa}).(structfields{ii}) = ...
0179 [data1_west.(fields{aa}).(fields{aa}).(structfields{ii}),data1_east.(fields{aa}).(fields{aa}).(structfields{ii})];
0180 otherwise
0181
0182
0183
0184
0185
0186
0187
0188 try
0189 tdata = data1_west.(fields{aa}).(fields{aa}).(structfields{ii}) - data1_east.(fields{aa}).(fields{aa}).(structfields{ii});
0190 if range(tdata(:)) == 0
0191
0192 data1.(fields{aa}).(fields{aa}).(structfields{ii}) = ...
0193 data1_west.(fields{aa}).(fields{aa}).(structfields{ii});
0194 else
0195 warning('Unexpected data field and the west and east halves don''t match. Skipping.')
0196 end
0197 catch
0198 warning('Unexpected data field and the west and east halves don''t match. Skipping.')
0199 end
0200 clear tdata
0201 end
0202 end
0203 else
0204
0205 eval(['data1.(fields{aa}) = loaddap(''', ncep.(fields{aa}),'?',...
0206 fields{aa}, '[', num2str(min(data_time_idx)-1),':',...
0207 num2str(max(data_time_idx)-1), '][',...
0208 num2str(min(index_lat)-1), ':', num2str(max(index_lat)-1),...
0209 '][', num2str(min(index_lon)-1), ':',...
0210 num2str(max(index_lon)-1), ']'');']);
0211 end
0212
0213 datatmp = squeeze(data1.(fields{aa}).(fields{aa}).(fields{aa}));
0214 datatmp = (datatmp * data_attributes.(fields{aa}).(fields{aa}).scale_factor) + data_attributes.(fields{aa}).(fields{aa}).add_offset;
0215
0216 data.(fields{aa}).data = cat(1, data.(fields{aa}).data, datatmp);
0217 data.(fields{aa}).time = cat(1, data.(fields{aa}).time, squeeze(data1.(fields{aa}).(fields{aa}).time));
0218 data.(fields{aa}).lat = squeeze(data1.(fields{aa}).(fields{aa}).lat);
0219 data.(fields{aa}).lon = squeeze(data1.(fields{aa}).(fields{aa}).lon);
0220 end
0221
0222
0223
0224
0225
0226
0227 data.prate.data = data.prate.data/1000;
0228
0229
0230
0231
0232
0233
0234
0235
0236
0237
0238
0239 Llv = 2.5*10^6;
0240 rho = 1025;
0241 Et = data.lhtfl.data/Llv/rho;
0242 data.P_E.data = data.prate.data-Et;
0243
0244
0245 WW = data.uwnd.data + data.vwnd.data * 1i;
0246 data.tau.data = stresslp(abs(WW),10);
0247 [data.tx.data,data.ty.data] = wstress(data.uwnd.data,data.vwnd.data,10);
0248 data.tx.data=reshape(data.tx.data*0.1, size(data.uwnd.data));
0249 data.ty.data=reshape(data.ty.data*0.1, size(data.uwnd.data));
0250
0251
0252 data.lon = data.uwnd.lon;
0253 data.lon(data.lon > 180) = data.lon(data.lon > 180) - 360;
0254 data.lat = data.uwnd.lat;
0255
0256
0257
0258
0259
0260
0261
0262
0263
0264
0265
0266