SheafSystem  0.0.0.0
zone_centered_segment_refiner.cc
Go to the documentation of this file.
1 
2 //
3 // Copyright (c) 2014 Limit Point Systems, Inc.
4 //
5 // Licensed under the Apache License, Version 2.0 (the "License");
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 // http://www.apache.org/licenses/LICENSE-2.0
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an "AS IS" BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17 
20 
21 #include "SheafSystem/zone_centered_segment_refiner.h"
22 
23 #include "SheafSystem/assert_contract.h"
24 #include "SheafSystem/base_space_poset.h"
25 #include "SheafSystem/error_message.h"
26 #include "SheafSystem/block.impl.h"
27 #include "SheafSystem/field_refinement_buffer.h"
28 #include "SheafSystem/section_evaluator.h"
29 #include "SheafSystem/sec_ed_invertible.h"
30 #include "SheafSystem/field_vd.h"
31 
32 using namespace std;
33 using namespace fields; // Workaround for MS C++ bug.
34 
35 // ===========================================================
36 // ZONE_CENTERED_SEGMENT_REFINER FACET
37 // ===========================================================
38 
39 // PUBLIC MEMBER FUNCTIONS
40 
43  : local_field_refiner(xpolicy)
44 {
45  // Preconditions:
46 
47  // Body:
48 
49  // Postconditions:
50 
51  ensure(invariant());
52  ensure(&policy() == &xpolicy);
53 
54  return;
55 }
56 
57 
60 {
61  // Preconditions:
62 
63  // Body:
64 
65  not_implemented();
66 
67  // Postconditions:
68 
69  ensure(invariant());
70 
71  return;
72 }
73 
74 
75 // PROTECTED MEMBER FUNCTIONS
76 
79 {
80  // Preconditions:
81 
82  // Body:
83 
84  not_implemented();
85 
86  // Postconditions:
87 
88  ensure(invariant());
89 
90  return;
91 }
92 
93 void
96 {
97  // Preconditions:
98 
99  require(xbuffer.base_space != 0);
100  require(xbuffer.base_space->in_jim_edit_mode());
101 
102  // Body:
103 
104  // Modify the cover relation graph.
105 
106  modify_crg(xbuffer);
107 
108  // Modify the subposets.
109 
110  modify_subposets(xbuffer);
111 
112  // Put the new zones in the refined zone ids buffer
113 
117 
118  // Postconditions:
119 
120  // Exit:
121 
122  return;
123 }
124 
125 void
128 {
129  // Preconditions:
130 
131  require(xbuffer.base_space != 0);
132  require(xbuffer.base_space->in_jim_edit_mode());
133 
134  // Body:
135 
136  base_space_poset* lbase = xbuffer.base_space;
137  scoped_index lzone_id = xbuffer.zone_id;
138  int lzone_depth = lbase->refinement_depth(lzone_id);
139  int lnew_depth = lzone_depth + 1;
140 
141  assertion(lzone_id.same_scope(lbase->member_hub_id_space(false)));
142 
145 
146  // Unlink the lower cover of the current zone.
147 
148  pod_index_type lpoint0_id = lbase->first_cover_member(LOWER, lzone_id.pod());
149  lbase->delete_link(lzone_id.pod(), lpoint0_id);
150  pod_index_type lpoint1_id = lbase->first_cover_member(LOWER, lzone_id.pod());
151  lbase->delete_link(lzone_id.pod(), lpoint1_id);
152 
153  // Create a new point.
154 
155  _new_point_id = lbase->member_id(create_vertex(*lbase, lnew_depth), false);
156 
157  // Create a first new segment.
158 
159  _new_seg_0_id = lbase->member_id(create_zone(*lbase, lnew_depth), false);
160 
161  // Link the first new segment to the first point and the new point.
162 
163  lbase->new_link(_new_seg_0_id.pod(), lpoint0_id);
164  lbase->new_link(_new_seg_0_id.pod(), _new_point_id.pod());
165 
166  // Link the current zone to the first new segment.
167 
168  lbase->new_link(lzone_id, _new_seg_0_id);
169 
170  // Create a second new segment.
171 
172  _new_seg_1_id = lbase->member_id(create_zone(*lbase, lnew_depth), false);
173 
174  // Link the second new segment to the new point and the second point.
175 
176  lbase->new_link(_new_seg_1_id.pod(), _new_point_id.pod());
177  lbase->new_link(_new_seg_1_id.pod(), lpoint1_id);
178 
179  // Link the current zone to the second new segment.
180 
181  lbase->new_link(lzone_id.pod(), _new_seg_1_id.pod());
182 
183  // Postconditions:
184 
185  // Exit:
186 
187  return;
188 }
189 
190 void
193 {
194  // Preconditions:
195 
196  require(xbuffer.base_space != 0);
197 
198  // Body:
199 
200  base_space_poset* lbase = xbuffer.base_space;
201  scoped_index lzone_id = xbuffer.zone_id;
202  subposet& lvertices = lbase->vertices();
203  subposet& lelements = lbase->elements();
204 
205  // More efficient to get id spaces from buffer than directly from subposets
206  // because latter uses lookup by name.
207 
208  scattered_insertion_index_space_handle* lvertices_id_space = xbuffer.vertices_id_space;
209  scattered_insertion_index_space_handle* lcoord_disc_seq_id_space = xbuffer.coord_disc_seq_id_space;
210  scattered_insertion_index_space_handle* lelements_id_space = xbuffer.elements_id_space;
211 
212  // Put the new point in the vertices subposet and extend the sequence id space.
213 
214  lvertices.insert_member(_new_point_id);
215  lvertices_id_space->push_back(_new_point_id);
216  lcoord_disc_seq_id_space->push_back(_new_point_id);
217 
218  // The refined zone is no longer an element;
219  // remove it from the elements subposet.
220 
228 
229  // When removing the member, we have to be careful to reuse its
230  // sequence id, so the sequence id stays sequential.
231 
234 
235  pod_index_type lseq_id = lelements_id_space->pod(lzone_id);
236 
237  lelements_id_space->remove(lzone_id, true);
238  lelements.remove_member(lzone_id);
239 
240  // Put the first new segment in the elements subposet,
241  // reusing the sequence id of the old segment.
242 
243  lelements.insert_member(_new_seg_0_id);
244  lelements_id_space->insert(lseq_id, _new_seg_0_id);
245 
246  // Put the second new segment in the elements subposet,
247  // extending the sequence id space.
248 
249  lelements.insert_member(_new_seg_1_id);
250  lelements_id_space->push_back(_new_seg_1_id);
251 
252  // Postconditions:
253 
254  // Exit:
255 
256  return;
257 }
258 
259 
260 void
263 {
264  // Preconditions:
265 
266  // Body:
267 
268  scoped_index lzone_id = xbuffer.zone_id;
269 
270  // Set the local coordinates buffer to the center of the zone.
271 
272  xbuffer.coord_evaluator->center(xbuffer.local_coords);
273 
274  // Evaluate the global coordinates at the local coordinates.
275 
276  xbuffer.coord_evaluator->value_at_coord(xbuffer.coord_dofs,
277  xbuffer.local_coords,
278  xbuffer.coord_value);
279 
280  // Make sure the coordinates dof map has enough capacity for the new point.
281 
283 
284  // Insert the value in the coordinates section.
285 
287  xbuffer.coord_value.base(),
288  xbuffer.coord_value.ct()*sizeof(sec_vd_dof_type),
289  false);
290 
291  // Postconditions:
292 
293 
294  // Exit:
295 
296  return;
297 }
298 
299 
300 // PRIVATE MEMBERS
301 
302 //const sheaf::size_type
303 //fields::zone_centered_segment_refiner::
304 //REFINED_ZONE_CT;
305 
306 
307 // ===========================================================
308 // LOCAL_FIELD_REFINER FACET
309 // ===========================================================
310 
311 // PUBLIC MEMBER FUNCTIONS
312 
313 int
315 db() const
316 {
317  int result;
318 
319  // Preconditions:
320 
321 
322  // Body:
323 
324  result = 1;
325 
326  // Postconditions:
327 
328  ensure(result == 1);
329 
330  // Exit:
331 
332  return result;
333 }
334 
335 
336 const std::string&
339 {
340  // Preconditions:
341 
342 
343  // Body:
344 
345  static const string result("segment_complex");
346 
347  // Postconditions:
348 
349  ensure(!result.empty());
350 
351  // Exit:
352 
353  return result;
354 }
355 
359 {
360  size_type result;
361 
362  // Preconditions:
363 
364 
365  // Body:
366 
367  result = REFINED_ZONE_CT;
368 
369  // Postconditions:
370 
371  ensure(result > 1);
372 
373  // Exit:
374 
375  return result;
376 }
377 
381 {
382  // Preconditions:
383 
384  require(xi < refined_zone_ct());
385 
386  // Body:
387 
388  // Affine transformation u'[i] = T[i][j]*u[j] + T[i][db];
389  // with sum convention over 0 <= j < db.
390 
391  // Specifically:
392  //
393  // u' = a*u +b*v + c;
394  // v' = d*u _e*v + f.
395  //
396  // map = {a, b, c, d, e, f}
397  // One such map for each refined zone.
398 
399  // 2 = db*(db+1)
400 
401  static const chart_point_coord_type lmap[REFINED_ZONE_CT][2] =
402  {
403  {
404  0.5, 0.0
405  },
406  {0.5, 0.5}
407  };
408 
409 
410  const chart_point_coord_type* result = lmap[xi];
411 
412  // Postconditions:
413 
414  // Exit:
415 
416  return result;
417 }
418 
419 
420 // ===========================================================
421 // ANY FACET
422 // ===========================================================
423 
424 // PUBLIC MEMBER FUNCTIONS
425 
428 clone() const
429 {
431 
432  // Preconditions:
433 
434  // Body:
435 
436  result = new zone_centered_segment_refiner();
437 
438  // Postconditions:
439 
440  ensure(result != 0);
441  // ensure(invariant());
442  ensure(result->invariant());
443  ensure(is_same_type(result));
444 
445  return result;
446 }
447 
451 {
452  // Preconditions:
453 
454  require(is_ancestor_of(&xother));
455 
456  // Body:
457 
458  not_implemented();
459 
460  // Postconditions:
461 
462  ensure(invariant());
463 
464  return *this;
465 }
466 
471 {
472 
473  // Preconditions:
474 
475  require(is_ancestor_of(&xother));
476 
477  // Body:
478 
479  not_implemented();
480 
481  // Postconditions:
482 
483  ensure(invariant());
484 
485  // Exit:
486 
487  return *this;
488 }
489 
492 {
493  // Preconditions:
494 
495  // Body:
496 
497  // Postconditions:
498 
499  ensure(invariant());
500 
501  return;
502 }
503 
504 
505 bool
507 invariant() const
508 {
509  bool result = true;
510 
511  // Preconditions:
512 
513  // Body:
514 
515  // Must satisfy base class invariant.
516 
517  result = result && local_field_refiner::invariant();
518 
519  if(invariant_check())
520  {
521  // Prevent recursive calls to invariant.
522 
524 
525  // Finished, turn invariant checking back on.
526 
528  }
529 
530  // Postconditions:
531 
532  return result;
533 }
534 
535 bool
537 is_ancestor_of(const any* xother) const
538 {
539 
540  // Preconditions:
541 
542  require(xother != 0);
543 
544  // Body:
545 
546  // True if other conforms to this
547 
548  bool result = dynamic_cast<const zone_centered_segment_refiner*>(xother) != 0;
549 
550  // Postconditions:
551 
552  return result;
553 
554 }
555 
556 
557 
double chart_point_coord_type
The type of local coordinate in the base space; the scalar type for the local coordinate vector space...
Definition: fiber_bundle.h:57
virtual zone_centered_segment_refiner * clone() const
Virtual constructor, creates a new instance of the same type as this.
virtual bool invariant() const
Class invariant.
A client handle for a subposet.
Definition: subposet.h:86
section_evaluator * coord_evaluator
The section evaluator for the coordinates section of the target.
zone_centered_segment_refiner()
Default constructor; disabled.
size_type ct() const
The number of items currently in use.
const pod_type & pod() const
The "plain old data" storage of this; the value in the external id space.
Definition: scoped_index.h:672
A field refiner that introduces a new vertex in the center of a segment.
virtual size_type refined_zone_ct() const
The number of refined zones created by this.
scattered_insertion_index_space_handle * coord_disc_seq_id_space
The discretization sequence id space of the target coordinates.
virtual const std::string & zone_type_name() const
The name of the type of zone this creates during refinement.
A buffer for data which is used by both a local_field_refiner object and its associated field_refinem...
Namespace for fields component of sheaf system.
size_type remove(const scoped_index &xid, bool update_extrema)
Removes the equivalence associated with xid.hub_pod(). synonym for remove_hub(xid.hub_pod(), xupdate_extrema). Returns the number of entries actually removed, either 0 or 1.
pod_index_type create_vertex(base_space_poset &xbase, int xdepth)
Creates a new vertex at depth xdepth.
virtual void refine_coordinates(field_refinement_buffer &xbuffer)
Refines the coordinates of the target.
STL namespace.
block< sec_vd_value_type > coord_value
A buffer for computing coordinates at a point.
virtual dof_type value_at_coord(const dof_type xdofs[], size_type xdofs_ub, const dof_type xlocal_coords[], size_type xlocal_coords_ub) const
Value at a specified local_coordinate. Single component version.
virtual pod_type pod(pod_type xid) const
The pod index in this space equivalent to xid in the hub id space.
block< sec_vd_dof_type > coord_dofs
A buffer for gathering coordinate dofs.
bool same_scope(const scoped_index &xother) const
True if and only if this is in the same id space as xother.
Definition: scoped_index.h:464
virtual bool invariant() const
Class invariant.
const field_refinement_policy & policy() const
The refinement policy for this refiner.
Abstract base class with useful features for all objects.
Definition: any.h:39
The lattice of closed cells of a cellular space; a lattice representation of a computational mesh...
void reserve_coord_fiber(const scoped_index &xdisc_id)
Ensures the coordinate dofs have enough capacity for discretization id xdisc.
void push_back(const_reference_type item)
Insert item at the end of the items in the auto_block.
const chart_point_coord_type * local_coordinates_map(size_type xi) const
The map from the local coordinates of refined zone xi the the local coordinates of the parent zone...
scoped_index zone_id
The id of the current zone.
scoped_index _new_point_id
The index of the point added by the current base space refinement.
scattered_insertion_index_space_handle * elements_id_space
The sequence id space used by the elements subposet.
subposet & vertices()
The subposet containing all the vertices, that is, the cells of dimension 0 (mutable version)...
pointer_type base() const
The underlying storage array.
void set_ct(size_type xct)
Sets ct() == xct.
An index within the external ("client") scope of a given id space.
Definition: scoped_index.h:116
virtual int db() const
The base dimension; the dimension of the local coordinates (independent variable).
unsigned long size_type
An unsigned integral type used to represent sizes and capacities.
Definition: sheaf.h:52
An abstract policy that determines the conditions under which a zone should be refined.
scoped_index _new_seg_0_id
The index of the first segment added by the current base space refinement.
virtual void insert_member(pod_index_type xmbr_hub_id)
Inserts the member of host() with hub id xmbr_hub_id.
Definition: subposet.cc:1091
void insert(pod_type xid, const scoped_index &xhub_id)
Make id xid in this id space equivalent to xhub_id in the hub id space. synonym for insert(xid...
virtual void center(coord_type xresult[], size_type xresult_ub) const
The local coordinates at the center of the evaluator.
virtual bool is_ancestor_of(const any *xother) const
Conformance test; true if other conforms to this.
void disable_invariant_check() const
Disable invariant check. Intended for preventing recursive calls to invariant and for suppressing inv...
Definition: any.h:97
field_vd & target
The field being refined.
virtual zone_centered_segment_refiner & operator=(const local_field_refiner &xother)
Assignment operator.
scattered_insertion_index_space_handle * vertices_id_space
The sequence id space used by the vertices subposet.
const bool LOWER
Selector for lower cover.
Definition: sheaf.h:67
virtual void refine_base_space(field_refinement_buffer &xbuffer)
Refines the base space or the target.
An abstract refiner for a field over a local region (primitive cell) in the base space.
bool invariant_check() const
True if invariant checking is enabled.
Definition: any.h:79
void put_fiber(pod_index_type xdisc_id, const vd_lite &xfiber)
Sets the fiber referred to by discretization id xdisc_id to xfiber.
Definition: sec_vd.cc:1144
virtual void remove_member(pod_index_type xmbr_hub_id)
Removes the member of host() with hub id xmbr_hub_id.
Definition: subposet.cc:1209
int_type pod_index_type
The plain old data index type.
Definition: pod_types.h:49
A handle for a scattered_insertion_index_space_state.
sec_ed_invertible & coordinates() const
The independent variable of this field.
Definition: field_vd.cc:339
void push_back(const scoped_index &xhub_id)
Make the next id in this space equivalent to xhub_id in the hub id space. synonym for push_back(xhub_...
subposet & elements()
The subposet containing the elements or zones, that is, the cells of maximal dimension.
block< chart_point_coord_type > local_coords
A buffer for the local coordinates of a point.
pod_index_type create_zone(base_space_poset &xbase, int xdepth)
Creates a new quadrangle in base space xbase, with refinement depth xdepth.
void modify_crg(field_refinement_buffer &xbuffer)
Modifies the cover relation graph of the base space.
base_space_poset * base_space
The current base space.
double sec_vd_dof_type
The type of degree of freedom in the section space.
Definition: fiber_bundle.h:78
bool in_jim_edit_mode() const
True if editing jims and jim order relation is allowed.
bool is_same_type(const any *other) const
True if other is the same type as this.
Definition: any.cc:79
void enable_invariant_check() const
Enable invariant checking.
Definition: any.h:87
void modify_subposets(field_refinement_buffer &xbuffer)
Modifies subposets in the base space.
scoped_index _new_seg_1_id
The index of the second segment added by the current base space refinement.
block< scoped_index > _refined_zone_ids
The member ids of the zones created by the most recent execution of refine().