rheolef  6.3
geo_trace_move.cc
Go to the documentation of this file.
1 // en utilisant une table de liens S -> K (face-element: meme procs)
2 // => trace_ray renvoie un numero d'element tout de suite
3 // les liens S -> sont dans le maillage des la lecture : geo::get
4 #include "rheolef/geo.h"
5 
6 namespace rheolef {
7 
8 template <class T, class M>
11  const point_basic<T>& x,
12  const point_basic<T>& v,
13  point_basic<T>& y) const
14 {
15  y = x+v;
16  size_type dis_ie = _locator.seq_locate (*this,y);
17  if (dis_ie != std::numeric_limits<size_type>::max()) {
18  return dis_ie;
19  }
20  bool hit = _tracer_ray_boundary.seq_trace_ray_boundary (*this, x, v, y);
21  if (hit) {
22  dis_ie = _locator.seq_locate (*this,y);
23  check_macro (dis_ie != std::numeric_limits<size_type>::max(), "invalid ray computation");
24  return dis_ie;
25  }
26  for (size_t i = 0; i < _dimension; i++) {
27  y[i] = (v[i] < 0) ? _xmin[i] : _xmax[i];
28  }
29  dis_ie = _locator.seq_locate (*this,y);
30  if (dis_ie != std::numeric_limits<size_type>::max()) {
31  return dis_ie;
32  }
33  error_macro ("invalid dis_trace_move");
35 }
36 template <class T, class M>
39  const point_basic<T>& x,
40  const point_basic<T>& v,
41  point_basic<T>& y) const
42 {
43  y = x+v;
44  size_type dis_ie = _locator.dis_locate (*this,y);
45  if (dis_ie != std::numeric_limits<size_type>::max()) {
46  return dis_ie;
47  }
48  bool hit = _tracer_ray_boundary.dis_trace_ray_boundary (*this, x, v, y);
49  if (hit) {
50  dis_ie = _locator.dis_locate (*this,y);
51  check_macro (dis_ie != std::numeric_limits<size_type>::max(), "invalid ray computation");
52  return dis_ie;
53  }
54  error_macro ("invalid dis_trace_move");
56 }
57 template <class T>
58 void
60  const array<point_basic<T>,sequential>& x,
61  const array<point_basic<T>,sequential>& v,
62  array<size_type, sequential>& dis_ie,
63  array<point_basic<T>,sequential>& y) const
64 {
65  check_macro (x.ownership() == v.ownership(), "invalid ranges for x and v argumenst");
66  dis_ie.resize (x.ownership());
67  y.resize (x.ownership());
68  for (size_type i = 0, n = x.size(); i < n; i++) {
69  dis_ie[i] = base::seq_trace_move (x[i], v[i], y[i]);
70  }
71 }
72 #ifdef _RHEOLEF_HAVE_MPI
73 template <class T>
74 void
76  const array<point_basic<T>,distributed>& x,
77  const array<point_basic<T>,distributed>& v,
78  array<size_type, distributed>& dis_ie, // in: guest; out: localized
79  array<point_basic<T>,distributed>& y) const
80 {
81  trace_macro("trace_move...");
82  check_macro (x.ownership() == v.ownership(), "invalid ranges for x and v argumenst");
83  if (dis_ie.ownership() != x.ownership()) dis_ie.resize (x.ownership());
84  y.resize (x.ownership());
85  for (size_type i = 0, n = x.size(); i < n; i++) {
86  y[i] = x[i] + v[i];
87  }
88  bool do_stop_when_failed = false;
89  trace_macro("trace_move/locate...");
90  locate (y, dis_ie, do_stop_when_failed);
91  std::list<size_type> failed;
92  for (size_type i = 0, n = x.size(); i < n; i++) {
93  if (dis_ie[i] != std::numeric_limits<size_type>::max()) continue;
94  failed.push_back (i);
95  }
96  distributor fld_ownership (distributor::decide, base::comm(), failed.size());
97  if (fld_ownership.dis_size() == 0) {
98  trace_macro("trace_move done(1)");
99  return;
100  }
101  array<point_basic<T> > fld_x (fld_ownership);
102  array<point_basic<T> > fld_v (fld_ownership);
103  array<point_basic<T> > fld_y (fld_ownership);
104  array<size_type> fld_dis_ie (fld_ownership, std::numeric_limits<size_type>::max());
105  typename std::list<size_type>::const_iterator iter = failed.begin();
106  for (size_type fld_i = 0, fld_n = fld_x.size(); fld_i < fld_n; ++fld_i, ++iter) {
107  size_type i = *iter;
108  fld_x [fld_i] = x[i];
109  fld_v [fld_i] = v[i];
110  }
111  do_stop_when_failed = true;
112  trace_macro("trace_move/ray_boundary...");
113  trace_ray_boundary (fld_x, fld_v, fld_dis_ie, fld_y, do_stop_when_failed);
114  trace_macro("trace_move/ray_boundary = "
115  << fld_x.dis_size() << "/" << x.dis_size() << " = "
116  << 1.0*fld_x.dis_size()/x.dis_size());
117  iter = failed.begin();
118  for (size_type fld_i = 0, fld_n = fld_x.size(); fld_i < fld_n; ++fld_i, ++iter) {
119  size_type i = *iter;
120  dis_ie[i] = fld_dis_ie [fld_i];
121  y[i] = fld_y [fld_i];
122  }
123 #ifdef TO_CLEAN
124  for (size_type i = 0, n = x.size(); i < n; i++) {
126  "trace_move: localization failed");
127  }
128 #endif // TO_CLEAN
129  trace_macro("trace_move done(2)");
130 }
131 #endif // _RHEOLEF_HAVE_MPI
132 template class geo_base_rep<Float,sequential>;
133 template class geo_rep<Float,sequential>;
134 #ifdef _RHEOLEF_HAVE_MPI
135 template class geo_base_rep<Float,distributed>;
136 template class geo_rep<Float,distributed>;
137 #endif // _RHEOLEF_HAVE_MPI
138 
139 } // namespace rheolef
140