Aleph-w  1.5a.2
Biblioteca general de algoritmos y estructuras de datos
 Todo Clases Archivos Funciones Variables 'typedefs' Enumeraciones Amigas Grupos Páginas
tpl_binNodeUtils.H
1 # ifndef TPL_BINNODEUTILS_H
2 # define TPL_BINNODEUTILS_H
3 
4 # include <ahFunction.H>
5 # include <tpl_arrayStack.H>
6 # include <tpl_arrayQueue.H>
7 # include <tpl_dynListQueue.H>
8 # include <bitArray.H>
9 # include <tpl_dynDlist.H>
10 # include <tpl_binNode.H>
11 
12 using namespace Aleph;
13 namespace Aleph {
14 
15  template <class Node> inline static
16 void __inorder_rec(Node * node, const int& level, int & position,
17  void (*visitFct)(Node *, int, int))
18 {
19  if (node == Node::NullPtr)
20  return;
21 
22  __inorder_rec((Node*) LLINK(node), level + 1, position, visitFct);
23 
24  (*visitFct)(node, level, position);
25  ++position;
26 
27  __inorder_rec((Node*) RLINK(node), level + 1, position, visitFct);
28 }
50  template <class Node> inline
51 int inOrderRec(Node * root, void (*visitFct)(Node*, int, int))
52 {
53  int position = 0;
54  __inorder_rec(root, 0, position, visitFct);
55  return position;
56 }
57  template <class Node> inline static
58 void __preorder_rec (Node * p, const int & level, int & position,
59  void (*visitFct)(Node*, int, int))
60 {
61  if (p == Node::NullPtr)
62  return;
63 
64  (*visitFct)(p, level, position);
65  ++position;
66 
67  __preorder_rec((Node*) LLINK(p), level + 1, position, visitFct);
68  __preorder_rec((Node*) RLINK(p), level + 1, position, visitFct);
69 }
92  template <class Node> inline
93 int preOrderRec(Node * root, void (*visitFct)(Node*, int, int))
94 {
95  int position = 0;
96  __preorder_rec(root, 0, position, visitFct);
97  return position;
98 }
99  template <class Node> inline static
100 void __postorder_rec(Node * node, const int & level, int & position,
101  void (*visitFct)(Node*, int, int))
102 {
103  if (node == Node::NullPtr)
104  return;
105 
106  __postorder_rec((Node*) LLINK(node), level + 1, position, visitFct);
107  __postorder_rec((Node*) RLINK(node), level + 1, position, visitFct);
108 
109  (*visitFct)(node, level, position);
110  ++position;
111 }
133  template <class Node> inline
134 int postOrderRec(Node * root, void (*visitFct)(Node*, int, int))
135 {
136  int position = 0;
137  __postorder_rec(root, 0, position, visitFct);
138  return position;
139 }
171  template <class Node, class Op>
173 {
174  static void for_each_inorder(Node * root, Op & op)
175  {
176  if (root == Node::NullPtr)
177  return;
178 
179  for_each_inorder((Node*) LLINK(root), op);
180  op(root);
181  for_each_inorder((Node*) RLINK(root), op);
182  }
183 
184 public:
185 
187  void operator () (Node * root, Op & op)
188  {
189  for_each_inorder(root, op);
190  }
191 
193  void operator () (Node * root, Op && op = Op())
194  {
195  for_each_inorder(root, op);
196  }
197 };
198 
204  template <class Node, class Operation> inline
205 bool traverse(Node * root, Operation & operation)
206 {
207  if (root == Node::NullPtr)
208  return true;
209 
210  return traverse<Node, Operation>((Node*) LLINK(root), operation) and
211  operation(root) and
212  traverse<Node, Operation>((Node*) RLINK(root), operation);
213 }
214 
215  template <class Node, class Operation> inline
216 bool traverse(Node * root, Operation && operation = Operation())
217 {
218  return traverse<Node, Operation>(root, operation);
219 }
220 
259  template <class Node, class Op>
261 {
262  bool to_leave;
263 
264  void inorder(Node * root, Op & op)
265  {
266  if (root == Node::NullPtr or to_leave)
267  return;
268 
269  for_each_inorder((Node*) LLINK(root), op);
270  to_leave = op(root);
271  for_each_inorder((Node*) RLINK(root), op);
272  }
273 
274 public:
275 
276  Goto_In_Order() : to_leave(false) { /* empty */ }
277 
278  void leave() { to_leave = true; }
279 
281  void operator () (Node * root, Op & op)
282  {
283  inorder(root, op);
284  }
285 
287  void operator () (Node * root, Op && op = Op()) const
288  {
289  inorder(root, op);
290  }
291 
292 };
324  template <class Node, class Op>
326 {
327  static void preorder(Node * root, Op & op)
328  {
329  if (root == Node::NullPtr)
330  return;
331 
332  op(root);
333  preorder((Node*) LLINK(root), op);
334  preorder((Node*) RLINK(root), op);
335  }
336 
337 public:
338 
340  void operator () (Node * root, Op & op)
341  {
342  preorder(root, op);
343  }
344 
346  void operator () (Node * root, Op && op = Op())
347  {
348  preorder(root, op);
349  }
350 };
351 
352 /*
353  template <class Node>
354 class For_Each_Preorder
355 {
356  static void preorder(Node * root, void (*op)(Node*))
357  {
358  if (root == Node::NullPtr)
359  return;
360 
361  op(root);
362  preorder((Node*) LLINK(root), op);
363  preorder((Node*) RLINK(root), op);
364  }
365 
366 public:
367 
368  void operator () (Node * root, void (*op)(Node*))
369  {
370  preorder(root, op);
371  }
372 };
373 */
374 
406  template <class Node, class Op>
408 {
409  static void postorder(Node * root, Op & op)
410  {
411  if (root == Node::NullPtr)
412  return;
413 
414  postorder((Node*) LLINK(root), op);
415  postorder((Node*) RLINK(root), op);
416  op(root);
417  }
418 
419 public:
421  void operator () (Node * root, Op & op)
422  {
423  postorder(root, op);
424  }
425 
427  void operator () (Node * root, Op && op = Op())
428  {
429  postorder(root, op);
430  }
431 };
432 
459  template <class Node> inline
460 size_t simple_preOrderStack(Node * node, void (*visitFct)(Node *, int, int))
461 {
462  if (node == Node::NullPtr)
463  return 0;
464 
465  ArrayStack<Node *> stack(Node::MaxHeight);
466  stack.push(node);
467 
468  Node * p;
469  size_t count = 0;
470  while (not stack.is_empty())
471  {
472  p = stack.pop();
473 
474  (*visitFct) (p, stack.size(), count++);
475 
476  if (RLINK(p) != Node::NullPtr)
477  stack.push(RLINK(p));
478 
479  if (LLINK(p) != Node::NullPtr)
480  stack.push(LLINK(p));
481  }
482  return count;
483 }
484 
511  template <class Node> inline
512 size_t preOrderStack(Node * node, void (*visitFct)(Node *, int, int))
513 {
514  if (node == Node::NullPtr)
515  return 0;
516 
517  ArrayStack<Node *> stack(Node::MaxHeight);
518  Node *p = node;
519  size_t count = 0;
520 
521  while (true)
522  {
523  (*visitFct)(p, stack.size(), count++);
524 
525  if (LLINK(p) != Node::NullPtr)
526  {
527  stack.push(p); // p y RLINK(p) faltan por visitarse
528  p = LLINK(p); // avanzar a la izquierda
529  continue; // ir a visitar raíz rama izquierda
530  }
531  while (true)
532  {
533  if (RLINK(p) != Node::NullPtr)
534  {
535  p = RLINK(p); // avanzar a la derecha
536  break; // ir a visitar raíz rama derecha
537  }
538  if (stack.is_empty())
539  return count; // fin
540 
541  p = stack.pop(); // sacar para ir a rama derecha
542  }
543  }
544 }
545 
571  template <class Node> inline
572 size_t inOrderStack(Node * node, void (*visitFct)(Node *, int, int))
573 {
574  if (node == Node::NullPtr)
575  return 0;
576 
577  ArrayStack<Node *> stack(Node::MaxHeight);
578  Node *p = node;
579  size_t count = 0;
580 
581  while (true)
582  {
583  if (LLINK(p) != Node::NullPtr)
584  {
585  stack.push(p); // p y RLINK(p) faltan por visitarse
586  p = LLINK(p); // avanzar a la izquierda
587  continue; // continuar bajando por la rama izquierda
588  }
589  while (true)
590  {
591  (*visitFct)(p, stack.size(), count++);
592 
593  if (RLINK(p) != Node::NullPtr)
594  {
595  p = RLINK(p); // avanzar a la derecha
596  break; // ir a visitar raíz rama derecha
597  }
598  if (stack.is_empty())
599  return count;
600 
601  p = stack.pop(); // sacar para ir a rama derecha
602  }
603  }
604 }
605 
631  template <class Node> inline
632 size_t postOrderStack(Node * root, void (*visitFct)(Node *, int, int))
633 {
634  if (root == Node::NullPtr)
635  return 0;
636 
637  typedef std::pair<Node*, char> Postorder_Pair;
638  ArrayStack<Postorder_Pair> stack(Node::MaxHeight);
639 
640  Postorder_Pair __pair;
641  Node *& p = __pair.first = root;
642  char & side = __pair.second = 'i';
643  stack.push(__pair);
644  size_t count = 0;
645 
646  while (not stack.is_empty())
647  {
648  __pair = stack.pop();
649  switch (side)
650  {
651  case 'i':
652  if (LLINK(p) != Node::NullPtr)
653  stack.push(Postorder_Pair(LLINK(p), 'i'));
654 
655  stack.push(Postorder_Pair(p, 'l'));
656  break;
657 
658  case 'l':
659  if (RLINK(p) != Node::NullPtr)
660  stack.push(Postorder_Pair(RLINK(p), 'i'));
661 
662  stack.push(Postorder_Pair(p, 'r'));
663  break;
664 
665  case 'r':
666  (*visitFct) (p, stack.size(), count++);
667  break;
668  }
669  }
670 
671  return count;
672 }
673 
674 template <class Node>
675 static void prefix(Node * root, DynList<Node*> & acc)
676 {
677  if (root == Node::NullPtr)
678  return;
679 
680  acc.append(root);
681  prefix((Node*) LLINK(root), acc);
682  prefix((Node*) RLINK(root), acc);
683 }
684 
685 template <class Node>
686 static void infix(Node * root, DynList<Node*> & acc)
687 {
688  if (root == Node::NullPtr)
689  return;
690 
691  infix((Node*) LLINK(root), acc);
692  acc.append(root);
693  infix((Node*) RLINK(root), acc);
694 }
695 
696 template <class Node>
697 static void suffix(Node * root, DynList<Node*> & acc)
698 {
699  if (root == Node::NullPtr)
700  return;
701 
702  sufffix((Node*) LLINK(root), acc);
703  siffix((Node*) RLINK(root), acc);
704  acc.append(root);
705 }
706 
713 template <class Node>
714 DynList<Node*> prefix(Node * root)
715 {
716  DynList<Node*> ret_val;
717  prefix(root, ret_val);
718  return ret_val;
719 }
720 
727 template <class Node>
728 DynList<Node*> infix(Node * root)
729 {
730  DynList<Node*> ret_val;
731  infix(root, ret_val);
732  return ret_val;
733 }
734 
741 template <class Node>
742 DynList<Node*> suffix(Node * root)
743 {
744  DynList<Node*> ret_val;
745  suffix(root, ret_val);
746  return ret_val;
747 }
748 
749 
759  template <class Node> inline
760 size_t compute_cardinality_rec(Node * node)
761 {
762  if (node == Node::NullPtr)
763  return 0;
764 
765  return (compute_cardinality_rec(LLINK(node)) + 1 +
767 }
768 
778 template <class Node> inline size_t computeHeightRec(Node * node)
779 {
780  if (node == Node::NullPtr)
781  return 0;
782 
783  const size_t left_height = computeHeightRec(LLINK(node));
784  const size_t right_height = computeHeightRec(RLINK(node));
785 
786  return 1 + std::max(left_height, right_height);
787 }
788 
797  template <class Node> inline
798 void destroyRec(Node *& root)
799 {
800  if (root == Node::NullPtr)
801  return;
802 
803  destroyRec((Node*&) LLINK(root));
804  destroyRec((Node*&) RLINK(root));
805  delete root;
806 
807  root = (Node*) Node::NullPtr;
808 }
809 
820  template <class Node> inline
821 Node * copyRec(Node * src_root)
822  throw(std::exception, std::bad_alloc)
823 {
824  if (src_root == Node::NullPtr)
825  return (Node*) Node::NullPtr;
826 
827  Node * tgt_root = new Node(*src_root);
828 
829  try
830  {
831  LLINK(tgt_root) = copyRec<Node>((Node*) LLINK(src_root));
832  RLINK(tgt_root) = copyRec<Node>((Node*) RLINK(src_root));
833 
834  }
835  catch (...)
836  {
837  I(RLINK(tgt_root) == Node::NullPtr);
838 
839  if (LLINK(tgt_root) != Node::NullPtr)
840  destroyRec((Node*&) LLINK(tgt_root)); // TODO: diff de Node*&
841 
842  delete tgt_root;
843 
844  throw;
845  }
846 
847  return tgt_root;
848 }
849 
860  template <class Node> inline
861 bool areSimilar(Node * t1, Node * t2)
862 {
863  if (t1 == Node::NullPtr and t2 == Node::NullPtr)
864  return true;
865 
866  if (t1 == Node::NullPtr or t2 == Node::NullPtr)
867  return false;
868 
869  return (areSimilar(LLINK(t1), LLINK(t2)) and
870  areSimilar(RLINK(t1), RLINK(t2)));
871 }
872 
891  template <class Node, class Equal> inline
892 bool areEquivalents(Node * t1, Node * t2)
893 {
894  if (t1 == Node::NullPtr and t2 == Node::NullPtr)
895  return true;
896 
897  if (t1 == Node::NullPtr or t2 == Node::NullPtr)
898  return false;
899 
900  if (not Equal () (KEY(t1), KEY(t2)))
901  return false;
902 
903  return (areEquivalents<Node, Equal>(LLINK(t1), LLINK(t2)) and
904  areEquivalents<Node, Equal>(RLINK(t1), RLINK(t2)));
905 }
906  template <class Node> inline
907 bool areEquivalents(Node * t1, Node * t2)
908 {
909  return areEquivalents<Node, Aleph::equal_to<typename Node::key_type> >(t1, t2);
910 }
911 
942  template <class Node> inline
943 void levelOrder(Node * root,
944  void (*visitFct)(Node*, int, bool), size_t queue_size)
945 {
946 
947  if (root == Node::NullPtr)
948  return;
949 
950  const size_t two_power =
951  (size_t) (std::log((float)queue_size)/std::log(2.0) + 1);
953  queue.put(std::pair<Node*, bool>(root, bool()));
954 
955  for (int pos = 0; not queue.is_empty(); pos++)
956  {
957  std::pair<Node*, bool> pr = queue.get();
958  Node *& p = pr.first;
959 
960  (*visitFct) (p, pos, pr.second);
961 
962  if (LLINK(p) != Node::NullPtr)
963  queue.put(std::pair <Node*, bool> (LLINK(p), true));
964 
965  if (RLINK(p) != Node::NullPtr)
966  queue.put(std::pair <Node*, bool> (RLINK(p), false));
967  }
968 }
969 
970 
991  template <class Node, class Operation> inline
992 bool level_traverse(Node * root, Operation & operation)
993 {
994  if (root == Node::NullPtr)
995  return true;
996 
998  queue.put(root);
999 
1000  while (not queue.is_empty())
1001  {
1002  Node * p = queue.get();
1003 
1004  if (not operation(p))
1005  return false;
1006 
1007  if (LLINK(p) != Node::NullPtr)
1008  queue.put((Node*) LLINK(p));
1009 
1010  if (RLINK(p) != Node::NullPtr)
1011  queue.put((Node*) RLINK(p));
1012  }
1013  return true;
1014 }
1015 
1016  template <class Node, class Operation> inline
1017 bool level_traverse(Node * root, Operation && operation = Operation())
1018 {
1019  return level_traverse<Node, Operation>(root, operation);
1020 }
1021 
1044  template <template <class> class Node, typename Key> inline
1045 Node<Key> * build_tree(DynArray<Key> & preorder,
1046  const int & l_p, const int & r_p,
1047  DynArray<Key> & inorder,
1048  const int & l_i, const int & r_i)
1049 {
1050  if (l_p > r_p) // ¿está vacío el recorrido?
1051  { // sí, retornar árbol vacío
1052  I(l_i > r_i);
1053  return Node <Key> ::NullPtr;
1054  }
1055 
1056  I(r_p - l_p == r_i - l_i);
1057 
1058  Node<Key> * root = new Node <Key> (preorder[l_p]); // crear la raíz
1059  if (r_p == l_p)
1060  return root; // recorrido de longitud 1
1061 
1062  I(l_i <= r_i);
1063 
1064  int i = 0;
1065  for (int j = l_i; j <= r_i; ++j)
1066  if (inorder[j] == preorder[l_p])
1067  {
1068  i = j - l_i;
1069  break;
1070  }
1071 
1072  I(i <= r_i);
1073 
1074  LLINK(root) = build_tree <Node, Key> (preorder, l_p + 1, l_p + i,
1075  inorder, l_i, l_i + (i - 1));
1076  RLINK(root) = build_tree <Node, Key> (preorder, l_p + i + 1, r_p,
1077  inorder, l_i + i + 1, r_i);
1078  return root;
1079 }
1080 
1081  template <class Node> inline static void
1082 __compute_nodes_in_level(Node * root, const int & level,
1083  const int & current_level,
1084  DynDlist<Node*> & level_list)
1085 {
1086  if (root == Node::NullPtr)
1087  return;
1088  if (current_level == level)
1089  {
1090  level_list.append(root);
1091  return; // no vale la pena descender más
1092  }
1093  __compute_nodes_in_level(LLINK(root), level, current_level + 1, level_list);
1094  __compute_nodes_in_level(RLINK(root), level, current_level + 1, level_list);
1095 }
1096 
1110  template <class Node> inline
1111 void compute_nodes_in_level(Node * root, const int & level,
1113 {
1114  __compute_nodes_in_level(root, level, 0, list);
1115 }
1116 
1142  template <class Node> inline
1143 void inOrderThreaded(Node * root, void (*visitFct)(Node*))
1144 {
1145  if (root == Node::NullPtr)
1146  return;
1147 
1148  Node *p = root, *r = Node::NullPtr, *q;
1149  while (p != Node::NullPtr)
1150  {
1151  q = LLINK(p);
1152  if (q == Node::NullPtr)
1153  { // No hay rama izq ==> visitar p
1154  (*visitFct)(p);
1155  r = p;
1156  p = RLINK(p);
1157  continue;
1158  }
1159 
1160  // avanzar hacia el nodo más a la derecha de la rama izquierda
1161  while (q != r and RLINK(q) != Node::NullPtr)
1162  q = RLINK(q);
1163 
1164  if (q != r) // tiene p un predecesor?
1165  { // si ==> dejar un hilo para luego subir a visitar p
1166  RLINK(q) = p; // Aquí se coloca el hilo
1167  p = LLINK(p); // Seguir bajando por la izquierda
1168  continue;
1169  }
1170 
1171  (*visitFct)(p);
1172 
1173  RLINK (q) = Node::NullPtr; // Borrar hilo
1174  r = p;
1175  p = RLINK(p); // avanzar a la rama derecha
1176  }
1177 }
1178 
1204  template <class Node> inline
1205 void preOrderThreaded(Node * node, void (*visitFct)(Node*))
1206 {
1207  if (node == Node::NullPtr)
1208  return;
1209 
1210  Node * p = node, * r = Node::NullPtr, *q;
1211  while (p != Node::NullPtr)
1212  {
1213  q = LLINK(p);
1214 
1215  if (q == Node::NullPtr)
1216  {
1217  (*visitFct)(p);
1218  r = p;
1219  p = RLINK(p);
1220  continue;
1221  }
1222 
1223  // avanzar hacia el nodo más a la derecha de la rama izquierda
1224  while (q != r and RLINK(q) != Node::NullPtr)
1225  q = RLINK(q);
1226 
1227  if (q != r)
1228  {
1229  RLINK(q) = p;
1230  (*visitFct)(p);
1231  p = LLINK(p);
1232  continue;
1233  }
1234 
1235  RLINK(q) = Node::NullPtr; /* delete thread */
1236  r = p;
1237  p = RLINK(p); /* advance to right branch */
1238  }
1239 }
1240 
1241  template <class Node> inline static
1242 size_t __internal_path_length(Node * p, const size_t & level)
1243 {
1244  if (p == Node::NullPtr)
1245  return 0;
1246 
1247  return level + __internal_path_length(LLINK(p), level + 1) +
1248  __internal_path_length(RLINK(p), level + 1);
1249 }
1250 
1258  template <class Node> inline
1259 size_t internal_path_length(Node * p)
1260 {
1261  return __internal_path_length(p, 0);
1262 }
1263 
1283  template <class Node> inline
1284 void tree_to_bits(Node * root, BitArray & array)
1285 {
1286  if (root == Node::NullPtr)
1287  {
1288  array.push(1);
1289  return;
1290  }
1291 
1292  array.push(0);
1293  tree_to_bits((Node*) LLINK(root), array);
1294  tree_to_bits((Node*) RLINK(root), array);
1295 }
1296 
1313 template <class Node> inline
1315 {
1316  BitArray ret_val;
1317  tree_to_bits(root, ret_val);
1318  return ret_val;
1319 }
1320 
1321  template <class Node> static inline
1322 Node * __bits_to_tree(BitArray & array, int & i)
1323 {
1324  int bit = array.read_bit(i++);
1325  if (bit == 1) // ¿Es un nodo externo?
1326  return Node::NullPtr; // sí
1327 
1328  Node * p = new Node; // crear nodo interno actual
1329  LLINK(p) = (Node*) __bits_to_tree<Node>(array, i); // subárbol izq.
1330  RLINK(p) = (Node*) __bits_to_tree<Node>(array, i); // subárbol der.
1331 
1332  return p;
1333 }
1334 
1356 template <class Node> inline Node * bits_to_tree(BitArray & array, int idx = 0)
1357 {
1358  return __bits_to_tree <Node> (array, idx);
1359 }
1360 
1376  template <class Node, class Get_Key> inline
1377 void save_tree_keys_in_prefix(Node * root, ofstream & output)
1378 {
1379  if (root == Node::NullPtr)
1380  return;
1381 
1382  output << Get_Key () (root) << " ";
1383 
1384  save_tree_keys_in_prefix<Node,Get_Key>((Node*)LLINK(root), output);
1385  save_tree_keys_in_prefix<Node,Get_Key>((Node*)RLINK(root), output);
1386 }
1387 
1408  template <class Node, class Load_Key> inline
1409 void load_tree_keys_in_prefix(Node * root, ifstream & input)
1410 {
1411  if (root == Node::NullPtr)
1412  return;
1413 
1414  Load_Key () (root, input);
1415 
1416  load_tree_keys_in_prefix<Node,Load_Key>((Node*)LLINK(root), input);
1417  load_tree_keys_in_prefix<Node,Load_Key>((Node*)RLINK(root), input);
1418 }
1419 
1445  template <class Node, class Get_Key> inline
1446 void save_tree(Node * root, ofstream & output)
1447 {
1448  BitArray prefix;
1449  tree_to_bits(root, prefix);
1450  prefix.save(output);
1451  save_tree_keys_in_prefix <Node, Get_Key> (root, output);
1452 }
1453 
1469  template <class Node, class Load_Key> inline
1470 Node * load_tree(ifstream & input)
1471 {
1472  BitArray prefix;
1473  prefix.load(input);
1474  Node * root = bits_to_tree <Node> (prefix);
1475  load_tree_keys_in_prefix <Node, Load_Key> (root, input);
1476  return root;
1477 }
1478 
1479 
1480  template <class Node, class Get_Key> inline
1481 void put_tree_keys_in_array(Node * root, ofstream & out)
1482 {
1483  if (root == Node::NullPtr)
1484  return;
1485 
1486  const string str = Get_Key () (root);
1487 
1488  if (str == "\t")
1489  out << "\"\t\"";
1490  else if (str == "\n")
1491  out << "\"\\n\"";
1492  else
1493  out << "\"" << str << "\"";
1494  out << ", ";
1495 
1496  put_tree_keys_in_array <Node, Get_Key> ((Node *) LLINK(root), out);
1497  put_tree_keys_in_array <Node, Get_Key> ((Node *) RLINK(root), out);
1498 }
1499 
1500 
1501  template <class Node, class Load_Key> inline
1502 void load_tree_keys_from_array(Node * root, const char * keys[], int & idx)
1503 {
1504  if (root == Node::NullPtr)
1505  return;
1506 
1507  if (Load_Key()(root, keys[idx]))
1508  ++idx;
1509 
1510  load_tree_keys_from_array <Node, Load_Key> ((Node *) LLINK(root), keys, idx);
1511  load_tree_keys_from_array <Node, Load_Key> ((Node *) RLINK(root), keys, idx);
1512 }
1513 
1558  template <class Node, class Get_Key> inline
1560  const string & array_name,
1561  ofstream & output)
1562 {
1563  BitArray prefix;
1564  tree_to_bits(root, prefix);
1565  prefix.save_in_array_of_chars(array_name + "_cdp", output);
1566  output << "const char * " << array_name << "_k[] = { " << endl;
1567  put_tree_keys_in_array <Node, Get_Key> (root, output);
1568  output << "NULL };" << endl;
1569 }
1570 
1571 
1619  template <class Node, class Load_Key> inline
1620 Node * load_tree_from_array(const unsigned char bits[],
1621  const size_t & num_bits,
1622  const char * keys[])
1623 {
1624  BitArray prefix;
1625  prefix.load_from_array_of_chars(bits, num_bits);
1626  Node * root = bits_to_tree <Node> (prefix);
1627  int i = 0;
1628  load_tree_keys_from_array <Node, Load_Key> (root, keys, i);
1629  return root;
1630 }
1631 
1632 
1645  template <class Node,
1646  class Compare = Aleph::less<typename Node::key_type> > inline
1648 {
1649  typedef typename Node::key_type Key_Type;
1650 
1651  if (p == Node::NullPtr)
1652  return true;
1653 
1654  if (LLINK(p) != Node::NullPtr)
1655  {
1656  if (less_or_equal_than<Key_Type, Compare> (KEY(LLINK(p)), KEY(p)))
1657  return check_binary_search_tree<Node, Compare>(LLINK(p));
1658  else
1659  return false;
1660  }
1661 
1662  if (RLINK(p) != Node::NullPtr)
1663  {
1664  if (less_or_equal_than<Key_Type, Compare> (KEY(p), KEY(RLINK(p))))
1665  return check_binary_search_tree<Node, Compare>(RLINK(p));
1666  else
1667  return false;
1668  }
1669  return true;
1670 }
1671 
1686  template <class Node> inline Node *
1688  const int & l, const int & r)
1689 {
1690  if (l > r)
1691  return Node::NullPtr;
1692 
1693  Node * root = new Node(preorder[l]);
1694 
1695  if (l == r)
1696  return root;
1697 
1698  int first_greater = l + 1;
1699  while ((first_greater <= r) and (preorder[first_greater] < preorder[l]))
1700  ++first_greater;
1701 
1702  LLINK(root) =
1703  preorder_to_binary_search_tree<Node>(preorder, l + 1, first_greater - 1);
1704  RLINK(root) =
1705  preorder_to_binary_search_tree<Node>(preorder, first_greater, r);
1706 
1707  return root;
1708 }
1709 
1725  template <class Node,
1726  class Compare = Aleph::less<typename Node::key_type>>
1727  inline
1728 Node * searchInBinTree(Node * root,
1729  const typename Node::key_type & key,
1730  Compare & cmp)
1731 {
1732  while (root != Node::NullPtr)
1733  if (cmp(key, KEY(root))) // ¿en rama izquierda?
1734  root = (Node*) LLINK(root); // baje a la izquierda
1735  else if(cmp (KEY(root), key)) // ¿en rama derecha?
1736  root = (Node*) RLINK(root); // baje a la derecha
1737  else
1738  break; // se encontró!
1739 
1740  return root;
1741 }
1742 
1743  template <class Node,
1744  class Compare = Aleph::less<typename Node::key_type> > inline
1745 Node * searchInBinTree(Node * root,
1746  const typename Node::key_type & key,
1747  Compare && cmp = Compare())
1748 {
1749  return searchInBinTree <Node, Compare> (root, key, cmp);
1750 }
1751 
1763  template <class Node> inline
1764 Node * find_min(Node * root)
1765 {
1766  while (LLINK(root) != Node::NullPtr)
1767  root = static_cast<Node*>(LLINK(root));
1768 
1769  return root;
1770 }
1771 
1783  template <class Node> inline
1784 Node * find_max(Node * root)
1785 {
1786  while (RLINK(root) != Node::NullPtr)
1787  root = static_cast<Node*>(RLINK(root));
1788 
1789  return root;
1790 }
1803  template <class Node> inline
1804 Node * find_successor(Node * p, Node *& pp)
1805 {
1806  I(p != Node::NullPtr);
1807  I(RLINK(p) != Node::NullPtr);
1808 
1809  pp = p;
1810  p = (Node*) RLINK(p);
1811  while (LLINK(p) != Node::NullPtr)
1812  {
1813  pp = p;
1814  p = (Node*) LLINK(p);
1815  }
1816 
1817  return p;
1818 }
1819 
1832  template <class Node> inline
1833 Node* find_predecessor(Node * p, Node *& pp)
1834 {
1835  I(p != Node::NullPtr);
1836  I(LLINK(pp) != Node::NullPtr);
1837 
1838  pp = p;
1839  p = static_cast<Node*>(LLINK(p));
1840 
1841  while (RLINK(p) != Node::NullPtr)
1842  {
1843  pp = p;
1844  p = static_cast<Node*>(RLINK(p));
1845  }
1846 
1847  return p;
1848 }
1849 
1871  template <class Node,
1872  class Compare = Aleph::less<typename Node::key_type> > inline
1873 Node * search_parent(Node * root, const typename Node::key_type & key,
1874  Node *& parent, Compare && cmp = Compare())
1875 {
1876  I((LLINK(parent) == root) or (RLINK(parent) == root));
1877  I(root != Node::NullPtr);
1878 
1879  while (true)
1880  if (cmp(key, KEY(root)))
1881  {
1882  if (LLINK(root) == Node::NullPtr)
1883  return root;
1884 
1885  parent = root;
1886  root = static_cast<Node*>(LLINK(root));
1887  }
1888  else if (cmp(KEY(root), key))
1889  {
1890  if (RLINK(root) == Node::NullPtr)
1891  return root;
1892 
1893  parent = root;
1894  root = static_cast<Node*>(RLINK(root));
1895  }
1896  else
1897  return root;
1898 }
1899 
1918  template <class Node,
1919  class Compare = Aleph::less<typename Node::key_type> >
1920  inline Node *
1921 search_rank_parent(Node * root,
1922  const typename Node::key_type & key,
1923  Compare && cmp = Compare())
1924 {
1925  I(root != Node::NullPtr);
1926 
1927  while (true)
1928  if (cmp(key, KEY(root)))
1929  {
1930  if (LLINK(root) == Node::NullPtr)
1931  return root;
1932 
1933  root = static_cast<Node*>(LLINK(root));
1934  }
1935  else if (cmp(KEY(root), key))
1936  {
1937  if (RLINK(root) == Node::NullPtr)
1938  return root;
1939 
1940  root = static_cast<Node*>(RLINK(root));
1941  }
1942  else
1943  return root;
1944 }
1945 
1961  template <class Node,
1962  class Compare = Aleph::less<typename Node::key_type> > inline
1963 Node * insert_in_binary_search_tree(Node *& root, Node * p)
1964 {
1965  if (root == Node::NullPtr)
1966  return root = p;
1967 
1968  if (Compare () (KEY(p), KEY(root))) // ¿p < root?
1969  return insert_in_binary_search_tree<Node,Compare>((Node*&) LLINK(root), p);
1970  else if (Compare () (KEY(root), KEY(p))) // ¿p > root?
1971  return insert_in_binary_search_tree<Node,Compare>((Node*&) RLINK(root), p);
1972 
1973  return Node::NullPtr; // clave repetida ==> no hay inserción
1974 }
1975 
1976 # define INSERT_DUP insert_dup_in_binary_search_tree<Node,Compare>
1977 
1995  template <class Node,
1996  class Compare = Aleph::less<typename Node::key_type> > inline
1997 Node * insert_dup_in_binary_search_tree(Node *& root, Node * p)
1998 {
1999  if (root == Node::NullPtr)
2000  return root = p;
2001 
2002  if (Compare () (KEY(p), KEY(root))) // ¿p < root?
2003  return INSERT_DUP ((Node*&) LLINK(root), p);
2004 
2005  return INSERT_DUP((Node*&) RLINK(root), p);
2006 }
2007 # undef INSERT_DUP
2008 
2027  template <class Node,
2028  class Compare = Aleph::less<typename Node::key_type> > inline
2029 Node * search_or_insert_in_binary_search_tree(Node *& r, Node * p)
2030 {
2031  if (r == Node::NullPtr)
2032  return r = p;
2033 
2034  if (Compare () (KEY(p), KEY(r))) // ¿p < root?
2035  return
2036  search_or_insert_in_binary_search_tree<Node,Compare>((Node*&)LLINK(r), p);
2037  else if (Compare () (KEY(r), KEY(p))) // ¿p > root?
2038  return
2039  search_or_insert_in_binary_search_tree<Node,Compare>((Node*&)RLINK(r), p);
2040 
2041  return r;
2042 }
2043 
2044 # define SPLIT split_key_rec<Node, Compare>
2045 
2065  template <class Node,
2066  class Compare = Aleph::less<typename Node::key_type> > inline
2067 bool split_key_rec(Node * root, const typename Node::key_type & key,
2068  Node *& ts, Node *& tg)
2069 {
2070  if (root == Node::NullPtr)
2071  { // key no se encuentra en árbol ==> split tendrá éxito
2072  ts = tg = Node::NullPtr;
2073  return true;
2074  }
2075 
2076  if ( Compare() (key, KEY(root)) ) // ¿key < KEY(root)?
2077  if (SPLIT((Node*&) LLINK(root), key, ts, (Node*&) LLINK(root)))
2078  {
2079  tg = root;
2080  return true;
2081  }
2082  else
2083  return false;
2084 
2085  if (Compare() (KEY(root), key)) // ¿key > KEY(root)?
2086  if (SPLIT((Node*&) RLINK(root), key, (Node*&) RLINK(root), tg))
2087  {
2088  ts = root;
2089  return true;
2090  }
2091  else
2092  return false;
2093 
2094  return false; // clave existe en árbol ==> se deja intacto
2095 }
2096 
2097 # undef SPLIT
2098 
2099 # define SPLIT split_key_dup_rec<Node, Compare>
2100 
2119  template <class Node,
2120  class Compare = Aleph::less<typename Node::key_type> > inline
2121 void split_key_dup_rec(Node * root, const typename Node::key_type & key,
2122  Node *& ts, Node *& tg)
2123 {
2124  if (root == Node::NullPtr)
2125  { // key no se encuentra en árbol ==> split tendrá éxito
2126  ts = tg = Node::NullPtr;
2127  return;
2128  }
2129 
2130  if (Compare() (key, KEY(root))) // ¿key < KEY(root)?
2131  SPLIT((Node*&) LLINK(root), key, ts, (Node*&) LLINK(root));
2132  else if (Compare () (KEY(root), key)) // ¿key > KEY(root)?
2133  SPLIT((Node*&) RLINK(root), key, (Node*&) RLINK(root), tg);
2134  else // key == KEY(root)
2135  SPLIT((Node*&) LLINK(root), key, ts, (Node*&) LLINK(root));
2136 }
2137 
2138 # undef SPLIT
2139 
2155 template <class Node> inline Node * join_exclusive(Node *& ts, Node *& tg)
2156 {
2157  if (ts == Node::NullPtr)
2158  return tg;
2159 
2160  if (tg == Node::NullPtr)
2161  return ts;
2162 
2163  LLINK(tg) = join_exclusive(RLINK(ts), LLINK(tg));
2164 
2165  RLINK(ts) = tg;
2166  Node * ret_val = ts;
2167  ts = tg = Node::NullPtr; // deben quedar vacíos después del join
2168 
2169  return ret_val;
2170 }
2171 
2172 # define REMOVE remove_from_search_binary_tree<Node, Compare>
2173 
2191  template <class Node,
2192  class Compare = Aleph::less<typename Node::key_type> > inline
2193 Node * remove_from_search_binary_tree(Node *& root,
2194  const typename Node::key_type & key)
2195 {
2196  if (root == Node::NullPtr)
2197  return Node::NullPtr;
2198 
2199  if (Compare () (key, KEY(root))) // ¿key < KEY(root)?
2200  return REMOVE((Node*&) LLINK(root), key);
2201  else if (Compare () (KEY(root), key)) // ¿key > KEY(root)?
2202  return REMOVE((Node*&) RLINK(root), key);
2203 
2204  Node * ret_val = root; // respaldar root que se va a borrar
2205  root = join_exclusive((Node*&) LLINK(root), (Node*&) RLINK(root));
2206 
2207  ret_val->reset();
2208 
2209  return ret_val;
2210 }
2211 
2212 # undef REMOVE
2213 
2234  template <class Node,
2235  class Compare = Aleph::less<typename Node::key_type> > inline
2236 Node * insert_root(Node *& root, Node * p)
2237 {
2238  Node * l = Node::NullPtr, * r = Node::NullPtr;
2239 
2240  if (not split_key_rec<Node, Compare>(root, KEY(p), l, r))
2241  return Node::NullPtr;
2242 
2243  LLINK(p) = l;
2244  RLINK(p) = r;
2245  root = p;
2246 
2247  return root;
2248 }
2249 
2272  template <class Node,
2273  class Compare = Aleph::less<typename Node::key_type> > inline
2274 Node * insert_dup_root(Node *& root, Node * p)
2275 {
2276  split_key_dup_rec<Node, Compare>(root, KEY(p), LLINK(p), RLINK(p));
2277  return root = p;
2278 }
2279 
2298  template <class Node,
2299  class Compare = Aleph::less<typename Node::key_type> > inline
2300 Node * join_preorder(Node * t1, Node * t2, Node *& dup)
2301 {
2302  if (t2 == Node::NullPtr)
2303  return t1;
2304 
2305  Node * l = (Node*) LLINK(t2); // respaldos de ramas de t2
2306  Node * r = (Node*) RLINK(t2);
2307 
2308  if (insert_in_binary_search_tree <Node, Compare> (t1, t2) == Node::NullPtr)
2309  // inserción fallida ==> elemento duplicado ==> insertar en dup
2310  insert_in_binary_search_tree<Node, Compare>(dup, t2);
2311 
2312  join_preorder(t1, l, dup);
2313  join_preorder(t1, r, dup);
2314 
2315  return t1;
2316 }
2317 
2335  template <class Node,
2336  class Compare = Aleph::less<typename Node::key_type> > inline
2337 Node * join(Node * t1, Node * t2, Node *& dup)
2338 {
2339  if (t1 == Node::NullPtr)
2340  return t2;
2341 
2342  if (t2 == Node::NullPtr)
2343  return t1;
2344 
2345  Node * l = (Node*) LLINK(t1); // respaldos ramas de t1
2346  Node * r = (Node*) RLINK(t1);
2347 
2348  t1->reset();
2349 
2350  // mientras la clave raíz de t1 esté contenida en t2
2351  while (t1 != Node::NullPtr and
2352  insert_root<Node, Compare>(t2, t1) == Node::NullPtr)
2353  { // sí ==> sáquelo de t1 e insértelo en dup
2354  Node * p = remove_from_search_binary_tree(t1, KEY(t1));
2355 
2356  l = (Node*) LLINK(t1);
2357  r = (Node*) RLINK(t1);
2358 
2359  I(p != Node::NullPtr);
2360 
2361  insert_in_binary_search_tree<Node, Compare>(dup, p);
2362  }
2363 
2364  LLINK(t2) = join<Node, Compare>(l, (Node*) LLINK(t2), dup);
2365  RLINK(t2) = join<Node, Compare>(r, (Node*) RLINK(t2), dup);
2366 
2367  return t2;
2368 }
2369 
2374  template <class Node> inline
2375 Node * rotate_to_right(Node * p)
2376 {
2377  I(p != Node::NullPtr);
2378 
2379  Node * q = static_cast<Node*>(LLINK(p));
2380  LLINK(p) = RLINK(q);
2381  RLINK(q) = p;
2382 
2383  return q;
2384 }
2385 
2398  template <class Node> inline
2399 Node * rotate_to_right(Node * p, Node * pp)
2400 {
2401  I(p != Node::NullPtr);
2402  I(pp != Node::NullPtr);
2403  I( ((Node*) LLINK(pp)) == p or ((Node*) RLINK(pp)) == p);
2404 
2405  Node *q = static_cast<Node*>(LLINK(p));
2406  LLINK(p) = RLINK(q);
2407  RLINK(q) = p;
2408 
2409  if (static_cast<Node*>(LLINK(pp)) == p) // actualización del padre
2410  LLINK(pp) = q;
2411  else
2412  RLINK(pp) = q;
2413 
2414  return q;
2415 }
2416 
2421  template <class Node> inline
2422 Node* rotate_to_left(Node * p)
2423 {
2424  I(p != Node::NullPtr);
2425 
2426  Node *q = static_cast<Node*>(RLINK(p));
2427  RLINK(p) = LLINK(q);
2428  LLINK(q) = p;
2429 
2430  return q;
2431 }
2432 
2447  template <class Node> inline
2448 Node* rotate_to_left(Node * p, Node * pp)
2449 {
2450  I(p != Node::NullPtr);
2451  I(pp != Node::NullPtr);
2452  I(static_cast<Node*>(LLINK(pp)) == p or static_cast<Node*>(RLINK(pp)) == p);
2453 
2454  Node *q = static_cast<Node*>(RLINK(p));
2455  RLINK(p) = LLINK(q);
2456  LLINK(q) = p;
2457 
2458  // actualización del padre
2459  if (LLINK(pp) == p)
2460  LLINK(pp) = q;
2461  else
2462  RLINK(pp) = q;
2463 
2464  return q;
2465 }
2466 
2492  template <class Node, class Key,
2493  class Compare = Aleph::less<typename Node::key_type> > inline
2494 void split_key(Node * root, const Key & key, Node *& l, Node *& r)
2495 {
2496  if (root == Node::NullPtr)
2497  {
2498  l = r = (Node*) Node::NullPtr;
2499  return;
2500  }
2501 
2502  Node * current;
2503  Node ** current_parent = NULL;
2504  Node ** pending_child = NULL;
2505  char current_is_right;
2506  Compare cmp;
2507 
2508  if (cmp (key, KEY(root)))
2509  {
2510  r = root;
2511  pending_child = &l;
2512  current_is_right = true;
2513  }
2514  else
2515  {
2516  l = root;
2517  pending_child = &r;
2518  current_is_right = false;
2519  }
2520 
2521  current = root;
2522 
2523  while (current != Node::NullPtr)
2524  {
2525  if (cmp (key, KEY(current)))
2526  { /* current must be in right side */
2527  if (not current_is_right)
2528  {
2529  current_is_right = not current_is_right;
2530  *pending_child = *current_parent; /* change of side */
2531  pending_child = current_parent;
2532  }
2533 
2534  current_parent = static_cast<Node**>(&LLINK(current));
2535  }
2536  else
2537  { /* current must be in left side */
2538  if (current_is_right)
2539  {
2540  current_is_right = not current_is_right;
2541  *pending_child = *current_parent; /* change of side */
2542  pending_child = current_parent;
2543  }
2544  current_parent = static_cast<Node**>(&RLINK(current));
2545  }
2546 
2547  current = *current_parent;
2548  }
2549 
2550  *pending_child = static_cast<Node*>(Node::NullPtr);
2551 }
2552 
2570  template <class Node> inline
2571 void swap_node_with_successor(Node * p, // Node for swapping
2572  Node *& pp, // parent of p
2573  Node * q, // Successor inorder of p
2574  Node *& pq) // parent of q
2575 {
2576  I(p != Node::NullPtr and q != Node::NullPtr and
2577  pp != Node::NullPtr and pq != Node::NullPtr);
2578  I(LLINK(pp) == p or RLINK(pp) == p);
2579  I(LLINK(pq) == q or RLINK(pq) == q);
2580  I(LLINK(q) == Node::NullPtr);
2581 
2582  /* Set of pp to its new son q */
2583  if (LLINK(pp) == p)
2584  LLINK(pp) = q;
2585  else
2586  RLINK(pp) = q;
2587 
2588  LLINK(q) = LLINK(p);
2589  LLINK(p) = Node::NullPtr;
2590 
2591  /* Checks if successor is right child of p. In this case, p will
2592  become q's son. This situation happens when p's son does not have
2593  a left branch */
2594  if (RLINK(p) == q)
2595  {
2596  RLINK(p) = RLINK(q);
2597  RLINK(q) = p;
2598  pq = pp;
2599  pp = q;
2600  return;
2601  }
2602 
2603  /* In this case, successor is the leftmost node descending from
2604  right son of p */
2605  Node *qr = RLINK(q);
2606  RLINK(q) = RLINK(p);
2607  LLINK(pq) = p;
2608  RLINK(p) = qr;
2609 
2610  std::swap(pp, pq);
2611 }
2612 
2630  template <class Node> inline
2631 void swap_node_with_predecessor(Node * p, // Node for swapping
2632  Node *& pp, // p's parent
2633  Node * q, // Predecessor inorder of p
2634  Node *& pq) // q's parent
2635 {
2636  I((p != Node::NullPtr) and (q != Node::NullPtr) and
2637  (pp != Node::NullPtr) and (pq != Node::NullPtr));
2638  I((RLINK(pp) == p) or (LLINK(pp) == p)); /* assert pp is parent of p */
2639  I((RLINK(pq) == q) or (LLINK(pq) == q)); /* assert pq is parent of q */
2640  I(RLINK(q) == Node::NullPtr);
2641 
2642  /* Set of pp to its new son q */
2643  if (RLINK(pp) == p)
2644  RLINK(pp) = q;
2645  else
2646  LLINK(pp) = q;
2647 
2648  RLINK(q) = RLINK(p);
2649  RLINK(p) = Node::NullPtr;
2650 
2651  /* Checks if predecessor is left child of p. In this case, p will
2652  become q's son. This situation happens when p's son does not have
2653  a right branch */
2654  if (LLINK(p) == q)
2655  {
2656  LLINK(p) = LLINK(q);
2657  LLINK(q) = p;
2658  pq = pp;
2659  pp = q;
2660  return;
2661  }
2662 
2663  /* In this case, predecessor is the rightmost node descending from
2664  right son of p */
2665  Node *ql = LLINK(q);
2666  LLINK(q) = LLINK(p);
2667  RLINK(pq) = p;
2668  LLINK(p) = ql;
2669  std::swap(pp, pq);
2670 }
2671 
2690  template <class Node, class Key,
2691  class Compare = Aleph::less<typename Node::key_type> > inline
2692 Node * insert_root_rec(Node * root, Node * p)
2693 {
2694  if (root == Node::NullPtr)
2695  return p; /* insertion in empty tree */
2696 
2697  if (Compare () (KEY(p), KEY(root)))
2698  { /* insert in left subtree */
2699  Node *left_branch =
2700  insert_root_rec<Node, Key, Compare>(static_cast<Node*>(LLINK(root)), p);
2701  if (left_branch == Node::NullPtr)
2702  return (Node*) Node::NullPtr;
2703 
2704  LLINK(root) = left_branch;
2705  root = rotate_to_right(root);
2706  }
2707  else if (Compare () (KEY(root), KEY(p) ))
2708  { /* insert in right subtree */
2709  Node *right_branch =
2710  insert_root_rec<Node, Key, Compare>(static_cast<Node*>(RLINK(root)), p);
2711  if (right_branch == Node::NullPtr)
2712  return (Node*) Node::NullPtr;
2713 
2714  RLINK(root) = right_branch;
2715  root = rotate_to_left(root);
2716  }
2717  else
2718  return (Node*) Node::NullPtr; /* duplicated key */
2719 
2720  return root;
2721 }
2722 
2741  template <class Node, class Key,
2742  class Compare = Aleph::less<typename Node::key_type> > inline
2743 Node * search_or_insert_root_rec(Node * root, Node * p)
2744 {
2745  if (root == Node::NullPtr)
2746  return p; // insertion in empty tree
2747 
2748  if (Compare () (KEY(p), KEY(root)))
2749  { // insert in left subtree
2750  Node * left_branch =
2751  search_or_insert_root_rec<Node, Key, Compare>((Node*) LLINK(root), p);
2752  if (left_branch == p) // ¿hubo inserción?
2753  {
2754  LLINK(root) = left_branch;
2755  root = rotate_to_right(root);
2756  return p;
2757  }
2758 
2759  return left_branch; // no la hubo
2760  }
2761  else if (Compare () (KEY(root), KEY(p)))
2762  { // insert in right subtree
2763  Node * right_branch =
2764  search_or_insert_root_rec<Node, Key, Compare>((Node*) RLINK(root), p);
2765  if (right_branch == p) // ¿hubo inserción?
2766  {
2767  RLINK(root) = right_branch;
2768  root = rotate_to_left(root);
2769  return p;
2770  }
2771 
2772  return right_branch; // no la hubo
2773  }
2774 
2775  return root;
2776 }
2777 
2778 
2779 } // end Aleph
2780 
2781 # endif // TPL_BINNODEUTILS_H
Node * join_preorder(Node *t1, Node *t2, Node *&dup)
Definition: tpl_binNodeUtils.H:2300
Node * search_or_insert_root_rec(Node *root, Node *p)
Definition: tpl_binNodeUtils.H:2743
Itor::difference_type count(const Itor &beg, const Itor &end, const T &value)
Definition: ahAlgo.H:127
Definition: Queue.H:18
#define LLINK(p)
Definition: tpl_binNode.H:196
DynList< Node * > infix(Node *root)
Definition: tpl_binNodeUtils.H:728
void save(ofstream &output)
Definition: bitArray.H:378
#define RLINK(p)
Definition: tpl_binNode.H:201
Definition: tpl_binNodeUtils.H:407
size_t postOrderStack(Node *root, void(*visitFct)(Node *, int, int))
Definition: tpl_binNodeUtils.H:632
Definition: Stack.H:19
void preOrderThreaded(Node *node, void(*visitFct)(Node *))
Definition: tpl_binNodeUtils.H:1205
DynList< Node * > suffix(Node *root)
Definition: tpl_binNodeUtils.H:742
size_t preOrderStack(Node *node, void(*visitFct)(Node *, int, int))
Definition: tpl_binNodeUtils.H:512
Definition: ahFunction.H:145
Definition: bitArray.H:96
Definition: tpl_dynDlist.H:26
Definition: tpl_arrayStack.H:42
const size_t & size() const
Retorna el número de elementos que contiene la pila.
Definition: tpl_arrayStack.H:184
void operator()(Node *root, Op &op)
operación sobre cada nodo
Definition: tpl_binNodeUtils.H:281
Node * search_rank_parent(Node *root, const typename Node::key_type &key, Compare &&cmp=Compare())
Definition: tpl_binNodeUtils.H:1921
void split_key(Node *root, const Key &key, Node *&l, Node *&r)
Definition: tpl_binNodeUtils.H:2494
void load(ifstream &input)
Definition: bitArray.H:406
Definition: tpl_arrayQueue.H:38
Node * insert_root_rec(Node *root, Node *p)
Definition: tpl_binNodeUtils.H:2692
void swap_node_with_successor(Node *p, Node *&pp, Node *q, Node *&pq)
Definition: tpl_binNodeUtils.H:2571
void swap_node_with_predecessor(Node *p, Node *&pp, Node *q, Node *&pq)
Definition: tpl_binNodeUtils.H:2631
void load_tree_keys_in_prefix(Node *root, ifstream &input)
Definition: tpl_binNodeUtils.H:1409
Node * insert_root(Node *&root, Node *p)
Definition: tpl_binNodeUtils.H:2236
Node * insert_dup_in_binary_search_tree(Node *&root, Node *p)
Definition: tpl_binNodeUtils.H:1997
Node * find_max(Node *root)
Definition: tpl_binNodeUtils.H:1784
Definition: tpl_dynListQueue.H:22
T & put(const T &item)
Definition: tpl_arrayQueue.H:138
void operator()(Node *root, Op &op)
operación sobre cada nodo
Definition: tpl_binNodeUtils.H:421
void save_in_array_of_chars(const string &name, ofstream &output)
Definition: bitArray.H:442
Node * bits_to_tree(BitArray &array, int idx=0)
Definition: tpl_binNodeUtils.H:1356
Node * rotate_to_right(Node *p)
Definition: tpl_binNodeUtils.H:2375
void operator()(Node *root, Op &op)
operación sobre cada nodo
Definition: tpl_binNodeUtils.H:187
T & push(const T &data)
Definition: tpl_arrayStack.H:84
size_t internal_path_length(Node *p)
Definition: tpl_binNodeUtils.H:1259
Node * find_min(Node *root)
Definition: tpl_binNodeUtils.H:1764
Node * searchInBinTree(Node *root, const typename Node::key_type &key, Compare &cmp)
Definition: tpl_binNodeUtils.H:1728
Node * join_exclusive(Node *&ts, Node *&tg)
Definition: tpl_binNodeUtils.H:2155
void save_tree_in_array_of_chars(Node *root, const string &array_name, ofstream &output)
Definition: tpl_binNodeUtils.H:1559
int preOrderRec(Node *root, void(*visitFct)(Node *, int, int))
Definition: tpl_binNodeUtils.H:93
Definition: tpl_binNodeUtils.H:325
Node * rotate_to_left(Node *p, Node *pp)
Definition: tpl_binNodeUtils.H:2448
Node * preorder_to_binary_search_tree(DynArray< typename Node::key_type > &preorder, const int &l, const int &r)
Definition: tpl_binNodeUtils.H:1687
Definition: tpl_binNodeUtils.H:260
Node * join(Node *t1, Node *t2, Node *&dup)
Definition: tpl_binNodeUtils.H:2337
void split_key_dup_rec(Node *root, const typename Node::key_type &key, Node *&ts, Node *&tg)
Definition: tpl_binNodeUtils.H:2121
size_t computeHeightRec(Node *node)
Definition: tpl_binNodeUtils.H:778
Node * load_tree(ifstream &input)
Definition: tpl_binNodeUtils.H:1470
Node * find_predecessor(Node *p, Node *&pp)
Definition: tpl_binNodeUtils.H:1833
void push(const unsigned int value)
Inserta al final del arreglo el valor value.
Definition: bitArray.H:281
Node * insert_in_binary_search_tree(Node *&root, Node *p)
Definition: tpl_binNodeUtils.H:1963
Node * insert_dup_root(Node *&root, Node *p)
Definition: tpl_binNodeUtils.H:2274
bool split_key_rec(Node *root, const typename Node::key_type &key, Node *&ts, Node *&tg)
Definition: tpl_binNodeUtils.H:2067
int read_bit(const size_t i) const
Definition: bitArray.H:225
size_t compute_cardinality_rec(Node *node)
Definition: tpl_binNodeUtils.H:760
void load_from_array_of_chars(const unsigned char str[], const size_t num_bits)
Definition: bitArray.H:479
void save_tree_keys_in_prefix(Node *root, ofstream &output)
Definition: tpl_binNodeUtils.H:1377
void destroyRec(Node *&root)
Definition: tpl_binNodeUtils.H:798
T get()
Definition: tpl_arrayQueue.H:199
int postOrderRec(Node *root, void(*visitFct)(Node *, int, int))
Definition: tpl_binNodeUtils.H:134
bool level_traverse(Node *root, Operation &operation)
Definition: tpl_binNodeUtils.H:992
Node * search_parent(Node *root, const typename Node::key_type &key, Node *&parent, Compare &&cmp=Compare())
Definition: tpl_binNodeUtils.H:1873
size_t simple_preOrderStack(Node *node, void(*visitFct)(Node *, int, int))
Definition: tpl_binNodeUtils.H:460
void levelOrder(Node *root, void(*visitFct)(Node *, int, bool), size_t queue_size)
Definition: tpl_binNodeUtils.H:943
size_t inOrderStack(Node *node, void(*visitFct)(Node *, int, int))
Definition: tpl_binNodeUtils.H:572
Definition: tpl_binNodeUtils.H:172
BitArray tree_to_bits(Node *root)
Definition: tpl_binNodeUtils.H:1314
Node * copyRec(Node *src_root)
Definition: tpl_binNodeUtils.H:821
Node * remove_from_search_binary_tree(Node *&root, const typename Node::key_type &key)
Definition: tpl_binNodeUtils.H:2193
T pop()
Definition: tpl_arrayStack.H:119
Node * find_successor(Node *p, Node *&pp)
Definition: tpl_binNodeUtils.H:1804
Node * load_tree_from_array(const unsigned char bits[], const size_t &num_bits, const char *keys[])
Definition: tpl_binNodeUtils.H:1620
bool check_binary_search_tree(Node *p)
Definition: tpl_binNodeUtils.H:1647
void compute_nodes_in_level(Node *root, const int &level, DynDlist< Node * > &list)
Definition: tpl_binNodeUtils.H:1111
Definition: ahDry.H:13
T & append(const T &item)
Inserta un item como último elemento.
Definition: htlist.H:685
#define KEY(p)
Definition: tpl_binNode.H:206
void operator()(Node *root, Op &op)
operación sobre cada nodo
Definition: tpl_binNodeUtils.H:340
T get()
Definition: tpl_dynListQueue.H:107
void save_tree(Node *root, ofstream &output)
Definition: tpl_binNodeUtils.H:1446
DynList< Node * > prefix(Node *root)
Definition: tpl_binNodeUtils.H:714
Definition: List.H:23
Node * search_or_insert_in_binary_search_tree(Node *&r, Node *p)
Definition: tpl_binNodeUtils.H:2029
bool is_empty() const
Retorna true si la pila está vacía.
Definition: tpl_arrayStack.H:181
Node< Key > * build_tree(DynArray< Key > &preorder, const int &l_p, const int &r_p, DynArray< Key > &inorder, const int &l_i, const int &r_i)
Definition: tpl_binNodeUtils.H:1045
T & put(const T &data)
Definition: tpl_dynListQueue.H:86
T & append(const T &item)
Definition: tpl_dynDlist.H:106
int inOrderRec(Node *root, void(*visitFct)(Node *, int, int))
Definition: tpl_binNodeUtils.H:51
void inOrderThreaded(Node *root, void(*visitFct)(Node *))
Definition: tpl_binNodeUtils.H:1143

Leandro Rabindranath León