OPAL (Object Oriented Parallel Accelerator Library)  2021.1.99
OPAL
DomainMap.hpp
Go to the documentation of this file.
1 // -*- C++ -*-
2 /***************************************************************************
3  *
4  * The IPPL Framework
5  *
6  * This program was prepared by PSI.
7  * All rights in the program are reserved by PSI.
8  * Neither PSI nor the author(s)
9  * makes any warranty, express or implied, or assumes any liability or
10  * responsibility for the use of this software
11  *
12  * Visit www.amas.web.psi for more details
13  *
14  ***************************************************************************/
15 
16 // -*- C++ -*-
17 /***************************************************************************
18  *
19  * The IPPL Framework
20  *
21  *
22  * Visit http://people.web.psi.ch/adelmann/ for more details
23  *
24  ***************************************************************************/
25 
26 // include files
27 #include "Index/NDIndex.h"
28 #include "Field/LField.h"
29 #include "FieldLayout/Vnode.h"
30 
31 
32 
33 
34 
35 
37 
38 // Insert a new key in the DomainMap.
39 
40 template < class Key , class T , class Touches, class Contains, class Split >
41 void
43  bool noSplit)
44 {
45 
46 
47 
48  // Tell the tree top to insert.
49  Root->insert(d, noSplit);
50  // Increment the total size.
51  Size += 1;
52  // Update the pointer to the first element.
53  update_leftmost();
54 }
55 
57 
58 // Recalculate the first element in the tree.
59 
60 template < class Key , class T , class Touches, class Contains, class Split >
61 void
63 {
64 
65 
66 
67  Node *p=Root;
68  // First dive all the way left.
69  while ( p->Left )
70  p = p->Left;
71  // Look for the first element.
72  typename Node::cont_type::iterator v;
73  while ( (v=p->cont.begin()) == p->cont.end() ) {
74  // First look right.
75  if ( p->Right ) {
76  // If it is there, go there and then all the way left.
77  p = p->Right;
78  while ( p->Left )
79  p = p->Left;
80  }
81  else {
82  // If there is no right, go up until you can go right more.
83  Node *y = p->Parent;
84  while (y && (p==y->Right)) {
85  p = y;
86  y = y->Parent;
87  }
88  p = y;
89  }
90  }
91  if ( (Leftmost.p=p) != 0 )
92  Leftmost.v = v;
93 }
94 
96 
97 // Find the range that touches a given T.
98 
99 template < class Key, class T , class Touches, class Contains, class Split >
100 std::pair<typename DomainMap<Key,T,Touches,Contains,Split>::touch_iterator,
103 {
104 
105  Node *p=Root;
106 
107  if ( p ) {
108 
109  // First dive left, checking touches.
110  for ( Node* y=p->Left; y && Touches::test(t,y->MyDomain); y=y->Left )
111  p = y;
112 
113  do {
114  // Look for the first element that actually touches.
115  for (typename Node::cont_type::iterator v=p->cont.begin();
116  v!=p->cont.end(); ++v)
117  if ( Touches::test(t,(*v).first) ) {
118  // Found it!
119  touch_iterator f;
120  f.TouchThis = t;
121  f.p = p;
122  f.v = v;
123  return std::pair<touch_iterator,touch_iterator>(f,touch_iterator());
124  }
125 
126  // Didn't find one here. Move on.
127  Node *y = p->Right;
128  if ( y && Touches::test(t,y->MyDomain) ) {
129  // If it is there, go there and then all the way left.
130  p = y;
131  for ( y=p->Left; y && Touches::test(t,y->MyDomain) ; y=y->Left )
132  p = y;
133  }
134  else {
135  // If there is no right, go up until you can go right more.
136  for ( y = p->Parent; y && (p==y->Right); y = y->Parent )
137  p = y;
138  p = y;
139  }
140  } while (p);
141  }
142  // Didn't find any.
143  return std::pair<touch_iterator,touch_iterator>(touch_iterator(),touch_iterator());
144 }
145 
147 
148 //
149 // Copy ctor and assign do deep copies.
150 //
151 
152 template < class Key, class T , class Touches, class Contains, class Split >
155 : Root( new Node(a.Root->MyDomain) ), Size(0)
156 {
157 
158 
159 
160  for (iterator p=a.begin(); p!=a.end(); ++p)
161  insert_noupdate( *p );
162  update_leftmost();
163 }
164 
165 template < class Key, class T , class Touches, class Contains, class Split >
166 void
169 {
170 
171 
172 
173  if ( this != &a ) {
174  // Clean out the current contents.
175  delete Root;
176  Root = new Node( a.Root->MyDomain );
177  Size = 0;
178  // Add the new stuff.
179  for (iterator p=a.begin(); p!=a.end(); ++p)
180  insert_noupdate( *p );
181  // Reset the pointer to the first one.
182  update_leftmost();
183  }
184 }
185 /***************************************************************************
186  * $RCSfile: DomainMap.cpp,v $ $Author: adelmann $
187  * $Revision: 1.1.1.1 $ $Date: 2003/01/23 07:40:25 $
188  * IPPL_VERSION_ID: $Id: DomainMap.cpp,v 1.1.1.1 2003/01/23 07:40:25 adelmann Exp $
189  ***************************************************************************/
std::complex< double > a
std::string::iterator iterator
Definition: MSLang.h:16
void operator=(const DomainMap< Key, T, Touches, Contains, Split > &)
Definition: DomainMap.hpp:168
void update_leftmost()
Definition: DomainMap.hpp:62
void insert(const value_type &d, bool noSplit=false)
Definition: DomainMap.hpp:42
std::pair< touch_iterator, touch_iterator > touch_range(const Key &t) const
Definition: DomainMap.hpp:102
void insert_noupdate(const value_type &d)
Definition: DomainMap.h:526
Node * Right
Definition: DomainMap.h:99
cont_type cont
Definition: DomainMap.h:101
Node::cont_type::iterator v
Definition: DomainMap.h:469
static bool test(const NDIndex< Dim > &a, const NDIndex< Dim > &b)
Definition: NDIndex.h:265