TDataSetIter.cxx

Go to the documentation of this file.
00001 // @(#)root/table:$Id: TDataSetIter.cxx 34913 2010-08-20 19:18:35Z pcanal $
00002 // Author: Valery Fine(fine@mail.cern.ch)   03/07/98
00003 
00004 /*************************************************************************
00005  * Copyright (C) 1995-2000, Rene Brun and Fons Rademakers.               *
00006  * All rights reserved.                                                  *
00007  *                                                                       *
00008  * For the licensing terms see $ROOTSYS/LICENSE.                         *
00009  * For the list of contributors see $ROOTSYS/README/CREDITS.             *
00010  *************************************************************************/
00011 
00012 #include "Riosfwd.h"
00013 #include "Riostream.h"
00014 
00015 #include "TDataSetIter.h"
00016 #include "TBrowser.h"
00017 #include "TSystem.h"
00018 
00019 #ifndef WIN32
00020 # ifndef HASSTRCASE
00021 #  define HASSTRCASE
00022 # endif
00023 #endif
00024 
00025 #ifndef HASSTRCASE
00026 #  define strcasecmp(arg1,arg2) stricmp(arg1,arg2)
00027 #endif
00028 
00029 TDataSet *TDataSetIter::fgNullDataSet = (TDataSet *)(-1);
00030 
00031 ClassImp(TDataSetIter)
00032 
00033 //////////////////////////////////////////////////////////////////////////
00034 //                                                                      //
00035 // TDataSetIter                                                         //
00036 //                                                                      //
00037 // TDataSetIter is a class iterator to navigate TDataSet objects        //
00038 // via 4 internal pointers :                                            //
00039 //                                                                      //
00040 //  1. fRootDataSet    - "root" dataset                                 //
00041 //  2. fWorkingDataSet - Working dataset                                //
00042 //  3. fDataSet        - the last selected TDataSet                     //
00043 //  4. fNext           - TIter for the the list of the "root" dataset   //
00044 //                                                                      //
00045 //////////////////////////////////////////////////////////////////////////
00046 
00047 //______________________________________________________________________________
00048 TDataSetIter::TDataSetIter(TDataSet *link, Bool_t dir)
00049 {
00050    //to be documented
00051    fWorkingDataSet= fRootDataSet   =link;
00052    fMaxDepth      = fDepth         =1;
00053    fDataSet= fgNullDataSet ;
00054    fNext = link ? new TIter(link->GetCollection() ,dir):0;
00055    for(UInt_t i = 0; i < sizeof(fNextSet) / sizeof(TIter*); ++i) {
00056       fNextSet[i] = (TIter*)0;
00057    }
00058 }
00059 
00060 //______________________________________________________________________________
00061 TDataSetIter::TDataSetIter(TDataSet *link, Int_t depth, Bool_t dir)
00062 {
00063    //to be documented
00064    fRootDataSet = fWorkingDataSet = link;
00065    fMaxDepth    = depth;
00066    fDepth       = 1;
00067    fDataSet     = fgNullDataSet;
00068    fNext        = (link)? new TIter(link->GetCollection() ,dir):0;
00069 
00070    // Create a DataSet iterator to pass all nodes of the
00071    //     "depth"  levels
00072    //  of  TDataSet *link
00073    
00074    for(UInt_t i = 0; i < sizeof(fNextSet) / sizeof(TIter*); ++i) {
00075       fNextSet[i] = (TIter*)0;
00076    }
00077    if (fMaxDepth != 1) {
00078       fNextSet[0] = fNext;
00079       if (fMaxDepth > 100) fMaxDepth = 100;
00080       fDepth = 0;
00081    }
00082 }
00083 
00084 //______________________________________________________________________________
00085 TDataSetIter::~TDataSetIter()
00086 {
00087    //to be documented
00088    if (fMaxDepth != 1) {
00089       Int_t level = fDepth;
00090       if (level) level--;
00091       for (Int_t i = level;i>=0;i--) {
00092          TIter *s = fNextSet[i];
00093          if (s) delete s;
00094       }
00095    }
00096    else
00097       SafeDelete(fNext);
00098    fDepth = 0;
00099 }
00100 
00101 
00102 //______________________________________________________________________________
00103 TDataSet *TDataSetIter::operator *() const 
00104 { 
00105    //operator *
00106    return fDataSet == fgNullDataSet ? fWorkingDataSet : fDataSet; 
00107 }
00108 
00109 //______________________________________________________________________________
00110 TDataSet *TDataSetIter::GetNullSet() 
00111 { 
00112    // return a fake pointer == -1 casted to (TDataSet *)
00113    return (TDataSet *)fgNullDataSet;  
00114 }
00115 
00116 //______________________________________________________________________________
00117 TDataSet *TDataSetIter::Add(TDataSet *set, TDataSet *dataset)
00118 {
00119    ///////////////////////////////////////////////////////////////////////////////
00120    //                                                                           //
00121    // Add - adds the set to the dataset defined with the second parameters      //
00122    //                                                                           //
00123    // TDataSet dataset != 0 - Add the set to the TDataSet *dataset              //
00124    //                                                                           //
00125    //                     = 0 - (by default) to the current TDataSet defined    //
00126    //                          with fWorkingDataSet data member                 //
00127    //                                                                           //
00128    //  returns  the pointer to set is success or ZERO poiner                    //
00129    //  =======                                                                  //
00130    //                                                                           //
00131    //  Note: If this TDataSetIter is empty (i.e. Cwd() returns 0), the "set"    //
00132    //        becomes the "root" dataset of this iterator                        //                                                                         //
00133    ///////////////////////////////////////////////////////////////////////////////
00134 
00135    if (!set) return 0;
00136    TDataSet *s =  dataset;
00137    if (!s) s = Cwd();
00138    if (s) {
00139       s->Add(set);
00140       s = set;
00141    }
00142    else {
00143       //  make the coming dataset the current one for the iterator
00144       s = set;
00145       fRootDataSet    = s;
00146       fWorkingDataSet = s;
00147       if (fNext) {
00148          Error("Add","TDataSetIter.has been corrupted ;-!");
00149          delete fNext;
00150          fNext = 0;
00151       }
00152       fNext = new TIter(s->GetCollection() );
00153    }
00154    return s;
00155 }
00156 
00157 //______________________________________________________________________________
00158 TDataSet *TDataSetIter::Add(TDataSet *dataset, const Char_t *path)
00159 {
00160    ///////////////////////////////////////////////////////////////////////////////
00161    //                                                                           //
00162    // Add                                                                       //
00163    //                                                                           //
00164    // Char_t path != 0 - Add a TDataSet dataset to the TDataSet dataset         //
00165    //                    defined with "path"                                    //
00166    //              = 0 - (by default) to the current TDataSet defined           //
00167    //                     with fWorkingDataSet data member                      //
00168    //                                                                           //
00169    //  returns the dataset is success or ZERO pointer                           //
00170    //  =======                                                                  //
00171    //                                                                           //
00172    ///////////////////////////////////////////////////////////////////////////////
00173    if (!dataset) return 0;
00174    TDataSet *set = 0;
00175    if (path && strlen(path)) set = Find(path);
00176    return Add(dataset,set);
00177 }
00178 
00179 //______________________________________________________________________________
00180 TDataSet *TDataSetIter::Cd(const Char_t *dirname){
00181    /////////////////////////////////////////////////////////////////////
00182    //                                                                 //
00183    // TDataSet *TDataSetIter::Cd(const Char_t *dirname)               //
00184    //                                                                 //
00185    // Change the current working directory to dirname                 //
00186    //                                                                 //
00187    // Returns the pointer to the new "working" TDataSet               //
00188    // =======   0,  if the new directory doesn't exist.               //
00189    //                                                                 //
00190    // Remark:  The name = ".." has a special meaning.                 //
00191    // ------   TDataSetIter::Cd("..") returns the parent set          //
00192    //          But one still can not use ".." as a legal part         //
00193    //          of the full path                                       //
00194    /////////////////////////////////////////////////////////////////////
00195    TDataSet *set = 0;
00196    if (strcmp(dirname,".."))
00197       set =  Find(dirname);
00198    else
00199       set = fWorkingDataSet->GetParent();
00200    if (set) fWorkingDataSet = set;
00201    return set;
00202 }
00203 
00204 //______________________________________________________________________________
00205 TDataSet *TDataSetIter::Cd(TDataSet *ds)
00206 {
00207    /////////////////////////////////////////////////////////////////////
00208    //                                                                 //
00209    // TDataSet *TDataSetIter::Cd(const TDataSet *ds)                  //
00210    //                                                                 //
00211    // Make:  Cwd() = ds;                                              //
00212    // Look for the first occurence of the "ds" pointer for the current//
00213    // TDataSet in respect of the Cwd() if any                         //
00214    //                                                                 //
00215    // Change the current working directory to ds if present           //
00216    //                                                                 //
00217    // Returns the pointer to the new "working" TDataSet (i.e. ds)     //
00218    // =======   0,  if the new directory doesn't exist.               //
00219    //                                                                 //
00220    /////////////////////////////////////////////////////////////////////
00221    TDataSet *nextSet = 0;
00222    if (Cwd()) {
00223       TDataSetIter next(Cwd(),0);
00224       while ( (nextSet = next()) )
00225          if (ds == nextSet) {fWorkingDataSet = ds; break;}
00226    }
00227    return nextSet;
00228 }
00229 
00230 //______________________________________________________________________________
00231 TDataSet *TDataSetIter::Dir(Char_t *dirname)
00232 {
00233    //
00234    // Print the names of the TDataSet objects for the datatset named with "dirname"
00235    // apart of TDataSet::Ls()  this method prints one level only
00236    //
00237    TDataSet *set = (TDataSet *)fWorkingDataSet;
00238    if (dirname) set = Find(dirname);
00239    if (set) set->ls();
00240    return set;
00241 }
00242 
00243 //______________________________________________________________________________
00244 Int_t TDataSetIter::Du() const {
00245    // summarize dataset usage by Herb Ward proposal
00246    if (!fWorkingDataSet) return 0;
00247    TDataSetIter next(fWorkingDataSet,0);
00248    TDataSet *nextset = 0;
00249    Int_t count = 0;
00250    while((nextset = (count) ? next():fWorkingDataSet)) {
00251       count++;
00252       if (nextset->IsFolder()) cout << endl;
00253       TString path = nextset->Path();
00254       cout << setw(2) << next.GetDepth() << ". ";
00255       cout << path << setw(TMath::Max(Int_t(60-strlen(path.Data())),Int_t(0))) << "...";
00256       const Char_t *type = nextset->IsFolder() ? "directory" : "table" ;
00257       cout << setw(10) << type;
00258       cout  << " : " << setw(10) << nextset->GetTitle();
00259       cout << endl;
00260    }
00261    return count;
00262 }
00263 
00264 //______________________________________________________________________________
00265 TDataSet  *TDataSetIter::FindByName(const Char_t *name,const Char_t *path,Option_t *opt)
00266 {
00267    //to be documented
00268    return FindDataSet(name,path,opt);
00269 }
00270 
00271 //______________________________________________________________________________
00272 TDataSet  *TDataSetIter::FindByTitle(const Char_t *title,const Char_t *path,Option_t *opt)
00273 {
00274    //to be documented
00275    TString optt = "-t";
00276    optt += opt;
00277    return FindDataSet(title,path,optt.Data());
00278 }
00279 
00280 //______________________________________________________________________________
00281 TDataSet *TDataSetIter::FindDataSet(const Char_t *name,const Char_t *path,Option_t *opt)
00282 {
00283    //
00284    // FindDataSet looks for the object with the name supplied across dataset.
00285    //
00286    // name        - the "base" name title (with no path) of the TDataSet (see: opt = -t)
00287    // path        - path to start the search from (the current dataset "by default")
00288    // opt = "-i"  - case insensitive search
00289    //       "-t"  - first <name> parameter defines the object "title" rather the object "name"
00290    //
00291    // Note: If the name provided is not unique
00292    //       the first found is returned.
00293    //
00294 
00295    if (!name || strlen(name) == 0) return 0;
00296    if (strchr(name,'/')) {
00297       Error("FindDataSet","The name of the object <%s> can not contain any \"/\"",name);
00298       return 0;
00299    }
00300 
00301    Bool_t opti = opt ? strcasecmp(opt,"-i") == 0 : kFALSE;
00302    Bool_t optt = opt ? strcasecmp(opt,"-t") == 0 : kFALSE;
00303 
00304    TDataSet *startset = 0;
00305    if (path && strlen(path)) startset = Find(path);
00306    else                      startset = fWorkingDataSet;
00307    if (!startset) return 0;
00308 
00309    TDataSet *set = startset;
00310    if ( !((opti && strcasecmp( optt ? set->GetTitle() : set->GetName(),name) == 0 ) ||
00311       (strcmp(optt ? set->GetTitle() : set->GetName(),name) == 0)) )
00312    {
00313       TDataSetIter next(startset,0);
00314       while ((set = next()))
00315          if ( (opti && strcasecmp(optt ? set->GetTitle() : set->GetName(),name) == 0 ) ||
00316             (strcmp(optt ? set->GetTitle() : set->GetName(),name) == 0) )           break;
00317    }
00318 
00319    return set;
00320 }
00321 
00322 //______________________________________________________________________________
00323 TDataSet *TDataSetIter::FindDataSet(TDataSet *set,const Char_t *path,Option_t *opt)
00324 {
00325    //
00326    // Check whether the object does belong the TDataSet defined with "path"
00327    // opt = "-l"  - check the "reference" links only
00328    //       "-s"  - check the "structural" links only
00329    //             = "by default" - checks all links
00330    //
00331    if (!set) return 0;
00332    if (opt) {/* no used */}
00333 
00334    TDataSet *startset = 0;
00335    if (path) startset = Find(path);
00336    else      startset = fWorkingDataSet;
00337    if (!startset) return 0;
00338 
00339    TDataSetIter next(startset);
00340    TDataSet *nextSet = 0;
00341    while ( (nextSet = next()) )
00342       if (set == nextSet) break;
00343 
00344    return nextSet;
00345 }
00346 //______________________________________________________________________________
00347 TObject *TDataSetIter::FindObject(const Char_t *name) const
00348 {
00349    // This method is not recommended.
00350    // It is done to back TObject::FindObject method only.
00351    // One is recommnened to use FindByName method instead.
00352    return ((TDataSetIter *)this)->FindByName(name);
00353 }
00354 
00355 //______________________________________________________________________________
00356 TObject  *TDataSetIter::FindObject(const TObject *dataset) const
00357 {
00358    // This method is not recommended.
00359    // It is done to back TObject::FindObject method only.
00360    // One is recommended to use FindByName method instead.
00361    return ((TDataSetIter *)this)->FindByPointer((TDataSet *)dataset);
00362 }
00363 //______________________________________________________________________________
00364 TDataSet *TDataSetIter::FindByPointer(TDataSet *set,const Char_t *path,Option_t *)
00365 {
00366    //
00367    // Check whether the object does belong the TDataSet defined with "path"
00368    // opt = "-l"  - check the "reference" links only
00369    //       "-s"  - check the "structural" links only
00370    //             = "by default" - checks all links
00371    //
00372    if (!set) return 0;
00373 
00374    TDataSet *startset = 0;
00375    if (path && path[0]) startset = Find(path);
00376    else      startset = fWorkingDataSet;
00377    if (!startset) return 0;
00378 
00379    TDataSetIter next(startset);
00380    TDataSet *nextSet = 0;
00381    while ( (nextSet = next()) )
00382       if (set == nextSet) break;
00383 
00384    return nextSet;
00385 }
00386 
00387 //______________________________________________________________________________
00388 Int_t TDataSetIter::Flag(const Char_t *path,UInt_t flag,TDataSet::EBitOpt reset)
00389 {
00390    //to be documented
00391    TDataSet *set = Find(path);
00392    if (set) set->SetBit(flag,reset);
00393    return 0;
00394 }
00395 //______________________________________________________________________________
00396 Int_t TDataSetIter::Flag(TDataSet *dataset,UInt_t flag,TDataSet::EBitOpt reset)
00397 {
00398    //to be documented
00399    if (dataset) dataset->SetBit(flag,reset);
00400    return 0;
00401 }
00402 
00403 //______________________________________________________________________________
00404 TDataSet *TDataSetIter::Ls(const Char_t *dirname,Option_t *opt) const {
00405    //
00406    //   Ls(const Char_t *dirname,Option_t)
00407    //
00408    //   Prints the list of the TDataSet defined with dirname
00409    //
00410    //   dirname     = 0   - prints the current dataset
00411    //   dirname[0]  = '/' - print TDataSet defined with dirname
00412    //   dirname[0] != '/' - prints DataSet with respect of the current class
00413    //
00414 
00415    TDataSet *set= 0;
00416    if (dirname && strlen(dirname)) set = ((TDataSetIter*)this)->Find(dirname);
00417    if (!set && dirname==0) set=Cwd();
00418    if (set) set->ls(opt);
00419    return set;
00420 }
00421 
00422 //______________________________________________________________________________
00423 TDataSet *TDataSetIter::Ls(const Char_t *dirname,Int_t depth) const {
00424    //
00425    //   Ls(const Char_t *dirname,Int_t depth)
00426    //
00427    //   Prints the list of the TDataSet defined with dirname
00428    //   Returns the dataset defined by "path" or Cwd();
00429    //
00430    //   dirname     = 0   - prints the current dataset
00431    //   dirname[0]  = '/' - print TDataSet defined with dirname
00432    //   dirname[0] != '/' - prints DataSet with respect of the current class
00433    //
00434    //   depth       = 0   - print all level of the TDataSet defined with dirname
00435    //               > 0   - print depth levels at most of the dirname TDataSet
00436    //
00437    TDataSet *set= fWorkingDataSet;
00438    if (dirname && strlen(dirname)) set= ((TDataSetIter*)this)->Find(dirname);
00439    if (set) set->ls(depth);
00440    return set;
00441 }
00442 
00443 //______________________________________________________________________________
00444 TDataSet *TDataSetIter::Mkdir(const Char_t *dirname)
00445 {
00446    //to be documented
00447    TDataSet *set = 0;
00448    set = Find(dirname,0,kTRUE);
00449    if (!fNext)  Reset();  // Create a new iterator
00450    // If this dataset is first one then make it the root and working
00451    if (!fRootDataSet ) fRootDataSet  = set;
00452    if (!fWorkingDataSet) fWorkingDataSet = fRootDataSet;
00453    return set;
00454 }
00455 
00456 //______________________________________________________________________________
00457 void TDataSetIter::Notify(TDataSet *)
00458 {
00459    //
00460    //  Notify(TDataSet *dataset)
00461    //
00462    //  This dummy method is called when TDataSetIter::Find dives in "dataset"
00463    //  to look for thew next level of the dataset's
00464    //  printf("void TDataSetIter::Notify(TDataSet *) level: %d %s\n",fDepth,ds->GetName());
00465    //
00466 }
00467 
00468 //______________________________________________________________________________
00469 TDataSet *TDataSetIter::Rmdir(TDataSet *dataset,Option_t *)
00470 {
00471    //
00472    //  Remove the TDataSet *dataset from the current dataset
00473    //  If the current dataset is the deleted dataset the its parent
00474    //  becomes the "current dataset" or 0 if this dataset has no parent.
00475    //
00476    //  returns: the "current dataset" pointer
00477    //
00478    //
00479    TDataSet *set = dataset;
00480    if (set) {
00481       if (set == fWorkingDataSet) {
00482          fWorkingDataSet = set->GetParent();
00483       }
00484       if (set == fRootDataSet) {
00485          fRootDataSet = 0;
00486       }
00487       delete set;
00488    }
00489    return Cwd();
00490 }
00491 
00492 //______________________________________________________________________________
00493 TDataSet *TDataSetIter::Next( TDataSet::EDataSetPass mode)
00494 {
00495    ////////////////////////////////////////////////////////////////////////////////
00496    //
00497    // returns the pointer the "next" TDataSet object
00498    //         = 0 if all objects have been returned.
00499    //
00500    //  mode = kContinue  - default normal mode
00501    //         kPrune     - stop passing of the current branch but continue with the next one if any
00502    //         kUp        - break passing, return to the previous level, then continue
00503    //         all other  - are treated as "kContinue"
00504    //
00505    ////////////////////////////////////////////////////////////////////////////////
00506 
00507    if (fMaxDepth==1) fDataSet = fNext ? NextDataSet(*fNext) :0;
00508    else {
00509       // Check the whether the next level does exist
00510       if (fDepth==0) fDepth = 1;
00511       if (fDataSet && fDataSet != fgNullDataSet &&
00512          (fDepth < fMaxDepth || fMaxDepth ==0) && mode == TDataSet::kContinue )
00513       {
00514          // create the next level iterator, go deeper
00515          TSeqCollection *list  = fDataSet->GetCollection();
00516          // Look for the next level
00517          if (list && list->GetSize() ) {
00518             fDepth++;
00519             if (fDepth >= 100) {
00520                Error("Next()"
00521                   ," too many (%d) nested levels of your TDataSet has been detected",fDepth);
00522                return 0;
00523             }
00524             fNextSet[fDepth-1] = new TIter(list);
00525          }
00526       }
00527 
00528       // Pick the next object of the current level
00529       TIter *next = fNextSet[fDepth-1];
00530       if (next) {
00531          fDataSet = 0;
00532          if (mode != TDataSet::kUp) fDataSet = NextDataSet(*next);
00533 
00534          // Go upstair if the current one has been escaped
00535          if (!fDataSet) {
00536             // go backwards direction
00537             while (!fDataSet && fDepth > 1) {
00538                fDepth--;
00539                delete next;
00540                next =  fNextSet[fDepth-1];
00541                TDataSet *set = NextDataSet(*next);
00542                if (set)
00543                   fDataSet = set;
00544             }
00545          }
00546       }
00547    }
00548    return (TDataSet *)fDataSet;
00549 }
00550 //______________________________________________________________________________
00551 TDataSet *TDataSetIter::NextDataSet(TIter &next)
00552 {
00553    //to be documented
00554    TDataSet *ds = (TDataSet *)next();
00555    if (ds) Notify(ds);
00556    return ds;
00557 }
00558 
00559 //______________________________________________________________________________
00560 TDataSet *TDataSetIter::NextDataSet(Int_t nDataSet)
00561 {
00562    // Pick the next object of the  level provided
00563    TIter *next = fNextSet[nDataSet];
00564    if (next) return NextDataSet(*next);
00565    return 0;
00566 }
00567 //______________________________________________________________________________
00568 TDataSet  *TDataSetIter::FindByPath(const Char_t *path, TDataSet *rootset,Bool_t mkdir)
00569 {
00570    //to be documented
00571    return Find(path,rootset,mkdir);
00572 }
00573 
00574 //______________________________________________________________________________
00575 TDataSet *TDataSetIter::Find(const Char_t *path, TDataSet *rootset,
00576                              Bool_t mkdirflag,Bool_t titleFlag)
00577 {
00578    ////////////////////////////////////////////////////////////////////////////////
00579    //                                                                            //
00580    //     titleFlag = kFALSE; use object name as key (by default)                //
00581    //                 kTRUE;  use object title as key  and ignore mkdirFlag      //
00582    //                                                                            //
00583    //           "path" ::= <relative path> | <absolute path> | <empty>           //
00584    //                                                                            //
00585    //  "relative path" ::= <dataset name> | <dataset name>/<dataset name>        //
00586    //                                                                            //
00587    //  "absolute path" ::= /<relative path>                                      //
00588    //  "empty"         ::= zero pointer | pointer to zero length string          //
00589    //                                                                            //
00590    // "relative path": the search is done against of fWorkingDataSet data mem    //
00591    // "absolute path": the search is done against of fRootDataSet    data mem    //
00592    // "empty path"   : no search is done just next TDataSet is returned if any   //
00593    //                                                                            //
00594    //  Remark: This version can not treat any "special name" like "..", ".", etc //
00595    //  ------                                                                    //
00596    ////////////////////////////////////////////////////////////////////////////////
00597    TDataSet *dataset=0,*dsnext=0,*ds=0;
00598    Int_t len=0,nextlen=0,yes=0,anywhere=0,rootdir=0;
00599    const Char_t *name=0,*nextname=0;
00600    TSeqCollection *tl=0;
00601 
00602    name = path;
00603    if (!name) return rootset;
00604    dataset = rootset;
00605    if (!dataset) {// Starting point
00606       rootdir = 1999;
00607       dataset = (path[0]=='/') ? fRootDataSet:fWorkingDataSet;}
00608 
00609    if (name[0] == '/') name++;
00610 
00611    if (!strncmp(name,".*/",3)) {anywhere=1998; name +=3;}
00612 
00613    len = strcspn(name," /");
00614    if (!len) return dataset;
00615 
00616    if (!dataset) goto NOTFOUND;
00617 
00618    //      Check name of root directory
00619    if (rootdir)
00620    {
00621       nextname = titleFlag ? dataset->GetTitle() : dataset->GetName();
00622       nextlen  = strlen(nextname);
00623       if (nextlen==len && !strncmp(name,nextname,len))
00624          return Find(name+len,dataset,mkdirflag,titleFlag);
00625    }
00626 
00627    tl = dataset->GetCollection();
00628    if (tl) {
00629       TIter next(tl);
00630       while ( (dsnext = NextDataSet(next)) )
00631       { //horisontal loop
00632          nextname = titleFlag ? dataset->GetTitle() : dsnext->GetName();
00633          if (!nextname)  continue;
00634          yes = name[0]=='*';     // wildcard test
00635          if (!yes) {             // real     test
00636             nextlen  = strlen(nextname);
00637             yes = (len == nextlen);
00638             if (yes)
00639                yes = !strncmp(name,nextname,len);
00640          }
00641 
00642          if (yes)
00643          {//go down
00644             if (fDepth == 0) fDepth = 1;
00645             Notify(dsnext);
00646             fDepth++;
00647             ds = Find(name+len,dsnext,mkdirflag,titleFlag);
00648             fDepth--;
00649             if (ds)
00650                return ds;
00651          }
00652 
00653          if (!anywhere) continue;        // next horizontal
00654          ds = Find(name,dsnext,mkdirflag,titleFlag);
00655          if (ds)
00656             return ds;
00657       }                                  // end of while
00658    }
00659 
00660 NOTFOUND:
00661    if (mkdirflag && !titleFlag)
00662    {
00663       // create dir the same type as the type of the fRootDataSet if present
00664       // Create TDataSet by default.
00665       char buf[512];buf[0]=0; strncat(buf,name,len);
00666       if (!fRootDataSet)
00667          ds = new TDataSet(buf);
00668       else {
00669          ds = fRootDataSet->Instance();
00670          ds->SetName(buf);
00671       }
00672 
00673       if (!fRootDataSet)         fRootDataSet    = ds;
00674       if (!fWorkingDataSet)      fWorkingDataSet = ds;
00675       if (dataset)
00676          dataset->Add(ds);
00677       else {
00678          dataset = ds;
00679          name +=len;
00680       }
00681 
00682       return Find(name,dataset,mkdirflag);
00683    }
00684 
00685    return 0;
00686 }
00687 //______________________________________________________________________________
00688 void TDataSetIter::Reset(TDataSet *l, int depth)
00689 {
00690    //
00691    // TDataSet *l != 0 means the new start pointer
00692    //    depth      != 0 means the new value for the depth
00693    //                    otherwise the privious one is used;
00694    //
00695    fDataSet = fgNullDataSet;
00696    if (fMaxDepth != 1) {
00697       // clean all interators
00698       Int_t level = fDepth;
00699       if (level) level--;
00700       for (int i = level;i>=0;i--) {
00701          TIter *s = fNextSet[i];
00702          if (s) delete s;
00703       }
00704       fNext = 0; // this iterator has been deleted in the loop above
00705    }
00706 
00707    fDepth = 0;
00708 
00709    if (l) {
00710       fRootDataSet    = l;
00711       fWorkingDataSet = l;
00712       SafeDelete(fNext);
00713       if (fRootDataSet->GetCollection() )
00714          fNext = new TIter(fRootDataSet->GetCollection() );
00715    }
00716    else {
00717       fWorkingDataSet = fRootDataSet;
00718       if (fNext)
00719          fNext->Reset();
00720       else if (fRootDataSet && fRootDataSet->GetCollection() )
00721          fNext = new TIter(fRootDataSet->GetCollection() );
00722    }
00723    // set the new value of the maximum depth to bypass
00724    if (depth) fMaxDepth = depth;
00725 }
00726 //______________________________________________________________________________
00727 TDataSet *TDataSetIter::Shunt(TDataSet *set, TDataSet *dataset)
00728 {
00729    ///////////////////////////////////////////////////////////////////////////////
00730    //                                                                           //
00731    // Shunt - moves the set to the dataset defined with the second parameters   //
00732    //                                                                           //
00733    // TDataSet dataset != 0 - Add the set to the TDataSet *dataset              //
00734    //                                                                           //
00735    //                     = 0 - (by default) to the current TDataSet defined    //
00736    //                          with fWorkingDataSet data member                 //
00737    //                                                                           //
00738    //  returns  the pointer to set if successful or ZERO pointer                //
00739    //  =======                                                                  //
00740    //                                                                           //
00741    //  Note: If this TDataSetIter is empty (i.e. Cwd() returns 0), the "set"    //
00742    //        becomes the "root" dataset of this iterator                        //                                                                         //
00743    ///////////////////////////////////////////////////////////////////////////////
00744 
00745    if (!set) return 0;
00746    TDataSet *s =  dataset;
00747    if (!s) s = Cwd();
00748    if (s) {
00749       s->Shunt(set);
00750       s = set;
00751    }
00752    else {
00753       //  make the coming dataset the current one for the iterator
00754       s = set;
00755       fRootDataSet    = s;
00756       fWorkingDataSet = s;
00757       if (fNext) {
00758          Error("Shunt","TDataSetIter.has been corrupted ;-!");
00759          delete fNext;
00760          fNext = 0;
00761       }
00762       fNext = new TIter(s->GetCollection() );
00763    }
00764    return s;
00765 }
00766 
00767 //______________________________________________________________________________
00768 TDataSet *TDataSetIter::Shunt(TDataSet *dataset, const Char_t *path)
00769 {
00770    ///////////////////////////////////////////////////////////////////////////////
00771    //                                                                           //
00772    // Shunt                                                                     //
00773    //                                                                           //
00774    // Char_t path != 0 - Move a TDataSet dataset from its parent to             //
00775    //                    the TDataSet dataset                                   //
00776    //                    defined with "path"                                    //
00777    //              = 0 - (by default) to the current TDataSet defined           //
00778    //                    with fWorkingDataSet data member                       //
00779    //                                                                           //
00780    //  returns the dataset is success or ZERO pointer                           //
00781    //  =======                                                                  //
00782    //                                                                           //
00783    ///////////////////////////////////////////////////////////////////////////////
00784    if (!dataset) return 0;
00785    TDataSet *set = 0;
00786    if (path && strlen(path)) set = Find(path);
00787    return Shunt(dataset,set);
00788 }
00789 
00790 //______________________________________________________________________________
00791 TDataSet *TDataSetIter::operator[](const Char_t *path)
00792 {
00793    //
00794    // operator [] returns the pointer to the TDataSet if it does contain
00795    // any data (TTable for example)
00796    //
00797    //  Input:
00798    //     path  = The path to the dataset to find
00799    //
00800    //  Output:
00801    //     pointer to the dataset if it found and
00802    //     its TDataSet::HasData() method returns non-zero
00803    //     (see for example TTable::HasData() )
00804    TDataSet *dataSet = Find(path);
00805    if (dataSet && dataSet->HasData()) return dataSet;
00806    return 0;
00807 }

Generated on Tue Jul 5 14:45:01 2011 for ROOT_528-00b_version by  doxygen 1.5.1