/[MITgcm]/MITgcm_contrib/gael/profilesMatlabProcessing/netcdf_ecco_GenericgridMatFirstStep_4points.m
ViewVC logotype

Annotation of /MITgcm_contrib/gael/profilesMatlabProcessing/netcdf_ecco_GenericgridMatFirstStep_4points.m

Parent Directory Parent Directory | Revision Log Revision Log | View Revision Graph Revision Graph


Revision 1.3 - (hide annotations) (download)
Thu May 13 19:42:34 2010 UTC (15 years, 2 months ago) by gforget
Branch: MAIN
CVS Tags: HEAD
Changes since 1.2: +0 -0 lines
FILE REMOVED
moving to profiles_genericgrid directory

1 gforget 1.1 %
2     %function: netcdf_ecco_GenericgridMatFirstStep
3     %object: compute the additional information to use an "ECCO format" data set with a non latlon grid
4     %author: Gael Forget (gforget@mit.edu)
5     %date: June 12th, 2007
6     %
7     %inputs:
8     % - an "ECCO format" data set and grid files (profilesXCincl1PointOverlap* etc)
9     % that the model should generate when you first try to run pkg/profiles
10     % with a non latlon grid
11     % - directories for I/O
12     % - lat_polar (see below)
13     %output: mat files that are then fed to netcdf_ecco_GenericgridMat2Nc (step 2)
14     %
15     %lat_polar: positive value smaller than 90
16     % [in Cube Sphere/Polar Cap case]
17     % lat_polar should be set to the latitude beyond which lies the cube polar tiles (all of the tile grid points)
18     % -> there we start by project coordinates on the polar tangent plane because the lat/lon system collapes at the pole
19     % -> we refer to this operation as "polar switch" below
20     % [in other grids that do not include the poles]
21     % set it to 85
22     %
23     %rk: below you will find a parameter [choice_plot] do do some display
24     %
25     function []=netcdf_ecco_GenericgridMatFirstStep_4points(file_data,rep_data,rep_grid,rep_out,lat_polar);
26    
27     warning off MATLAB:mir_warning_variable_used_as_function;
28    
29     fprintf('\n WARNING from netcdf_ecco_GenericgridMatFirstStep.m : \n');
30     fprintf('please have a look at netcdf_ecco_GenericgridNOTEONOVERLAPCORNERS \n\n');
31    
32    
33    
34     %choice to do some visual chek or not
35     choice_plot=0; if choice_plot==1; figure; end; fprintf('visualization off \n\n');
36    
37    
38     %longitude systems: 1 <-> degree east from Greenwich [0 360] // 2 <-> degree east and west [-180 180]
39     lonSystModel=2;
40     if lonSystModel==1; fprintf('the script below assumes [-180 +180] longitudes => please do not change \n'); return; end
41     %-> both model and observations will first be switched to this system
42    
43    
44    
45    
46     eval(['ncload ' rep_data file_data ' prof_lon prof_lat;']);
47    
48     %set the longitude system for observations:
49     [prof_lon]=netcdf_ecco_GenericgridRotateLon(prof_lon,0,0,lonSystModel);
50     prof_lonM2=prof_lon; prof_latM2=prof_lat;
51    
52     list_subsets=[1:4];
53    
54     for subset_cur=list_subsets
55     switch subset_cur
56     case 1
57     switch_to_polar=0;
58     list_profilesM2=find((prof_lonM2>=-90&prof_lonM2<90)&abs(prof_latM2)<lat_polar);
59     suff_cur='latlon1'; fprintf('computing mid latitudes, part 1 \n');
60     case 2
61     switch_to_polar=0;
62     list_profilesM2=find((prof_lonM2<-90|prof_lonM2>=90)&abs(prof_latM2)<lat_polar);
63     suff_cur='latlon2'; fprintf('computing mid latitudes, part 2 \n');
64     case 3
65     switch_to_polar=1;
66     list_profilesM2=find(prof_latM2>=switch_to_polar*lat_polar);
67     suff_cur='northpole'; fprintf('computing high latitude, northern hemisphere \n');
68     case 4
69     switch_to_polar=-1;
70     list_profilesM2=find(prof_latM2<=switch_to_polar*lat_polar);
71     suff_cur='southpole'; fprintf('computing high latitude, southern hemisphere \n');
72     end
73     prof_lonM1=prof_lonM2(list_profilesM2); prof_latM1=prof_latM2(list_profilesM2);
74    
75     %do the "polar switch" for the data
76     [prof_lonM1,prof_latM1]=netcdf_ecco_GenericgridPolarPlaneCoords(prof_lonM1,prof_latM1,switch_to_polar);
77    
78    
79     eval(['files_list=ls('' -1 ' rep_grid 'profilesXC*.data '');']);
80     tmp1=files_list; tmp2=strfind(files_list,rep_grid)+length(rep_grid);
81     tmp3=strfind(files_list,'.data')+4;
82     files_list='';
83     for tmp4=1:length(tmp2);
84     files_list=strvcat(files_list, tmp1(tmp2(tmp4):tmp3(tmp4)) );
85     end
86    
87    
88     for tcur=1:size(files_list,1)
89    
90     prof_interp_XC11=NaN*zeros(length(prof_lonM2),1); prof_interp_YC11=prof_interp_XC11;
91     prof_interp_XCNINJ=prof_interp_XC11; prof_interp_YCNINJ=prof_interp_XC11;
92     prof_interp_i=NaN*zeros(length(prof_lonM2),4); prof_interp_j=prof_interp_i; prof_interp_weights=prof_interp_i;
93     prof_interp_lon=prof_interp_i; prof_interp_lat=prof_interp_i;
94    
95     file_cur=deblank(files_list(tcur,:));
96     tmp3=strfind(file_cur,'.');
97     ni=str2num(file_cur(tmp3(end-2)+1:tmp3(end-1)-1));
98     nj=str2num(file_cur(tmp3(end-1)+1:tmp3(end)-1));
99     fid=fopen([rep_grid file_cur],'r','b'); XC_cur=fread(fid,[ni+2 nj+2],'float64'); fclose(fid);
100     tmp3=strfind(file_cur,'XC'); file_cur(tmp3)='Y';
101     fid=fopen([rep_grid file_cur],'r','b'); YC_cur=fread(fid,[ni+2 nj+2],'float64'); fclose(fid);
102     XC_ref=XC_cur; YC_ref=YC_cur;
103     %set the longitude system for model:
104     [XC_cur(:)]=netcdf_ecco_GenericgridRotateLon(XC_cur(:),0,0,lonSystModel);
105    
106    
107     %tests to avoid bug particualr cases (test1&test2) and useless loops
108     %-------------------------------------------------------------------
109    
110     %test1=1; if we are to do "polar switch", only tiles that have grid points in the "polar region" can be relevant!
111     test1=1; if switch_to_polar~=0; test1=~isempty(find(( YC_cur(:)-switch_to_polar*(lat_polar-10) )*switch_to_polar > 0)); end;
112    
113     %test2: if no switch_to_polar do not address the polar tiles (the ones that go though all latitudes)
114     test2=1; if switch_to_polar==0; test2=isempty(find(XC_cur(:)>175))|isempty(find(XC_cur(:)<-175))|isempty(find(abs(XC_cur(:))<5)); end;
115     %alternative:
116     % test2=1; if switch_to_polar==0; test2=isempty(find(abs(XC_cur(:)+135)<30))|isempty(find(abs(XC_cur(:)+45)<30))|...
117     % isempty(find(abs(XC_cur(:)-135)<30))|isempty(find(abs(XC_cur(:)-45)<30)); end;
118    
119     %test3: if no data don't bother!
120     test3=~isempty(list_profilesM2);
121    
122     %fprintf([num2str([subset_cur tcur test1 test2 test3]) '\n']);
123    
124     %%%%%%%%%%%%%%%%%%%%
125     if test1&test2&test3
126     %%%%%%%%%%%%%%%%%%%%
127    
128    
129     if choice_plot==1; subplot(2,1,1); plot(XC_cur(:),YC_cur(:),'yx'); hold on; plot(XC_cur(1,1),YC_cur(1,1),'b.'); plot(XC_cur(end,1),YC_cur(end,1),'m.');
130     tmp_lonM1=prof_lonM2(list_profilesM2); tmp_latM1=prof_latM2(list_profilesM2); plot(tmp_lonM1,tmp_latM1,'go'); axis([-180 180 -90 90]); end;
131    
132     if switch_to_polar~=0;
133     %switch to polar plane coordinates
134     tmp1=find(( YC_cur(:)-switch_to_polar*(lat_polar-10) )*switch_to_polar <= 0); XC_cur(tmp1)=NaN; YC_cur(tmp1)=NaN;
135     [XC_cur,YC_cur]=netcdf_ecco_GenericgridPolarPlaneCoords(XC_cur,YC_cur,switch_to_polar);
136     [XC_cur,YC_cur]=netcdf_ecco_GenericgridFixFieldsOverlapCorners(XC_cur,YC_cur);
137     else
138     lon0global=0;
139     if ~isempty(find(abs(XC_cur(:))>175)); lon0tile=180; else; lon0tile=0; end;
140     %alternative: lon0tile=mean(XC_cur(:));
141     prof_lonM1ref=prof_lonM1;
142     %do the "model flip" for the data ... or not
143     [prof_lonM1]=netcdf_ecco_GenericgridRotateLon(prof_lonM1,lon0global,lon0tile,lonSystModel);
144     %do the "model flip" for the model ... or not
145     [XC_cur]=netcdf_ecco_GenericgridRotateLon(XC_cur,lon0global,lon0tile,lonSystModel);
146     [XC_cur,YC_cur]=netcdf_ecco_GenericgridFixFieldsOverlapCorners(XC_cur,YC_cur);
147     end
148    
149     if choice_plot==1; subplot(2,1,2); plot(XC_cur(:),YC_cur(:),'yx'); hold on; plot(XC_cur(1,1),YC_cur(1,1),'b.'); plot(XC_cur(end,1),YC_cur(end,1),'m.');
150     plot(prof_lonM1,prof_latM1,'go'); if ~switch_to_polar; axis([-180 180 -90 90]); else; axis([-90 90 -90 90]); end; end;
151    
152     x0=zeros((ni+1)*(nj+1),4); y0=x0; i0=x0; j0=x0;
153    
154     tmp_count=0;
155     for icur=1:ni+1; for jcur=1:nj+1;
156     tmp_count=tmp_count+1;
157    
158     x0(tmp_count,:)=[XC_cur(icur,jcur) XC_cur(icur+1,jcur) XC_cur(icur+1,jcur+1) XC_cur(icur,jcur+1)];
159     y0(tmp_count,:)=[YC_cur(icur,jcur) YC_cur(icur+1,jcur) YC_cur(icur+1,jcur+1) YC_cur(icur,jcur+1)];
160     i0(tmp_count,:)=[icur icur+1 icur+1 icur]; j0(tmp_count,:)=[jcur jcur jcur+1 jcur+1];
161    
162     end; end;
163    
164     tmp1=find(~isnan(sum(x0,2)));
165     x0=x0(tmp1,:); y0=y0(tmp1,:); i0=i0(tmp1,:); j0=j0(tmp1,:);
166    
167    
168     %first step: restrict our attention to profiles that are within the area
169     %-----------
170     %will work in any case when
171     % 1) the cell is non polar, so we do not cross the longitude limit
172     % or
173     % 2) we use polar coordinates, which is well defined, for both model and data
174     %=> if this is not the case: I have put some NaNs in XC_cur
175     if isempty(find(isnan(XC_cur)))
176     x00=[XC_cur(:,1)' XC_cur(end,2:end-1) flipdim(XC_cur(:,end)',2) XC_cur(1,end-1:-1:2)];
177     y00=[YC_cur(:,1)' YC_cur(end,2:end-1) flipdim(YC_cur(:,end)',2) YC_cur(1,end-1:-1:2)];
178     list_profilesM1=zeros(size(prof_lonM1));
179     length_div=1e3;
180     num_div=ceil(length(prof_lonM1)/length_div);
181     for cur_div=1:num_div
182     list_profiles0=[(cur_div-1)*length_div+1:min(cur_div*length_div,length(prof_lonM1))];
183     [tmp1]=netcdf_ecco_GenericgridLocateCell(x00,y00,prof_lonM1(list_profiles0),prof_latM1(list_profiles0));
184     list_profilesM1(list_profiles0(find(tmp1>0)))=1;
185     end
186     list_profilesM1=find(list_profilesM1>0);
187     prof_lon=prof_lonM1(list_profilesM1); prof_lat=prof_latM1(list_profilesM1);
188     else
189     list_profilesM1=[1:length(prof_lonM1)]'; prof_lon=prof_lonM1; prof_lat=prof_latM1;
190     end
191    
192     %second step: the main computation
193     %---------------------------------
194     if ~isempty(list_profilesM1)
195    
196     length_div=1e2;
197     num_div=ceil(length(prof_lon)/length_div);
198     for cur_div=1:num_div
199     list_profiles0=[(cur_div-1)*length_div+1:min(cur_div*length_div,length(prof_lon))];
200    
201     %if mod(cur_div,20)==1;
202     %tmp1=length(find(~isnan(prof_interp_i(:,1)))); tmp2=length(prof_lon);
203     %fprintf([num2str(tcur) ' -- ' num2str(list_profiles0(1)) ' / ' num2str(length(prof_lon)) ' -- ' num2str(tmp1) '\n']);
204     %end
205    
206     [list_profiles2]=netcdf_ecco_GenericgridLocateCell(x0,y0,prof_lon(list_profiles0),prof_lat(list_profiles0));
207    
208     [coeffs2]=netcdf_ecco_GenericgridCoeffs_4points(x0,y0,prof_lon(list_profiles0),prof_lat(list_profiles0));
209    
210     list_profiles3=find(sum(list_profiles2,2)>0);
211    
212     for kkcur=1:length(list_profiles3)
213     %index in small data vector:
214     kcur0=list_profiles3(kkcur);
215     %more than one 1 can happen when close to cell edges; we pick the first;
216     tmp1=find(list_profiles2(kcur0,:)>0); tmp1=tmp1(1);
217     tmp2=squeeze(coeffs2(kcur0,tmp1,:)); %NOT PRACTICAL tmp3=find(tmp2>0);
218     %index in the full data vector:
219     kcur=list_profilesM2(list_profilesM1(list_profiles0(kcur0)));
220     %fill arrays:
221     prof_interp_XC11(kcur)=XC_ref(2,2); prof_interp_YC11(kcur)=YC_ref(2,2);
222     prof_interp_XCNINJ(kcur)=XC_ref(end-1,end-1); prof_interp_YCNINJ(kcur)=YC_ref(end-1,end-1);
223     prof_interp_i(kcur,:)=i0(tmp1,:)-1;
224     prof_interp_j(kcur,:)=j0(tmp1,:)-1;
225     prof_interp_weights(kcur,:)=tmp2(:);
226     end
227    
228     end%for cur_div=1:num_div
229    
230     end%if ~isempty(list_profilesM1)
231    
232     if switch_to_polar==0;
233     %undo the "model flip" for the data
234     [prof_lonM1]=netcdf_ecco_GenericgridRotateLon(prof_lonM1,lon0tile,lon0global,lonSystModel); %needed for computation
235     [XC_cur]=netcdf_ecco_GenericgridRotateLon(XC_cur,lon0tile,lon0global,lonSystModel); %needed for plot only
236     % if ~isempty(find(mod(prof_lonM1,360)~=mod(prof_lonM1ref,360)));
237     % fprintf('pb due to change in longitudes => stop \n'); return;
238     % end
239     end
240    
241     if choice_plot==1; tmp1=find(~isnan(prof_interp_i(:,1)));
242     tmp_i=prof_interp_i(tmp1,1); tmp_j=prof_interp_j(tmp1,1); tmp2=(tmp_j+1-1)*(ni+2)+(tmp_i+1); plot(XC_cur(tmp2),YC_cur(tmp2),'ro');
243     % tmp_i=prof_interp_i(tmp1,2); tmp_j=prof_interp_j(tmp1,2); tmp2=(tmp_j+1-1)*(ni+2)+(tmp_i+1); plot(XC_cur(tmp2),YC_cur(tmp2),'bo');
244     if ~switch_to_polar;
245     plot(prof_lonM2(tmp1),prof_latM2(tmp1),'k.');
246     else;
247     tmp_x=prof_lonM2(tmp1); tmp_y=prof_latM2(tmp1);
248     [tmp_x,tmp_y]=netcdf_ecco_GenericgridPolarPlaneCoords(tmp_x,tmp_y,switch_to_polar); plot(tmp_x,tmp_y,'k.');
249     end;
250     pause(2); clf;
251     end;
252    
253    
254     %third step : we do not use overlap corner points in interpolation
255     %-----------
256     %
257 gforget 1.2 %1) rare case when algorithm has collapsed on overlap corners:
258 gforget 1.1 tmp1=find(~isnan(prof_interp_XC11)&round(sum(prof_interp_weights,2)*1e6)*1e-6~=1);
259 gforget 1.2 %1.1) rarest case: two points in overlap corner => mask profile
260 gforget 1.1 tmp2=( (prof_interp_i(tmp1,:)==0&prof_interp_j(tmp1,:)==0)|( prof_interp_i(tmp1,:)==0&prof_interp_j(tmp1,:)==nj+1 )|...
261     ( prof_interp_i(tmp1,:)==ni+1&prof_interp_j(tmp1,:)==0 )|( prof_interp_i(tmp1,:)==ni+1&prof_interp_j(tmp1,:)==nj+1 ));
262 gforget 1.2 if ~isempty(find(sum(tmp2,2)~=1));
263     %fprintf('this is unexpected!! \n'); return;
264     fprintf([num2str(length(tmp2)) ' masked due to overlap corner issue \n']);
265     tmp11=tmp1(find(sum(tmp2,2)~=1));
266     prof_interp_XC11(tmp11)=NaN; prof_interp_YC11(tmp11)=NaN;
267     prof_interp_XCNINJ(tmp11)=NaN; prof_interp_YCNINJ(tmp11)=NaN;
268     prof_interp_i(tmp11,:)=NaN; prof_interp_j(tmp11,:)=NaN;
269     prof_interp_lon(tmp11,:)=NaN; prof_interp_lat(tmp11,:)=NaN;
270     prof_interp_weights(tmp11,:)=NaN;
271     %reset tmp1 to handle the other points
272     tmp1=find(~isnan(prof_interp_XC11)&round(sum(prof_interp_weights,2)*1e6)*1e-6~=1);
273     tmp2=( (prof_interp_i(tmp1,:)==0&prof_interp_j(tmp1,:)==0)|( prof_interp_i(tmp1,:)==0&prof_interp_j(tmp1,:)==nj+1 )|...
274     ( prof_interp_i(tmp1,:)==ni+1&prof_interp_j(tmp1,:)==0 )|( prof_interp_i(tmp1,:)==ni+1&prof_interp_j(tmp1,:)==nj+1 ));
275     end
276     %1.2) one point in overlap corner => equally weighted average of the three neighbors
277 gforget 1.1 tmp3=prof_interp_weights(tmp1,:); tmp3(find(tmp2==0))=1/3; tmp3(find(tmp2==1))=0;
278     prof_interp_weights(tmp1,:)=tmp3;
279 gforget 1.2 %2) normal behaviour => distribute equally the corner weight to the three neighbors
280 gforget 1.1 tmp1=find(~isnan(prof_interp_XC11));
281     tmp2=( (prof_interp_i(tmp1,:)==0&prof_interp_j(tmp1,:)==0)|( prof_interp_i(tmp1,:)==0&prof_interp_j(tmp1,:)==nj+1 )|...
282     ( prof_interp_i(tmp1,:)==ni+1&prof_interp_j(tmp1,:)==0 )|( prof_interp_i(tmp1,:)==ni+1&prof_interp_j(tmp1,:)==nj+1 ));
283     tmp3=find(sum(tmp2,2)==1); tmp1=tmp1(tmp3); tmp2=tmp2(tmp3,:);
284     tmp3=prof_interp_weights(tmp1,:);
285     if ~isempty(find(tmp2.*tmp3~=0)); fprintf('o');
286     tmp3=tmp3+1/3*sum(tmp3.*tmp2,2)*ones(1,4); tmp3(find(tmp2==1))=0;
287     prof_interp_weights(tmp1,:)=tmp3;
288     end
289    
290     %fourth step: store the lon/lat of the interpolation points for checks
291     %------------
292     tmp1=find(~isnan(prof_interp_i));
293     tmp2=(ni+2)*prof_interp_j(tmp1)+prof_interp_i(tmp1)+1;
294     %rk: the computation of the previous line accounts for the fact that i/j go from 0 to ni+1/nj+1
295     prof_interp_lon(tmp1)=XC_ref(tmp2); prof_interp_lat(tmp1)=YC_ref(tmp2);
296    
297 gforget 1.2
298 gforget 1.1 %fifth step: save in .mat file
299     %------------------------------
300     tmp1=findstr(file_data,'.nc');
301     eval(['save ' rep_out file_data(1:tmp1(end)-1) '_4mygrid.' suff_cur '.' num2str(tcur) '.mat prof_interp_*;']);
302    
303     %%%%%%%%%%%%%%%%%%%%%%%%
304     end%if test1&test2&test3
305     %%%%%%%%%%%%%%%%%%%%%%%%
306    
307     end%for tcur=...
308    
309     end%for subset_cur=1:3
310    
311    

  ViewVC Help
Powered by ViewVC 1.1.22