/core/third_parties/fparser.m
MATLAB | 1289 lines | 1035 code | 68 blank | 186 comment | 1 complexity | 70c6d7c29e9a265e05402f9918109558 MD5 | raw file
Possible License(s): BSD-3-Clause, AGPL-1.0, LGPL-2.0, GPL-3.0, GPL-2.0, LGPL-2.1, LGPL-3.0, BSD-2-Clause
- % PAR = FPARSER('M-file',['OPT',...,'OPT',...])
- % PAR = FPARSER('command_line','-c',['OPT',...,'OPT',...])
- %
- % to parse a M-file or command line
- % and list tokens and constructs
- % - functions/keywords
- % - variables/constants
- % - struct field assignments
- %
- % OPT option flags/arguments
- % -c : input is a command-line
- % -d : show results at run-time
- %
- % PAR output struct with fields
- % .tmpl lexical engine templates
- % .file file name
- % .buff file contents
- % .skel file contents after removal of
- % var class tokens
- % .res RESULTS [show at run-time: <-d>]
- % .nline nr of lines
- % .linx indices eol/lnr
- % .nent nr of tokens found
- % .nmtok nr of FUNCTIONS found
- % .mtok list of FUNCTIONS
- % .nvtok nr of VARIABLES found
- % .vtok list of VARIABLES
- % .nstok nr of STRUCT.FIELD assignments
- % .stok list of STRUCT.FIELD assignments
- %
- % contents of sorted token list cells
- % .mtok {'token' 'source' name_len nr_used inx_lst lin_lst}
- % .vtok {'token' 'type' name_len nr_used inx_lst lin_lst}
- % .stok {'token' 'contructor' name_len line_nr inx_lst lin_lst}
- %
- % contents of <inx_lst>s
- % nr_used indices
- % [beg1 ... begN = buffer offset beg
- % end1 ... endN] = buffer offset end
- % into par.buff where tokenX was found
- % contents of <lin_lst>s
- % nr_used indices
- % [lnr1 ... lnrN = line number
- % beg1 ... begN = line offset beg
- % end1 ... endN] = line offset end
- % of the file contents where tokenX was found
- %
- % USAGE EXAMPLE
- % see accompanying html-file <fpatdemo.html>
- % this option is not implemented in final version!
- % mod: modify default templates [def: par.tmpl]
- % '[xyz]' : do NOT delete characters <x><y><z>
- % '{xyz}' : delete additional characters <x><y><z>
- % created:
- % us 10-Jun-2001 / project <alias>
- % modified:
- % us 12-Dec-2005 09:26:17 / CSSM/TMW
- function olst=fparser(varargin)
- mod=[];
- mode=0;
- lst=ini_lst(varargin{:});
- if nargout
- olst=lst;
- end
- if nargin < 1 | isempty(varargin{1})
- help(mfilename);
- return;
- end
- var=varargin{1};
- % command line
- if nargin > 1 & lst.par.opt.cflg
- lst.file='command line';
- lst.type='string';
- mode=1;
- var=[var char(10)];
- % m-file
- else
- lst.file=var;
- lst.type='file';
- mode=1;
- [fp,msg]=fopen(var,'rt');
- if fp > 0
- var=fread(fp,'uchar');
- fclose(fp);
- var=char(var).';
- else
- % disp(sprintf('fparser> cannot open <%s>',var));
- % disp(sprintf('.......> %s',msg));
- return;
- end
- end
- % build empty output parameter struct
- lst.buff=var;
- lst.skel=var;
- lst.res='no tokens';
- linx=[0 find(var==10)];
- lst.nline=length(linx)-mode;
- lst.linx=[linx; 1:lst.nline+1];
- lst.linx(end,end)=nan;
- lst.nent=0;
- lst.nmtok=0; % functions
- lst.mtok={};
- lst.mtxt=[];
- lst.nvtok=0; % variables
- lst.vtok={};
- lst.vtxt=[];
- lst.nstok=0; % struct assignments
- lst.stok={};
- lst.stxt=[];
- %--------------------------------------------------------------------------------
- % templates
- % - special characters
- % tmpls='@._';
- % - unconditional:
- % tmpl1='=+-*/^''[](){},.:;\~!#$%&|<>?"`';
- tmpl1='=+-*/^''[](){},:;\~!#$%&|<>?"`';
- % - space both | right | surrounded by chars
- tmpl2='@';
- % - space both | left
- tmpl3='0123456789';
- iinc=[];
- idel=[];
- if nargin > 1 & ~isempty(mod)
- ib=strfind(mod,'[');
- if ~isempty(ib)
- ie=strfind(mod,']');
- if ~isempty(ie)
- iinc=mod(ib+1:ie-1);
- end
- end
- ib=strfind(mod,'{');
- if ~isempty(ib)
- ie=strfind(mod,'}');
- if ~isempty(ie)
- idel=mod(ib+1:ie-1);
- end
- end
- %D disp(sprintf('inc: <%s>',iinc));
- %D disp(sprintf('del: <%s>',idel));
- for i=1:length(iinc)
- tmpl1(find(iinc(i)==tmpl1))='';
- tmpl2(find(iinc(i)==tmpl2))='';
- tmpl3(find(iinc(i)==tmpl3))='';
- end
- tmpl1=[tmpl1 idel];
- end
- dflg=1;
- if nargin > 2
- lst.par.opt.dflg=1;
- end
- % tmpl3=[tmpl3 tmpl3];
- vari=var;
- lst.tmpl.tmpl1=tmpl1;
- lst.tmpl.cused=setdiff(char(32:128),tmpl1);
- lst.tmpl.tmpl2=tmpl2;
- lst.tmpl.tmpl3=tmpl3;
- lst.tmpl.inc=iinc;
- lst.tmpl.del=idel;
- %--------------------------------------------------------------------------------
- % MAIN LEXICAL ENGINE
- %--------------------------------------------------------------------------------
- %D disp('***** special constructs *****');
- [lst,var,sok]=get_stri(lst,var);
- [lst,var,sok]=get_comm(lst,var,'%',10);
- [lst,var,sok]=get_stru(lst,var,'.',tmpl1);
- var=[' ' var ' '];
- %--------------------------------------------------------------------------------
- %D disp('***** punctuations *****');
- for i=1:length(tmpl1)
- var=strrep(var,tmpl1(i),' ');
- %D disp(var)
- end
- for i=1:length(tmpl2)
- ix=strfind(var,tmpl2(i));
- if ~isempty(ix)
- % space both
- iy=find(var(ix+1)==' ' & var(ix-1)==' ');
- var(ix(iy))=' ';
- % char both | left
- iy=[...
- find((var(ix+1)~=' ' & var(ix-1)~=' ') | ...
- (var(ix-1)~=' '))...
- ];
- if ~isempty(iy)
- ixo=ix;
- iyo=iy;
- ix=ix(iy); % -1
- var(ix)=' '; % '|'
- nc=0;
- % erode ->
- while iy
- nc=nc+1;
- iy=find(var(ix+nc)~=' ');
- var(ix(iy)+nc)=' ';
- ix=ix(iy);
- end
- ix=ixo;
- iy=iyo;
- nc=0;
- % erode <-
- while iy
- nc=nc+1;
- iy=find(var(ix-nc)~=' ');
- var(ix(iy)-nc)=' ';
- ix=ix(iy);
- end
- end
- end
- % disp(var);
- end
- %--------------------------------------------------------------------------------
- %D disp('***** numbers *****')
- % must use an eroding process!
- vart=var;
- while true
- for i=1:length(tmpl3)
- ix=find(var==tmpl3(i));
- if ~isempty(ix)
- % space left
- iy=find(isspace(var(ix-1)));
- var(ix(iy))=' ';
- % space both
- iy=find(isspace(var(ix+1)) & isspace(var(ix-1)));
- var(ix(iy))=' ';
- end
- %D disp(var);
- end
- if isequal(var,vart)
- break;
- end
- vart=var;
- end
- %--------------------------------------------------------------------------------
- %D disp('***** tokens *****')
- tok={};
- emp={};
- tc={};
- var=var(2:end-1);
- b=var;
- trep=0;
- tnew=0;
- tent=0;
- [tc,b,tcp]=astrtok(b);
- tent=size(tc,1);
- tc=unique(tc);
- ix=xor(cellfun('isempty',tc),1);
- tc=tc(ix);
- for cc=1:size(tc,1)
- a=tc{cc};
- %D disp(sprintf('%s: searching',a));
- if (~isempty(tok) & ~isempty(strmatch(a,tok(:,1),'exact'))) | ...
- (~isempty(emp) & ~isempty(strmatch(a,emp(:,1),'exact')))
- trep=trep+1;
- %D disp(sprintf('repeat token %5d:%5d/%5d <%s>',trep,tnew,trep+tnew,a));
- continue;
- end
- tnew=tnew+1;
- w=[]; % keep this!
- if ~isempty(w)
- emp=[emp;{a w.class length(a)}];
- else
- p=evalin('base',sprintf('which(''%s'')',a));
- if strcmp(p,'variable')
- p=[];
- end
- if ~isempty(p)
- if iskeyword(a)
- p='keyword';
- end
- %D disp(sprintf('%s: PATH <%s>',a,p));
- tok=[tok;{a p length(a)}];
- else
- if a(1)=='@' & length(a) > 1
- emp=[emp;{a class(eval(a)) length(a)}];
- else
- emp=[emp;{a class(a) length(a)}];
- end
- end
- end % token not in tables
- end
- varo=var;
- if ~isempty(emp)
- ix=strmatch('@',emp(:,1));
- if ~isempty(ix)
- tlen=[size(tok,1)+1:size(tok,1)+length(ix)];
- tok(tlen,:)=emp(ix,:);
- emp(ix,:)=[];
- end
- if ~isempty(tok)
- [dum,ix]=unique(tok(:,1));
- tok=tok(ix,:);
- end
- [var,tcp,tok]=fill_pattern(var,tcp,tok,'+');
- [dum,ix]=unique(emp(:,1));
- if ~isempty(emp)
- emp=emp(ix,:);
- [var,tcp,emp]=fill_pattern(var,tcp,emp,'-');
- ix=strfind(var,'-');
- if ~isempty(ix)
- var=varo;
- var(ix)=' ';
- end
- else
- var=varo;
- end
- elseif ~isempty(tok)
- [dum,ix]=unique(tok(:,1));
- tok=tok(ix,:);
- [dum,tcp,tok]=fill_pattern(var,tcp,tok,'+');
- end
- %--------------------------------------------------------------------------------
- lst=set_var(lst,var,tok,emp,sok);
- lst=set_stru(lst);
- lst=show_ent(lst);
- if nargout
- olst=lst;
- end
- if lst.par.opt.dflg
- disp(lst.res);
- end
- return;
- %--------------------------------------------------------------------------------
- function [var,tcp,tmpl]=fill_pattern(var,tcp,tmpl,pat)
- [ts,tx]=sort([tmpl{:,3}]);
- tmpl=tmpl(tx,:);
- for i=size(tmpl,1):-1:1 % reverse search!
- s=tmpl{i,1};
- %D disp(sprintf('%s: CLR <%s>',var,s));
- six=strmatch(s,tcp.u(:,1),'exact');
- ix=tcp.u{six,end};
- tmpl{i,4}=size(ix,2);
- tmpl{i,5}=ix;
- var=astrrepx(var,pat,ix);
- %D disp(sprintf('%s: DONE <%s>',var,s));
- end
- return;
- %--------------------------------------------------------------------------------
- function [lst,tok,var]=set_var(lst,buf,tok,var,sok)
- if ~isempty(sok)
- sokt=sok;
- for i=1:size(sok,1)
- n=sok{i,1};
- o=n;
- nnew=1;
- nlen=0;
- if n(1) == '.'
- nnew=0;
- else
- ix=find(n=='.');
- n=n(1:ix-1);
- n=get_bracket(n);
- if isstruct(n)
- n=n.s;
- end
- nlen=length(n)+1;
- o=o(ix:end);
- ix=find(n=='|');
- if ~isempty(ix)
- n=n(1:ix(1)-1);
- end
- end
- if nnew
- if ~isempty(var)
- ix=strcmp(var(:,1),n);
- end
- if ~isempty(find(ix))
- p=sok{i,6};
- var{ix,4}=size(var{ix,5},2);
- var{ix,5}=[var{ix,5} p];
- else
- sok{i,1}=n;
- sok{i,2}='struct';
- sok{i,4}=length(n);
- var=[var;sok(i,[1 3:6])];
- end
- end
- end
- sok=sokt;
- end
- if ~isempty(tok)
- [dum,ix]=sort(tok(:,1));
- tok=tok(ix,:);
- tok=get_line(lst,tok);
- end
- if ~isempty(var)
- [dum,ix]=sort(var(:,1));
- var=var(ix,:);
- var=get_line(lst,var);
- end
- if ~isempty(sok)
- [dum,ix]=sort(sok(:,1));
- sok=sok(ix,:);
- sok=sok(:,[1 3:6]);
- sok=get_line(lst,sok);
- end
- lst.skel=buf;
- lst.nmtok=size(tok,1);
- lst.mtok=tok;
- lst.nvtok=size(var,1);
- lst.vtok=var;
- lst.nstok=size(sok,1);
- lst.stok=sok;
- lst.nent=lst.nmtok+lst.nvtok+lst.nstok;
- return;
- %--------------------------------------------------------------------------------
- function tok=get_line(lst,tok)
- if isempty(lst.linx)
- return;
- end
- for i=1:size(tok,1)
- p=tok{i,5};
- l=ones(3,size(p,2));
- for j=1:tok{i,4}
- ix=find(lst.linx(1,:)>=p(1,j));
- if ~isempty(ix)
- l(:,j)=[lst.linx(2,ix(1)-1);
- [p(:,j)-lst.linx(1,ix(1)-1)]];
- end
- end
- tok{i,6}=l;
- end
- return
- %--------------------------------------------------------------------------------
- function lst=show_ent(lst)
- % created:
- % us 30-Aug-2003 / CSSM/TMW <aparser>/<fparser>
- lst.res=[];
- lst.mtxt=[];
- lst.vtxt=[];
- lst.stxt=[];
- if ~lst.nent
- lst.res=sprintf('fparser> no tokens in <%s>',lst.file);
- else
- ml=[[lst.mtok{:,3}],[lst.vtok{:,3}],[lst.stok{:,3}]];
- ml=max([ml 20])+2;
- ml=max(ml,20);
- del={repmat('-',1,ml+7)};
- fm1=sprintf('%%-%d.%ds> %%5d',ml,ml);
- fm2=sprintf('%%%dd',ml-12);
- txt=[];
- txt=[txt;{sprintf(['functions/keywords ' fm2],lst.nmtok)}];
- txt=[txt;del];
- for i=1:size(lst.mtok,1)
- tmp=sprintf(fm1,lst.mtok{i,1},lst.mtok{i,4});
- tmp=[tmp ' ' sprintf('%s',lst.mtok{i,2})];
- txt=[txt;{tmp}];
- end
- mtxt=[txt;del];
- txt=[];
- txt=[txt;{sprintf(['variables/constants' fm2],lst.nvtok)}];
- txt=[txt;del];
- for i=1:size(lst.vtok,1)
- txt=[txt;{sprintf(fm1,lst.vtok{i,1},lst.vtok{i,4})}];
- end
- vtxt=[txt;del];
- txt=[];
- txt=[txt;{sprintf(['struct.field assmnt' fm2],lst.nstok)}];
- txt=[txt;del];
- for i=1:size(lst.stok,1)
- tok=lst.stok{i,1};
- tok=tok(~isspace(tok));
- tmp=sprintf(fm1,tok,lst.stok{i,4});
- tmp=[tmp ' ' sprintf('%s',lst.stok{i,2})];
- txt=[txt;{tmp}];
- end
- txt=[txt;del];
- stxt=txt;
- lst.res=char([mtxt;vtxt;stxt]);
- lst.mtxt=char(mtxt);
- lst.vtxt=char(vtxt);
- lst.stxt=char(stxt);
- end
- return;
- %--------------------------------------------------------------------------------
- function [lst,varo,stok]=get_stru(lst,var,tmpl,tmpl1)
- varo=var;
- stok={};
- % do not parse <structures>: <o=aparser(string,'{.}',...)>
- if find(tmpl1==tmpl)
- return;
- end
- if strfind(var,tmpl)
- [lst,b]=get_struct(lst,var);
- varo=b.s;
- stok=b.v;
- end
- return;
- %--------------------------------------------------------------------------------
- function lst=set_stru(lst)
- if ~lst.nent
- return;
- end
- atok=[lst.mtok;lst.vtok];
- if isempty(atok)
- return;
- end
- itok=[atok{:,5}];
- for i=1:size(lst.stok,1)
- p=lst.stok{i,5};
- ix=find(lst.linx(1,:)-p(1)<0);
- if ~isempty(ix)
- lst.stok{i,4}=ix(end);
- end
- tok=lst.stok{i,1};
- if tok(1) == '.'
- pix=itok(2,:)<p(1);
- jtok=itok(:,pix);
- [a,b]=sort(abs(jtok(2,:)-p(1)));
- bp=jtok(1,b(1));
- tok=lst.buff(bp:p(2));
- bx=1;
- while length(find(tok=='(')) < length(find(tok==')')) | ...
- length(find(tok=='{')) < length(find(tok=='}')) | ...
- length(find(tok=='[')) < length(find(tok==']'))
- bx=bx+1;
- bp=jtok(1,b(bx));
- tok=lst.buff(bp:p(2));
- end
- lst.stok{i,1}=tok;
- lst.stok{i,2}='';
- lst.stok{i,3}=length(tok);
- else
- lst.stok{i,2}='';
- end
- end
- if ~isempty(lst.stok)
- [dum,ix]=sort(lst.stok(:,1));
- lst.stok=lst.stok(ix,:);
- end
- return;
- %--------------------------------------------------------------------------------
- function [lst,varo,stok]=get_stri(lst,var)
-
- varo=var;
- stok={};
- [lst,b]=get_string(lst,var);
- varo=b.s;
- stok=b;
- return;
- %--------------------------------------------------------------------------------
- function [lst,varo,stok]=get_comm(lst,var,commdel,eoldel)
- varo=var;
- stok={};
- ib=find(var==commdel);
- if ~isempty(ib)
- ie=find(var==eoldel);
- for i=1:length(ib)
- ix=find(ie>=ib(i));
- varo(ib(i):ie(ix(1))-1)='%';
- end
- end
- return
- %--------------------------------------------------------------------------------
- %--------------------------------------------------------------------------------
- %--------------------------------------------------------------------------------
- % UTILITY FUNCTIONS ADDED FROM PROJECT <ALIAS>
- % modified for CSSM/TMW
- %--------------------------------------------------------------------------------
- %--------------------------------------------------------------------------------
- %--------------------------------------------------------------------------------
- function [lst,b]=get_string(lst,s,rtmpl,rr)
- magic='get_string';
- if isstruct(s)
- b=s;
- if isfield(s,'magic') & strcmp(getfield(s,'magic'),magic)
- if nargin < 4
- b.k=b.r;
- else
- b.k=rr;
- end
- for i=1:b.n
- nobj=sprintf(b.tmpl.mark,i);
- b.k=strrep(b.k,nobj,b.t{i}(2:end-1));
- end
- end
- return;
- end
- tmpl='''';
- btmpl=' ,;=({[';
- if nargin < 3
- rtmpl='|';
- end
- n=0;
- v={};
- t={};
- sl=length(s);
- b.magic=magic;
- b.n=0;
- b.s=s;
- b.c=s;
- b.k=[];
- b.r=s;
- b.t=t;
- b.v=v;
- b.tmpl.tmpl=tmpl;
- b.tmpl.rtmpl=rtmpl;
- b.tmpl.btmpl=btmpl;
- b.tmpl.mark='_S%-1dS_';
- if nargin < 1 | isempty(s)
- return;
- end
- % remove <inner> 'STRING's
- sori=s;
- while 1
- for i=2:ceil(sl/2)
- obr=repmat(tmpl,1,i);
- ix=strfind(s,obr);
- if ~isempty(ix)
- dix=[-1 diff(ix)];
- iy=ix(find(dix~=1));
- if ~isempty(iy)
- s=astrrepx(s,' ',[iy;iy+i-1]);
- end
- else
- break;
- end
- end
- if strcmp(s,sori)
- break;
- end
- sori=s;
- end
- % search 'STRING's
- rori=s;
- ix=strfind(s,tmpl);
- if ~isempty(ix)
- i=0;
- while i < length(ix)-1
- i=i+1;
- j=ix(i);
- hasdel=0;
- for k=btmpl
- if j==1 | s(j-1)==k | isspace(s(j-1))
- hasdel=1;
- break;
- end
- end
- if hasdel
- n=n+1;
- t=[t;{b.c(j:ix(i+1))}];
- v=[v;{b.c(j:ix(i+1)) j ix(i+1) ix(i+1)-j}];
- s(j+1:ix(i+1)-1)=rtmpl;
- rori(j+1:ix(i+1)-1)=char(0);
- i=i+1;
- end
- end
- end
- while 1
- ix=strfind(rori,[char(0) char(0)]);
- if isempty(ix)
- break;
- end
- rori(ix)='';
- end
- b.s=s;
- if n
- b.r=sprintf(strrep(rori,char(0),b.tmpl.mark),[1:n]);
- else
- b.r=rori;
- end
- b.n=n;
- b.t=t;
- b.v=v;
- return;
- %--------------------------------------------------------------------------------
- function [lst,b]=get_struct(lst,var,tmpl1)
- % we must deal with dynamic field assignments
- % valid field assignments
- % var.field var.field
- % var.(field).(field) var.(field).(field)
- % var.(field).field .field
- % var(...).field .field
- % var{...}.field .field
- magic='get_struct';
- tmpl='.';
- varo=var;
- it=0;
- tok={};
- stok={};
- b.magic=magic;
- b.n=0;
- b.s=var;
- b.c=var;
- b.t=tok;
- b.v=stok;
- if nargin < 2 | isempty(var)
- return;
- end
- vlen=length(var);
- if vlen == 1
- b.s=strrep(var,tmpl,'|');
- return;
- end
- % <aparser!>
- if nargin < 3
- tmpl1='=+-*/^''[](){},:;\~!#$%&|<>?"`';
- end
- tmpl2=tmpl1;
- for i='[](){}<>'
- tmpl2(tmpl2==i)='';
- end
- % mask off marker <|>
- var=strrep(var,'|',char(0));
- % mask off <continuation> <parent directory> constructs
- ix=find(var(1:end-1)=='.' & var(2:end)=='.');
- if ~isempty(ix)
- var=astrrepx(var,'|',ix);
- var=astrrepx(var,'|',ix+1);
- end
- vart=var;
- k=astrtok(var);
- for i=1:k.len
- if strfind(k.tb{i},'||')
- k.b(k.bos(i):k.eos(i))='|';
- end
- end
- var=k.b;
- var=strrep(var,char(0),'|');
- v=get_bracket(vart);
- var=v.s;
- if ~v.eflg
- var=astrrepx(var,'x',[v.eb;v.ee]);
- end
- for i=tmpl2
- var(vart==i)=i;
- end
- if ~v.eflg
- var(v.eb)='(';
- var(v.ee)=')';
- end
- var(vart==tmpl)=tmpl;
- % mask off dynamic field assignments
- ix=find(var==tmpl);
- for j=1:length(ix)
- px=ix(j);
- k=1;
- while px+k<vlen & isspace(var(px+k))
- k=k+1;
- end
- if var(px+k) == '('
- var(px+k)='X';
- while px+k<vlen & find(var(px+k)~=')')
- k=k+1;
- end
- var(px+k)='Y';
- end
- end
- for j=1:length(ix)
- % char both
- pref=0;
- suff=0;
- px=ix(j);
- k=1;
- while px+k<vlen & isspace(var(px+k))
- k=k+1;
- end
- if isletter(var(px+k)) | var(px+k) == tmpl
- suff=px+k;
- end
- px=ix(j);
- k=1;
- while px-k>1 & isspace(var(px-k))
- k=k+1;
- end
- if px-k > 0
- if ischar(var(px-k)) % letter | number
- pref=px-k;
- end
- end
- %D disp(sprintf('%5d %5d %5d-%5d <%s> [%d]',j,px,pref,suff,var(pref:suff),isletter(var(pref))))
- % ... ok
- if pref & suff
- % search right
- while suff<=vlen & ~isspace(var(suff)) & isempty(find(var(suff)==tmpl1))
- suff=suff+1;
- end
- suff=suff-1;
- % search left
- while pref>0 & ~isspace(var(pref)) & isempty(find(var(pref)==tmpl1))
- pref=pref-1;
- end
- pref=pref+1;
- % unflag for STRICT RULE!
- % if ~isletter(var(pref)) &
- % pref=0;
- % else
- %D disp(sprintf('%5d %5d %5d-%5d <%s> [%d]',j,px,pref,suff,var(pref:suff),isletter(var(pref))))
- % end
- it=it+1;
- stok{it,1}=pref-1;
- stok{it,2}=suff-1;
- end
- end
- var=vart;
- if it
- varz=char(' '*ones(size(var)));
- for i=1:it
- varz=astrrepx(varz,'|',[stok{i,1:2}]'+1);
- end
- k=astrtok(varz);
- stok=cell(size(k,1),7);
- i=0;
- for j=1:k.len
- %D disp(sprintf('%5d %5d-%5d <%s>',j,k.bos(j),k.eos(j),var(k.bos(j):k.eos(j))));
- vk=var(k.bos(j));
- if isletter(vk) | vk(1)=='.' | vk == ' '
- tvar=strrep(var(k.bos(j):k.eos(j)),' ','');
- if isempty(strfind(tvar,'..'))
- i=i+1;
- tok{i}=tvar;
- st=var(k.bos(j):k.eos(j));
- while st(end) == '.' | st(end) == ')'
- st=st(1:end-1);
- end
- if length(find(st=='(')) > length(find(st==')'))
- st(end+1)=')';
- end
- st(isspace(st))='';
- stok{i,1}=st;
- stok{i,2}='';
- stok{i,3}='field';
- stok{i,4}=length(stok{i,1});
- stok{i,5}=1;
- stok{i,6}=[k.bos(j);k.eos(j)];
- end
- end
- end
- varo(varz=='|')='|';
- end
- if isempty(tok)
- stok={};
- end
- varo(varo==tmpl)='|';
- b.s=varo;
- b.n=size(stok,1);
- b.t=tok;
- b.v=stok;
- return;
- %--------------------------------------------------------------------------------
- function b=get_bracket(k,b,flg)
- magic='get_bracket';
- if nargin < 2 | isempty(b)
- b='()';
- end
- if ischar(b)
- br=b;
- clear b; % R14+!
- b.magic=magic;
- b.bron=br(1);
- b.brof=br(2);
- end
- b.s=k;
- b.c=k;
- b.err=[];
- if nargin < 1 | isempty(k)
- b.eflg=-4;
- b.err=['no ' b.bron '...' b.brof ' found'];
- return;
- end
- b.eflg=0;
- klen=length(k);
- sz=char('_'*ones(1,klen));
- kb=length(find(k==b.bron));
- ke=length(find(k==b.brof));
- if ~kb & ~ke
- b.eflg=-3;
- b.err=['no ' b.bron '...' b.brof ' found'];
- return;
- elseif kb > ke
- b.eflg=-2;
- elseif kb < ke
- b.eflg=-1;
- end
- dep=0;
- depm=0;
- deps=0;
- kb=[];
- ke=[];
- zd=zeros(size(k));
- zs=zd;
- for i=1:klen
- if k(i)==b.bron
- dep=dep+1;
- depm=max(dep,depm);
- zd(i)=dep;
- if dep == 1
- deps=deps+1;
- zs(i)=deps;
- end
- end
- if k(i)==b.brof
- zd(i)=-dep;
- dep=dep-1;
- if dep == 0
- zs(i)=-deps;
- end
- end
- end
- kb=[];
- ke=[];
- kf=[];
- for i=1:depm+1
- kb=[kb find(zd==i)];
- ke=[ke find(zd==-i)];
- kf=[kf i*ones(size(find(zd==i)))];
- end
- if b.eflg
- if isempty(kb)
- kb=ke;
- kf=1;
- elseif isempty(ke)
- ke=1;
- end
- kdlen=length(kb)-length(ke);
- if kdlen
- ke(end:end+kdlen)=repmat(ke(end),1,kdlen+1);
- end
- end
- [kbs,kis]=sort(kb);
- kes=ke(kis);
- g=ones(size(kf));
- ix=1:length(g);
- ix=ix(1:length(kes));
- for i=2:depm
- iy=find(diff(kes(ix))<0);
- g(ix(iy))=i;
- ix=ix(iy);
- end
- zz={};
- for i=1:depm
- z=sz;
- ix=find(g==i);
- for j=ix
- z(kbs(j):kes(j))=k(kbs(j):kes(j));
- end
- zz=[zz;{z}];
- end
- zz=[zz;{k}];
- b.bl=size(kbs,2);
- b.depth=depm+1;
- b.ib=kbs;
- b.ie=kes;
- b.id=g;
- b.epoch=deps;
- b.eb=find(zs>0);
- b.ee=find(zs<0);
- b.z=char(zz);
- b.zd=zd;
- b.zs=cumsum(zs);
- if b.eflg | (isempty(kbs) & isempty(kes))
- berr='?';
- b.err=sz;
- if b.eflg == -1
- berr='-';
- elseif b.eflg == -2
- berr='+';
- end
- if isempty(kbs) & isempty(kes)
- ks=sort(find(k==b.bron | k==b.brof));
- b.err(ks(1))=berr;
- elseif b.eflg == -2 % beg > end
- ix=find(b.zs==max(b.zs));
- b.err(ix(1))=berr;
- elseif b.eflg == -1 % end > beg
- ix=find(b.zs>0);
- iy=find(b.c==b.brof);
- ix=setdiff(iy,ix+1);
- b.err(ix(1))=berr;
- end
- else
- b.zs(b.ee)=[1:b.epoch];
- b.s=astrrepx(b.s,'|',[b.eb;b.ee]);
- end
- return;
- %--------------------------------------------------------------------------------
- function [tb,bb,tbp]=astrtok(bb,pat,cflag)
- % [tb,b,tpb] = astrtok(string[,delimiter,cflag)
- % created:
- % us 10-Aug-1996
- if nargin < 2 | isempty(pat)
- pat=' ';
- end
- if nargin < 3 | isempty(cflag)
- cflag=0;
- end
- b=bb;
- tb={};
- u={};
- bl=length(b);
- pl=min(length(pat),bl);
- len=0;
- bos=[];
- eos=[];
- los=[];
- if ~isempty(b)
- b(isspace(b))=' ';
- if cflag
- while 1
- ix=strfind(b,' ');
- if isempty(ix)
- break;
- end
- b(ix)='';
- end
- b=deblank(b);
- b(strfind(b,' '))='';
- end
- if ~isempty(b)
- ix=strfind(b,pat);
- bos=[-pl+1 ix]+pl;
- los=diff([-pl+1 ix length(b)+pl])-pl;
- eos=min(bos+los-1,length(b));
- ix=find(eos>=bos);
- bos=bos(ix);
- eos=eos(ix);
- los=los(ix);
- len=length(bos);
- if isempty(len)
- len=0;
- end
- tb={};
- tb=cell(len,1);
- for i=1:len
- tb(i)={b(bos(i):eos(i))};
- end
- [u,j,k]=unique(tb);
- tt=cell(len,1);
- for i=1:len
- tt{i}=[bos(i) eos(i)];
- end
- for i=1:length(j);
- tp=reshape([tt{k==i}],2,length(find(k==i)));
- u(i,4)={tp};
- end
- end % ~isempty(len)
- end % ~isempty(b)
- tbp.tb=tb;
- tbp.u=u;
- tbp.b=bb;
- tbp.bl=length(bb);
- tbp.pat=pat;
- tbp.pl=pl;
- tbp.len=len;
- tbp.bos=bos;
- tbp.los=los;
- tbp.eos=eos;
- if nargout < 3
- tb=tbp;
- end
- return;
- %--------------------------------------------------------------------------------
- function [so,sp]=astrrepx(s,pat,pix,opat)
- % [s,sop] = astrrepx(str,npat,pix)
- % [s,sop] = astrrepx(str,npat,oix,opat)
- %
- % indexed string replacement:
- % str([inx11:inx12 inx21:inx22 ...])=npat
- %
- % str : input string: class <char> | <double>
- % pat : replacing pattern: class <char> | <double>
- %
- % pix : index into <s>
- % (2,N): [ beg1 beg2 ... begN
- % end1 end2 ... endN ]
- % (1,N): [ beg1 beg2 ... begN ]
- % endX = computed from <pat>length
- %
- % oix : index into occurrencies of <opat> in <s>
- % [] = all occurrencies
- % [nr(s)] = occurrencies [nr1 nr2 ... nrN]
- % nrX = <inf>
- % = last occurrence
- %
- % sop : replacement parameters <struct>
- %
- % note:
- % astrrepx only changes EXACT matches!
- %
- % examples:
- % s = astrrepx(s,pat,pix)
- % s = astrrepx(s,pat,oix,opat)
- %
- % s = astrrepx(s,pat,[1 4 10],opat)
- % s = astrrepx(s,pat,[],opat)
- % s = astrrepx(s,pat,[1 inf],opat)
- % v='d|dd|ddd|dd|dddd|dddddd';
- % created:
- % us 20-Dec-1993
- sp.pati=[];
- sp.opat=[];
- sp.pato=[];
- sp.pixi=[];
- sp.oixi=[];
- sp.nr=[];
- sp.nc=[];
- sp.pix=[];
- if nargin < 3
- help astrrepx;
- if nargout
- so=[];
- sp.msg='input parameters missing';
- end
- return;
- end
- %--------------------------------------------------------------------------------
- so=s;
- sp.pati=pat;
- sp.msg='running ...';
- if ~strcmp(class(s),class(pat))
- disp(sprintf('astrrepx> cannot merge input classes <%s>:<%s>',class(s),class(pat)));
- sp.msg='input classes do not match';
- return;
- end
- if ~ischar(s)
- [sp.nr,sp.nc]=size(s);
- s=s(:)';
- so=s;
- end
- %--------------------------------------------------------------------------------
- if nargin > 3
- pixi=pix;
- sp.opat=opat;
- sp.pixi=pixi;
- pix=findstr(s,opat);
- if isempty(pix)
- sp.msg='pattern not found';
- return;
- end
- pix=[pix;pix+length(opat)-1];
- pixl=size(pix,2);
- if isempty(pixi)
- pixi=[1:pixl];
- else
- pixi=pixi(1,:);
- pixi(isinf(pixi))=pixl;
- pixi=unique(pixi(find(pixi>0 & pixi<=pixl)));
- end
- sp.opat=opat;
- sp.oixi=pixi;
- pix=pix(:,pixi);
- % pattern must be <exact> !
- pixex=find(pix(1,2:end)<=pix(2,1:end-1));
- pix(:,[pixex pixex+1])=[];
- if isempty(pix)
- sp.msg='exact pattern match not found';
- return;
- end
- end % nargin > 3
- %--------------------------------------------------------------------------------
- sp.pix=pix;
- [nr,nc]=size(pix);
- if nr == 1
- pix=[pix;pix+length(pat)-1];
- end
- if 0
- pixx=find(pix(2,:)>0 & pix(2,:)<=length(so));
- pix=pix(:,pixx);
- end
- % pattern length must be <exact> !
- if ischar(s)
- rlen=length(pat);
- plen=pix(2,1)-pix(1,1)+1;
- % allow diff pix.length in case pat.length == 1!
- if rlen == 1
- nc=rlen;
- plen=sum(pix(2,:)-pix(1,:)+1);
- end
- if plen < rlen
- pat=pat(1:plen);
- elseif plen > rlen
- pat=(ones(ceil(plen/rlen),1)*pat)';
- pat=pat(1:plen);
- end
- end % input class <char>
- rpat=(ones(nc,1)*pat)';
- pixe=pix(2,:)+1;
- pixx=find(pixe<=length(so));
- k1=zeros(size(so));
- k2=k1;
- k1(pix(1,:))=1;
- k2(pixe(pixx))=-1;
- a=logical(cumsum(k1+k2));
- try
- so(a)=rpat;
- catch
- disp('astrrepx> this should NOT happen!')
- disp('astrrepx> please, contact <us@neurol.unizh.ch>');
- keyboard
- end
- if ~ischar(so)
- so=reshape(so,sp.nr,sp.nc);
- else
- pat=char(pat);
- end
- sp.pato=pat;
- sp.pix=pix;
- sp.msg='ok';
- return;
- %--------------------------------------------------------------------------------
- function lst=ini_lst(varargin)
- lst.magic='FPARSER';
- lst.ver='12-Dec-2005 09:26:17';
- lst.time=datestr(clock);
- lst.par.mos=version;
- lst.par.rel=sscanf(version('-release'),'%d');
- lst.par.opt.cflg=0; % input: command line
- lst.par.opt.dflg=0; % show res at run-time
- lst.tmpl=[];
- if nargin > 1
- if strmatch('-c',varargin,'exact')
- lst.par.opt.cflg=1;
- end
- if strmatch('-d',varargin,'exact')
- lst.par.opt.dflg=1;
- end
- end
- return;
- %--------------------------------------------------------------------------------