Changeset 747 for trunk/src/nc2struct.m


Ignore:
Timestamp:
Apr 22, 2014, 9:44:39 AM (10 years ago)
Author:
sommeria
Message:

adpatations to 3D fields

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/nc2struct.m

    r693 r747  
    2828%         if ListVarName=[] or {}, no variable value is read (only global attributes and list of variables and dimensions)
    2929%         if ListVarName is absent, or = '*', ALL the variables of the netcdf file are read.
    30 %         if ListVarName is a cell array with n lines, the set of variables will be sought by order of priority
    31 %                  in the list, while output names will be set by the first line
    32 %        - the string 'ListGlobalAttribute' followed by a list of attribute  names: reads only these attributes (fast reading)
    33 %        - the string 'TimeVarName', a string (the variable considered as
    34 %        time), an integer (the selected time index), the cell of other
    35 %        input variables limited to the input time index (considered as the last index of arrays)
    36 %        - the string 'TimeDimName', a string (the dimension considered as time), an integer (the selected time index), the cell of other
    37 %        input variables limited to the input time index (considered as the last index of arrays)
     30%         if ListVarName is a cell array with n lines, the set of variables will be sought by order of priority in the list,
     31%            while output names will be set by the first line
     32%       - the string 'ListGlobalAttribute' followed by a list of attribute  names: reads only these attributes (fast reading)
     33%       - the string 'TimeVarName', a string (the variable considered as time), an integer or vector with integer values
     34%            representing time indices to select, the cell of other input variable names.
     35%       - the string 'TimeDimName', a string (the name of the dimension considered as time), an integer or vector with integer values
     36%            representing time indices to select, the cell of other input variable names.
    3837
    3938%AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
     
    5352%AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
    5453   
    55 function [Data,var_detect,ichoice]=nc2struct(nc,varargin)
    56 
     54function [Data,var_detect,ichoice,errormsg]=nc2struct(nc,varargin)
     55errormsg='';%default error message
    5756if isempty(varargin)
    5857    varargin{1}='*';
     
    6766   
    6867    %% open the netcdf file for reading
    69     if ischar(nc) 
     68    if ischar(nc)
    7069        if exist(nc,'file')
    7170            try
    72             nc=netcdf.open(nc,'NC_NOWRITE');
    73             testfile=1;
     71                nc=netcdf.open(nc,'NC_NOWRITE');
     72                testfile=1;
    7473            catch ME
    75               Data.Txt=['ERROR opening ' nc ': ' ME.message];
    76               return
     74                errormsg=['ERROR opening ' nc ': ' ME.message];
     75                return
    7776            end
    7877        else
    79            Data.Txt=['ERROR:file ' nc ' does not exist'];
    80            return
     78            errormsg=['ERROR:file ' nc ' does not exist'];
     79            return
    8180        end
    8281    else
     
    8988            valuestr=[];%default
    9089            try
    91             valuestr = netcdf.getAtt(nc,netcdf.getConstant('NC_GLOBAL'),varargin{ilist});
     90                valuestr = netcdf.getAtt(nc,netcdf.getConstant('NC_GLOBAL'),varargin{ilist});
    9291            catch ME
    9392            end
     
    9594        end
    9695        netcdf.close(nc)
    97        return
     96        return
    9897    end
    9998   
    10099    %% time variable or dimension
    101100    input_index=1;
     101    CheckTimeVar=0;
     102    TimeVarName='';
    102103    if isequal(varargin{1},'TimeVarName')
    103104        TimeVarName=varargin{2};
    104         TimeVarIndex=varargin{3};
    105         input_index=4;
     105        CheckTimeVar=1;
     106        TimeIndex=varargin{3};
     107        input_index=4;% list of varibles to read is at fourth argument
    106108    elseif isequal(varargin{1},'TimeDimName')
    107109        TimeDimName=varargin{2};
    108         TimeVarIndex=varargin{3};
     110        TimeIndex=varargin{3};
    109111        input_index=4;
    110112    end
    111 
     113   
    112114    %% full reading: get the nbre of dimensions, variables, global attributes
    113     ListVarName=varargin{input_index}; 
     115    ListVarName=varargin{input_index};
    114116    [ndims,nvars,ngatts]=netcdf.inq(nc);%nbre of dimensions, variables, global attributes, in the netcdf file
    115117   
     
    130132                eval(['Data.' keystr '=valuestr;'])
    131133            else
    132                 eval(['Data.' keystr '='';']) 
     134                eval(['Data.' keystr '='';'])
    133135            end
    134136            att_key{iatt}=keystr;
     
    139141    end
    140142    Data.ListGlobalAttribute=att_key;
    141 
     143   
    142144    %%  -------- read dimension names-----------
    143145    ListDimNameNetcdf=cell(1,ndims);
     
    146148        [ListDimNameNetcdf{idim},dim_value(idim)] = netcdf.inqDim(nc,idim-1);%get name and value of each dimension
    147149    end
    148     if ~isempty(ListDimNameNetcdf) 
     150    if ~isempty(ListDimNameNetcdf)
    149151        flag_used=zeros(1,ndims);%initialize the flag indicating the selected dimensions in the list (0=unused)
    150152    end
    151153    if isequal(varargin{1},'TimeDimName')% time dimension introduced
    152         TimeDimIndex=find(strcmp(varargin{2},ListDimNameNetcdf));
     154        TimeDimIndex=find(strcmp(TimeDimName,ListDimNameNetcdf));
    153155        if isempty(TimeDimIndex)
    154             Data.Txt=['requested time dimension ' varargin{2} ' not found'];
     156            errormsg=['requested time dimension ' varargin{2} ' not found'];
    155157            return
    156158        end
    157159        if dim_value(TimeDimIndex)<varargin{3}
    158             Data.Txt=['requested time index ' num2str(varargin{3}) ' exceeds matrix dimension'];
     160           errormsg=['requested time index ' num2str(varargin{3}) ' exceeds matrix dimension'];
    159161            return
    160162        end
    161     end
    162  
     163    end 
     164    
    163165    %%  -------- read names of variables -----------
    164166    ListVarNameNetcdf=cell(1,nvars); %default
     
    166168    nbatt=zeros(1,nvars);
    167169    for ncvar=1:nvars %loop on the variables of the netcdf file
    168         %get name, type, dimensions and attribute numbers of each variable 
     170        %get name, type, dimensions and attribute numbers of each variable
    169171        [ListVarNameNetcdf{ncvar},xtype(ncvar),dimids{ncvar},nbatt(ncvar)] = netcdf.inqVar(nc,ncvar-1);
    170     end 
    171     testmulti=0;
     172    end
     173%     testmulti=0;
    172174    if isequal(ListVarName,'*')||isempty(ListVarName)
    173         var_index=1:nvars; %all the variables are selected in the netcdf file 
     175        var_index=1:nvars; %all the variables are selected in the netcdf file
    174176        Data.ListVarName=ListVarNameNetcdf;
    175177    else   %select input variables, if requested by the input ListVarName
    176         ind_remove=[];
    177178        check_keep=ones(1,size(ListVarName,2));
    178179        for ivar=1:size(ListVarName,2) % check redondancy of variable names
     
    181182            end
    182183        end
    183         ListVarName=ListVarName(:,logical(check_keep));         
     184        ListVarName=ListVarName(:,logical(check_keep));
    184185        sizvar=size(ListVarName);
    185         testmulti=(sizvar(1)>1);%test for multiple choice of variable ranked by order of priority
    186186        var_index=zeros(1,sizvar(2));%default
    187         if testmulti %multiple choice of variable ranked by order of priority
     187        if sizvar(1)>1 %multiple choice of variable ranked by order of priority
    188188            for iline=1:sizvar(1)
    189189                search_index=find(strcmp(ListVarName{iline,1},ListVarNameNetcdf),1);%look for the first variable name in the list of netcdf variables
     
    196196            iline=1;
    197197        end
    198         for ivar=1:sizvar(2)
     198        %ListVarName=ListVarName(iline,:);% select the appropriate option for input variable (lin ein the input name matrix)
     199        if CheckTimeVar
     200            TimeVarIndex=find(strcmp(TimeVarName,ListVarNameNetcdf),1); %look for the index of the time variable in the netcdf list
     201            if isempty(TimeVarIndex)
     202                errormsg='requested variable for time is missing';
     203                return
     204            end
     205            TimeDimIndex=dimids{TimeVarIndex}(1)+1;
     206            ListVarName=[ListVarName {TimeVarName}];
     207        end
     208        for ivar=1:size(ListVarName,2)
    199209            search_index=find(strcmp(ListVarName{iline,ivar},ListVarNameNetcdf),1);%look for the variable name in the list of netcdf file
    200210            if ~isempty(search_index)
     
    202212            end
    203213        end
    204         var_detect=(var_index~=0);%=1 for detected variables         
     214        var_detect=(var_index~=0);%=1 for detected variables
    205215        list_index=find(var_index);% indices in the input list corresponding to a detected variable
    206216        var_index=var_index(list_index);% netcdf variable indices corresponding to the output list of read variable
    207217        Data.ListVarName=ListVarName(1,list_index);%the first line of ListVarName sets the output names of the variables
    208218    end
    209      
    210   %% get the dimensions and attributes associated to  variables
    211   var_dim=cell(size(var_index));% initiate list of dimensions for variables
     219   
     220    %% get the dimensions and attributes associated to  variables
     221    var_dim=cell(size(var_index));% initiate list of dimensions for variables
    212222    for ivar=1:length(var_index)
    213223        var_dim{ivar}=dimids{var_index(ivar)}+1; %netcdf dimension indices used by the variable #ivar
     
    222232            end
    223233            try
    224              if isempty(valuestr)
    225                 Data.VarAttribute{ivar}.(attname)=valuestr;
    226             end
     234                if isempty(valuestr)
     235                    Data.VarAttribute{ivar}.(attname)=valuestr;
     236                end
    227237            catch ME
    228238                display(attname)
    229239                display(valuestr)
    230                 display(ME.message)         
     240                display(ME.message)
    231241                Data.VarAttribute{ivar}.(['atrr_' num2str(iatt)])='not read';
    232242            end
     
    234244    end
    235245   
    236 
    237246    %% select the dimensions used for the set of input variables
    238     if ~isempty(var_index)     
    239         dim_index=find(flag_used);%list of netcdf dimensions indices corresponding to used dimensions 
    240         Data.ListDimName=ListDimNameNetcdf(dim_index); 
     247    if ~isempty(var_index)
     248        dim_index=find(flag_used);%list of netcdf dimensions indices corresponding to used dimensions
     249        Data.ListDimName=ListDimNameNetcdf(dim_index);
    241250        Data.DimValue=dim_value(dim_index);
     251        if input_index==4% if a dimension is selected as time
     252            Data.DimValue(TimeDimIndex)=numel(TimeIndex);
     253        end
    242254    end
    243255   
     
    246258        for ivar=1:length(var_index)
    247259            VarName=Data.ListVarName{ivar};
    248             VarName=regexprep(VarName,'-',''); %suppress '-' if it exists in the netcdf variable name
    249             CheckSub=0;
     260            VarName=regexprep(VarName,'-','_'); %suppress '-' if it exists in the netcdf variable name (leads to errors in matlab)
     261%             CheckSub=0;
    250262            if input_index==4% if a dimension is selected as time
    251                 if var_dim{ivar}(end)==TimeDimIndex% if the last dim of the variable is the time
    252                     slice_length=prod(var_dim{ivar}(1:end-1));
    253                     Data.(VarName)=double(netcdf.getVar(nc,var_index(ivar)-1,TimeIndex*slice_length,slice_length)); %read the variable data
    254                     CheckSub=1;
    255                 end
    256             end
    257             if ~CheckSub
     263                ind_vec=zeros(1,numel(var_dim{ivar}));% vector with zeros corresponding to al the dimensions of the variable VarName
     264                ind_size=dim_value(var_dim{ivar});% vector giving the size of the variable VarName
     265                index_time=find(var_dim{ivar}==TimeDimIndex);
     266                if ~isempty(index_time)
     267                    ind_vec(index_time)=TimeIndex-1;% selected index(or indices) to read
     268                    ind_size(index_time)=numel(TimeIndex);%length of the selected set of time indices
     269                    if numel(TimeIndex)==1 && ~strcmp(VarName,TimeVarName)
     270                        Data.VarDimName{ivar}(index_time)=[];% for a single selected time remove the time in the list of dimensions (except for tTime itself)
     271                    end
     272                end                   
     273                Data.(VarName)=double(netcdf.getVar(nc,var_index(ivar)-1,ind_vec,ind_size)); %read the variable data
     274                Data.(VarName)=squeeze(Data.(VarName));%remove singeton dimension
     275            else
    258276                Data.(VarName)=netcdf.getVar(nc,var_index(ivar)-1); %read the whole variable data
    259                 if xtype(var_index(ivar))==5
     277            end
     278            if xtype(var_index(ivar))==5
    260279                Data.(VarName)=double(Data.(VarName)); %transform to double for single pecision
    261                 end
    262280            end
    263281        end
     
    267285    %%  -------- close fle-----------
    268286    if testfile==1
    269         netcdf.close(nc) 
    270     end
    271    
    272 %% old netcdf library
     287        netcdf.close(nc)
     288    end
     289   
     290    %% old netcdf library
    273291else
    274292    [Data,var_detect,ichoice]=nc2struct_toolbox(nc,varargin);
Note: See TracChangeset for help on using the changeset viewer.