Geant4 Cross Reference |
1 // Copyright (C) 2010, Guy Barrand. All rights 2 // See the file tools.license for terms. 3 4 #ifndef tools_rroot_ntuple 5 #define tools_rroot_ntuple 6 7 // to have same API than rcsv::ntuple. 8 9 #include "../rntuple" 10 11 #include "tree" 12 #include "leaf" 13 #include "stl_vector" 14 15 #include "../cids" 16 #include "../vfind" 17 #include "../vmanip" 18 #include "../ntuple_binding" 19 #include "../get_lines" 20 21 #ifdef TOOLS_MEM 22 #include "../mem" 23 #endif 24 25 namespace tools { 26 namespace rroot { 27 28 class ntuple : public virtual read::intuple { 29 typedef read::intuple parent; 30 public: 31 static const std::string& s_class() { 32 static const std::string s_v("tools::rroot 33 return s_v; 34 } 35 virtual const std::string& s_cls() const {re 36 public: //intuple 37 virtual void start() {m_index = -1;} 38 virtual bool next() { 39 m_index++; 40 if((uint64)m_index>=m_tree.entries()) retu 41 return true; 42 } 43 virtual read::icol* find_icol(const std::str 44 return find_named<read::icol>(m_cols,a_nam 45 } 46 virtual const std::vector<read::icol*>& colu 47 virtual const std::string& title() const {re 48 virtual bool number_of_entries(uint64 & a_va 49 public: 50 51 template <class T,class LEAF> 52 class column_ref : public virtual read::icol 53 typedef read::icolumn<T> parent; 54 public: 55 static cid id_class() {return 200+_cid(T() 56 public: //icol 57 virtual void* cast(cid a_class) const { 58 if(void* p = cmp_cast<column_ref>(this,a 59 return parent::cast(a_class); 60 } 61 virtual cid id_cls() const {return id_clas 62 public: //icol 63 virtual const std::string& name() const {r 64 public: //icolumn<T> 65 virtual bool fetch_entry() const {return _ 66 virtual bool get_entry(T& a_v) const { 67 if(!_fetch_entry()) {a_v = T();return fa 68 a_v = m_ref; 69 return true; 70 } 71 public: 72 column_ref(ifile& a_file,branch& a_branch, 73 :m_file(a_file) 74 ,m_branch(a_branch) 75 ,m_leaf(a_leaf) 76 ,m_index(a_index) //WARNING : we keep the 77 ,m_ref(a_ref) 78 {} 79 virtual ~column_ref(){} 80 protected: 81 column_ref(const column_ref& a_from) 82 :read::icol(a_from) 83 ,parent(a_from) 84 ,m_file(a_from.m_file) 85 ,m_branch(a_from.m_branch) 86 ,m_leaf(a_from.m_leaf) 87 ,m_index(a_from.m_index) 88 ,m_ref(a_from.m_ref) 89 {} 90 column_ref& operator=(const column_ref& a_ 91 if(&a_from==this) return *this; 92 return *this; 93 } 94 protected: 95 //typedef typename LEAF::value_t value_t; 96 bool _fetch_entry() const { 97 unsigned int n; 98 if(!m_branch.find_entry(m_file,uint32(m_ 99 if(!m_leaf.num_elem()) {m_ref = T();retu 100 typename LEAF::value_t _tmp; 101 if(!m_leaf.value(0,_tmp)) return false; 102 m_ref = T(_tmp); 103 return true; 104 } 105 protected: 106 ifile& m_file; 107 branch& m_branch; 108 LEAF& m_leaf; 109 int64& m_index; //WARNING : a ref. 110 T& m_ref; 111 //value_t m_tmp; 112 }; 113 114 template <class T,class LEAF> 115 class column : public column_ref<T,LEAF> { 116 typedef column_ref<T,LEAF> parent; 117 public: 118 static cid id_class() {return 200+_cid(T() 119 public: //icol 120 virtual void* cast(cid a_class) const { 121 if(void* p = cmp_cast<column>(this,a_cla 122 return parent::cast(a_class); 123 } 124 virtual cid id_cls() const {return id_clas 125 public: 126 column(ifile& a_file,branch& a_branch,LEAF 127 :parent(a_file,a_branch,a_leaf,a_index,m_v 128 ,m_value(T()) 129 {} 130 virtual ~column(){} 131 protected: 132 column(const column& a_from) 133 :read::icol(a_from) 134 ,read::icolumn<T>(a_from) 135 ,parent(a_from) 136 ,m_value(a_from.m_value) 137 {} 138 column& operator=(const column& a_from){ 139 if(&a_from==this) return *this; 140 m_value = a_from.m_value; 141 return *this; 142 } 143 public: 144 const T& get_value() const {return m_value 145 protected: 146 T m_value; 147 }; 148 149 class column_string_ref : public virtual rea 150 typedef read::icol parent; 151 public: 152 static cid id_class() { 153 static const std::string s_v; 154 return _cid(s_v)+10000; 155 } 156 public: //icol 157 virtual void* cast(cid a_class) const { 158 if(void* p = cmp_cast<column_string_ref> 159 return 0; 160 } 161 virtual cid id_cls() const {return id_clas 162 virtual const std::string& name() const {r 163 public: 164 virtual bool fetch_entry() const {return _ 165 public: 166 column_string_ref(ifile& a_file,branch& a_ 167 :m_file(a_file) 168 ,m_branch(a_branch) 169 ,m_leaf(a_leaf) 170 ,m_index(a_index) //WARNING : we keep the 171 ,m_ref(a_ref) 172 {} 173 virtual ~column_string_ref(){} 174 protected: 175 column_string_ref(const column_string_ref& 176 :parent(a_from) 177 ,m_file(a_from.m_file) 178 ,m_branch(a_from.m_branch) 179 ,m_leaf(a_from.m_leaf) 180 ,m_index(a_from.m_index) 181 ,m_ref(a_from.m_ref) 182 {} 183 column_string_ref& operator=(const column_ 184 if(&a_from==this) return *this; 185 return *this; 186 } 187 public: 188 bool get_entry(std::string& a_v) const { 189 if(!_fetch_entry()) {a_v.clear();return 190 a_v = m_ref; 191 return true; 192 } 193 protected: 194 bool _fetch_entry() const { 195 unsigned int n; 196 if(!m_branch.find_entry(m_file,uint32(m_ 197 const char* _cs = m_leaf.value(); 198 if(!_cs) {m_ref.clear();return false;} 199 m_ref = _cs; 200 return true; 201 } 202 protected: 203 ifile& m_file; 204 branch& m_branch; 205 leaf_string& m_leaf; 206 int64& m_index; //WARNING : a ref. 207 std::string& m_ref; 208 }; 209 210 class column_string : public column_string_r 211 typedef column_string_ref parent; 212 public: 213 static cid id_class() { 214 static const std::string s_v; 215 return _cid(s_v); 216 } 217 public: //icol 218 virtual void* cast(cid a_class) const { 219 if(void* p = cmp_cast<column_string>(thi 220 return parent::cast(a_class); 221 } 222 virtual cid id_cls() const {return id_clas 223 virtual const std::string& name() const {r 224 public: 225 column_string(ifile& a_file,branch& a_bran 226 :parent(a_file,a_branch,a_leaf,a_index,m_v 227 {} 228 virtual ~column_string(){} 229 protected: 230 column_string(const column_string& a_from) 231 :read::icol(a_from) 232 ,parent(a_from) 233 ,m_value(a_from.m_value) 234 {} 235 column_string& operator=(const column_stri 236 if(&a_from==this) return *this; 237 m_value = a_from.m_value; 238 return *this; 239 } 240 public: 241 const std::string& get_value() const {retu 242 protected: 243 std::string m_value; 244 }; 245 246 class column_vector_string_ref : public colu 247 typedef column_string_ref parent; 248 public: 249 static cid id_class() {return _cid_std_vec 250 public: //icol 251 virtual void* cast(cid a_class) const { 252 if(void* p = cmp_cast<column_vector_stri 253 return parent::cast(a_class); 254 } 255 virtual cid id_cls() const {return id_clas 256 virtual const std::string& name() const {r 257 public: 258 virtual bool fetch_entry() const {return _ 259 public: 260 column_vector_string_ref(ifile& a_file,bra 261 std::vector<std:: 262 :parent(a_file,a_branch,a_leaf,a_index,m_v 263 ,m_ref(a_ref) 264 ,m_sep(a_sep) 265 {} 266 virtual ~column_vector_string_ref(){} 267 protected: 268 column_vector_string_ref(const column_vect 269 :read::icol(a_from) 270 ,parent(a_from) 271 ,m_ref(a_from.m_ref) 272 ,m_sep(a_from.m_sep) 273 {} 274 column_vector_string_ref& operator=(const 275 if(&a_from==this) return *this; 276 m_sep = a_from.m_sep; 277 return *this; 278 } 279 public: 280 bool get_entry(std::vector<std::string>& a 281 if(!_fetch_entry()) {a_v.clear();return 282 a_v = m_ref; 283 return true; 284 } 285 protected: 286 bool _fetch_entry() const { 287 if(!parent::_fetch_entry()) return false 288 get_lines(m_value,m_ref); 289 return true; 290 } 291 protected: 292 std::vector<std::string>& m_ref; 293 char m_sep; 294 std::string m_value; 295 }; 296 297 class column_vector_string : public column_v 298 typedef column_vector_string_ref parent; 299 public: 300 static cid id_class() {return _cid_std_vec 301 public: //icol 302 virtual void* cast(cid a_class) const { 303 if(void* p = cmp_cast<column_vector_stri 304 return parent::cast(a_class); 305 } 306 virtual cid id_cls() const {return id_clas 307 virtual const std::string& name() const {r 308 public: 309 column_vector_string(ifile& a_file,branch& 310 :parent(a_file,a_branch,a_leaf,a_index,m_v 311 {} 312 virtual ~column_vector_string(){} 313 protected: 314 column_vector_string(const column_vector_s 315 :read::icol(a_from) 316 ,parent(a_from) 317 ,m_value(a_from.m_value) 318 {} 319 column_vector_string& operator=(const colu 320 if(&a_from==this) return *this; 321 m_value = a_from.m_value; 322 return *this; 323 } 324 public: 325 const std::vector<std::string>& get_value( 326 protected: 327 std::vector<std::string> m_value; 328 }; 329 330 // to read row_wise columns with vector of b 331 template <class T> 332 class std_vector_column_ref : public virtual 333 typedef read::icolumn<T> parent; 334 public: 335 static cid id_class() {return 200+_cid(T() 336 public: //icol 337 virtual void* cast(cid a_class) const { 338 if(void* p = cmp_cast<std_vector_column_ 339 return parent::cast(a_class); 340 } 341 virtual cid id_cls() const {return id_clas 342 public: //icol 343 virtual const std::string& name() const {r 344 public: //icolumn<T> 345 virtual bool fetch_entry() const {return _ 346 virtual bool get_entry(T& a_v) const { 347 if(!_fetch_entry()) {a_v = T();return fa 348 if(m_ref.empty()) {a_v = T();return fals 349 a_v = m_ref[0]; 350 return true; 351 } 352 public: 353 std_vector_column_ref(ifile& a_file,branch 354 :m_file(a_file) 355 ,m_branch(a_branch) 356 ,m_leaf(a_leaf) 357 ,m_index(a_index) //WARNING : we keep the 358 ,m_ref(a_ref) 359 {} 360 virtual ~std_vector_column_ref(){} 361 protected: 362 std_vector_column_ref(const std_vector_col 363 :read::icol(a_from) 364 ,parent(a_from) 365 ,m_file(a_from.m_file) 366 ,m_branch(a_from.m_branch) 367 ,m_leaf(a_from.m_leaf) 368 ,m_index(a_from.m_index) 369 ,m_ref(a_from.m_ref) 370 {} 371 std_vector_column_ref& operator=(const std 372 if(&a_from==this) return *this; 373 return *this; 374 } 375 protected: 376 bool _fetch_entry() const { 377 unsigned int n; 378 if(!m_branch.find_entry(m_file,uint32(m_ 379 m_leaf.value(m_ref); 380 return true; 381 } 382 protected: 383 ifile& m_file; 384 branch& m_branch; 385 leaf<T>& m_leaf; 386 int64& m_index; //WARNING : a ref. 387 std::vector<T>& m_ref; 388 }; 389 390 // to read column_wise columns with vector o 391 template <class RT,class T> 392 class column_element_ref : public virtual re 393 typedef read::icolumn<T> parent; 394 public: 395 static cid id_class() {return 300+_cid(T() 396 public: //icol 397 virtual void* cast(cid a_class) const { 398 if(void* p = cmp_cast<column_element_ref 399 return parent::cast(a_class); 400 } 401 virtual cid id_cls() const {return id_clas 402 public: //icol 403 virtual const std::string& name() const {r 404 public: //icolumn<T> 405 virtual bool fetch_entry() const {return _ 406 virtual bool get_entry(T& a_v) const { 407 if(!_fetch_entry()) {a_v = T();return fa 408 a_v = m_ref; 409 return true; 410 } 411 public: 412 column_element_ref(ifile& a_file,branch_el 413 :m_file(a_file) 414 ,m_be(a_branch) 415 ,m_leaf(a_leaf) 416 ,m_index(a_index) //WARNING : we keep the 417 ,m_ref(a_ref) 418 {} 419 virtual ~column_element_ref(){} 420 protected: 421 column_element_ref(const column_element_re 422 :read::icol(a_from),parent(a_from) 423 ,m_file(a_from.m_file) 424 ,m_be(a_from.m_be) 425 ,m_leaf(a_from.m_leaf) 426 ,m_index(a_from.m_index) 427 ,m_ref(a_from.m_ref) 428 {} 429 column_element_ref& operator=(const column 430 if(&a_from==this) return *this; 431 return *this; 432 } 433 protected: 434 bool _fetch_entry() const { 435 unsigned int n; 436 if(!m_be.find_entry(m_file,uint32(m_inde 437 iro* obj = m_be.object(); //Not owner. 438 if(!obj) {m_ref = T();return false;} 439 RT* v = id_cast<iro,RT>(*obj); 440 if(!v) {m_ref = T();return false;} 441 m_ref = *v; //it assumes a T::operator=( 442 return true; 443 } 444 protected: 445 ifile& m_file; 446 branch_element& m_be; 447 leaf_element& m_leaf; 448 int64& m_index; //WARNING : a ref. 449 T& m_ref; 450 }; 451 452 template <class RT,class T> 453 class column_element : public column_element 454 typedef column_element_ref<RT,T> parent; 455 public: 456 static cid id_class() {return 300+_cid(T() 457 public: //icol 458 virtual void* cast(cid a_class) const { 459 if(void* p = cmp_cast<column_element>(th 460 return parent::cast(a_class); 461 } 462 virtual cid id_cls() const {return id_clas 463 public: 464 column_element(ifile& a_file,branch_elemen 465 :parent(a_file,a_branch,a_leaf,a_index,m_v 466 ,m_value(T()) 467 {} 468 virtual ~column_element(){} 469 protected: 470 column_element(const column_element& a_fro 471 :read::icol(a_from) 472 ,read::icolumn<T>(a_from) 473 ,parent(a_from) 474 ,m_value(a_from.m_value) 475 {} 476 column_element& operator=(const column_ele 477 if(&a_from==this) return *this; 478 m_value = a_from.m_value; 479 return *this; 480 } 481 public: 482 const T& get_value() const {return m_value 483 protected: 484 T m_value; 485 }; 486 487 public: 488 ntuple(tree& a_tree):m_tree(a_tree),m_index( 489 #ifdef TOOLS_MEM 490 mem::increment(s_class().c_str()); 491 #endif 492 } 493 virtual ~ntuple() { 494 safe_clear<read::icol>(m_cols); 495 #ifdef TOOLS_MEM 496 mem::decrement(s_class().c_str()); 497 #endif 498 } 499 protected: 500 ntuple(const ntuple& a_from) 501 :parent(a_from),m_tree(a_from.m_tree){ 502 #ifdef TOOLS_MEM 503 mem::increment(s_class().c_str()); 504 #endif 505 } 506 ntuple& operator=(const ntuple&){return *thi 507 public: 508 bool initialize(std::ostream& a_out,const nt 509 safe_clear<read::icol>(m_cols); 510 511 std::vector<base_leaf*> leaves; 512 m_tree.find_leaves(leaves); 513 tools_vforcit(base_leaf*,leaves,it) { 514 base_leaf* bl = (*it); 515 if(find_named<read::icol>(m_cols,bl->nam 516 a_out << "tools::rroot::ntuple::initia 517 << " column with name " << sout( 518 << " already exists." 519 << std::endl; 520 safe_clear<read::icol>(m_cols); 521 return false; 522 } 523 branch* _branch = m_tree.find_leaf_branc 524 if(!_branch) { 525 a_out << "tools::rroot::ntuple::initia 526 << " can't find branch of leaf " 527 << std::endl; 528 safe_clear<read::icol>(m_cols); 529 return false; 530 } 531 532 //a_out << "tools::rroot::ntuple::initia 533 // << " branch " << _branch->name() 534 // << ", entries " << _branch->entr 535 // << std::endl; 536 537 #define TOOLS_RROOT_NTUPLE_CREATE_COL(a__type) 538 if(leaf<a__type>* lf_##a__type = safe_ca 539 cid user_cid;void* user_obj;\ 540 a_bd.find_user_obj(bl->name(),user_cid 541 typedef leaf<a__type> leaf_t;\ 542 if(!user_obj) {\ 543 if(a_enforce_double) {\ 544 column<double,leaf_t>* col = new c 545 m_cols.push_back(col);\ 546 } else {\ 547 column<a__type,leaf_t>* col = new 548 m_cols.push_back(col);\ 549 }\ 550 } else {\ 551 const base_leaf* lfc = bl->leaf_coun 552 if(lfc) {\ 553 /*::printf("debug : ntuple : creat 554 if(user_cid!=_cid_std_vector<a__ty 555 a_out << "tools::rroot::ntuple:: 556 << " for leaf with name " 557 << ", user variable type i 558 << std::endl;\ 559 safe_clear<read::icol>(m_cols);\ 560 return false;\ 561 }\ 562 std::vector<a__type>* user_var = ( 563 std_vector_column_ref<a__type>* co 564 (m_tree.file(),*_branch,*lf_##a__type, 565 m_cols.push_back(col);\ 566 } else {\ 567 /*::printf("debug : ntuple : creat 568 if(user_cid!=_cid(a__type())) {\ 569 a_out << "tools::rroot::ntuple:: 570 << " for leaf with name " 571 << ", user variable type i 572 << std::endl;\ 573 safe_clear<read::icol>(m_cols);\ 574 return false;\ 575 }\ 576 a__type* user_var = (a__type*)user 577 column_ref<a__type,leaf_t>* col =\ 578 new column_ref<a__type,leaf_t>(m 579 m_cols.push_back(col);\ 580 }\ 581 }\ 582 } 583 584 //below types are in sync with wroot/ntu 585 586 TOOLS_RROOT_NTUPLE_CREATE_COL(char) 587 else TOOLS_RROOT_NTUPLE_CREATE_COL(short 588 else TOOLS_RROOT_NTUPLE_CREATE_COL(int) 589 else TOOLS_RROOT_NTUPLE_CREATE_COL(float 590 else TOOLS_RROOT_NTUPLE_CREATE_COL(doubl 591 592 else if(leaf_string* ls = safe_cast<base 593 char sep = '\n'; 594 cid user_cid;void* user_obj; 595 if(!a_bd.find_user_obj(bl->name(),user 596 column_vector_string* col = new colu 597 m_cols.push_back(col); 598 } else if(user_cid==_cid_std_vector<std::str 599 std::vector<std::string>* user_var = 600 if(user_var) { 601 column_vector_string_ref* col = ne 602 m_cols.push_back(col); 603 } else { 604 column_vector_string* col = new column_v 605 m_cols.push_back(col); 606 } 607 } else if(user_cid==_cid(std::string() 608 std::string* user_var = (std::string 609 if(user_var) { 610 column_string_ref* col = new colum 611 m_cols.push_back(col); 612 } else { 613 column_string* col = new column_string(m 614 m_cols.push_back(col); 615 } 616 } else { 617 a_out << "tools::rroot::ntuple::init 618 << " for leaf with name " << s 619 << ", user variable type is no 620 << ". It's class id is " << us 621 << std::endl; 622 safe_clear<read::icol>(m_cols); 623 return false; 624 } 625 626 } else if(leaf_element* le = safe_cast<b 627 628 branch_element* be = safe_cast<branch, 629 if(!be) { 630 a_out << "tools::rroot::ntuple::init 631 safe_clear<read::icol>(m_cols); 632 return false; 633 } 634 635 #define TOOLS_RROOT_NTUPLE_CREATE_VEC_COL(a__n 636 if(be->class_name()==a__name) {\ 637 /*::printf("debug : ntuple : create 638 typedef a__type el_t;\ 639 std::vector<el_t>* user_var = a_bd.f 640 if(user_var) {\ 641 typedef column_element_ref< stl_ve 642 ce_t* col = new ce_t(m_tree.file() 643 m_cols.push_back(col);\ 644 } else {\ 645 typedef column_element< stl_vector 646 ce_t* col = new ce_t(m_tree.file() 647 m_cols.push_back(col);\ 648 }\ 649 } 650 651 TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 652 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 653 //else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 654 //else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 655 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 656 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 657 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 658 659 //else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 660 //else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 661 662 // WARNING : take care of the space in 663 /* VisualC++ : the below does not compile. 664 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 665 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 666 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 667 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 668 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 669 else TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 670 */ 671 672 else { 673 a_out << "tools::rroot::ntuple::init 674 << " WARNING : leaf element" 675 << " with name " << sout(bl->n 676 << ",title " << sout(bl->title 677 << " br_elem class name " << b 678 << " entries " << be->entry_nu 679 << std::endl; 680 } 681 682 } else { 683 a_out << "tools::rroot::ntuple::initia 684 << " WARNING : column type not y 685 << " with name " << sout(bl->nam 686 << " and title " << sout(bl->tit 687 << " s_cls() is " << sout(bl->s_ 688 << " Not fatal." 689 << std::endl; 690 } 691 692 } 693 694 #undef TOOLS_RROOT_NTUPLE_CREATE_VEC_COL 695 #undef TOOLS_RROOT_NTUPLE_CREATE_COL 696 697 size_t num = m_cols.size(); 698 if(!num) { 699 a_out << "tools::rroot::ntuple::initiali 700 << " zero columns." 701 << std::endl; 702 return false; 703 } 704 705 {tools_vforcit(column_binding,a_bd.columns( 706 if(!find_named<read::icol>(m_cols,(*it). 707 a_out << "tools::rroot::ntuple::initia 708 << " warning : for column bindin 709 << std::endl; 710 } 711 }} 712 713 //a_out << "tools::rroot::ntuple::initiali 714 // << " number of columns " << num << 715 // << std::endl; 716 717 return true; 718 } 719 720 bool get_row() const { 721 bool status = true; 722 tools_vforcit(read::icol*,m_cols,it) { 723 if(!(*it)->fetch_entry()) { 724 m_tree.out() << "tools::rroot::ntuple: 725 status = false; 726 } 727 } 728 return status; 729 } 730 protected: 731 tree& m_tree; 732 std::vector<read::icol*> m_cols; 733 int64 m_index; 734 }; 735 736 // for gopaw : 737 738 class fac_tree_holder { 739 public: 740 fac_tree_holder(ifac* a_fac,tree* a_tree):m_ 741 virtual ~fac_tree_holder() {delete m_tree;de 742 protected: 743 fac_tree_holder(const fac_tree_holder&){} 744 fac_tree_holder& operator=(const fac_tree_ho 745 protected: 746 ifac* m_fac; 747 tree* m_tree; 748 }; 749 750 class fac_tree_ntuple : public fac_tree_holder 751 typedef ntuple parent; 752 public: 753 static const std::string& s_class() { 754 static const std::string s_v("tools::rroot 755 return s_v; 756 } 757 virtual const std::string& s_cls() const {re 758 public: 759 fac_tree_ntuple(ifac* a_fac,tree* a_tree) // 760 :fac_tree_holder(a_fac,a_tree) 761 ,parent(*a_tree) //deleted first. 762 {} 763 virtual ~fac_tree_ntuple() {} 764 protected: 765 fac_tree_ntuple(const fac_tree_ntuple& a_fro 766 fac_tree_ntuple& operator=(const fac_tree_nt 767 }; 768 769 }} 770 771 #endif