00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030 #include "Utility/PAssert.h"
00031 #include "Utility/IpplInfo.h"
00032 #include "Field/BareField.h"
00033 #include "Field/BrickExpression.h"
00034 #include "Field/LField.h"
00035 #include "Field/Field.h"
00036 #include "Field/Assign.h"
00037 #include "Field/AssignDefs.h"
00038
00039
00040
00041
00042 template <unsigned Dim, class MFLOAT>
00043 void
00044 UniformCartesian<Dim,MFLOAT>::
00045 setup()
00046 {
00047 hasSpacingFields = false;
00048 FlCell = 0;
00049 FlVert = 0;
00050 VertSpacings = 0;
00051 CellSpacings = 0;
00052 volume = 0.0;
00053 }
00054
00055
00056
00057
00058 template <unsigned Dim, class MFLOAT>
00059 UniformCartesian<Dim,MFLOAT>::
00060 UniformCartesian(const NDIndex<Dim>& ndi)
00061 {
00062 setup();
00063 for (int d=0; d<Dim; d++) {
00064 gridSizes[d] = ndi[d].length();
00065 meshSpacing[d] = ndi[d].stride();
00066 origin(d) = ndi[d].first();
00067 }
00068 volume = 1.0;
00069 set_Dvc();
00070 }
00071
00072 template <unsigned Dim, class MFLOAT>
00073 UniformCartesian<Dim,MFLOAT>::
00074 UniformCartesian(const NDIndex<Dim>& ndi, MFLOAT* const delX)
00075 {
00076 setup();
00077 for (int d=0; d<Dim; d++) {
00078 gridSizes[d] = ndi[d].length();
00079 origin(d) = ndi[d].first();
00080 }
00081 set_meshSpacing(delX);
00082 }
00083
00084 template <unsigned Dim, class MFLOAT>
00085 UniformCartesian<Dim,MFLOAT>::
00086 UniformCartesian(const NDIndex<Dim>& ndi, MFLOAT* const delX,
00087 const Vektor<MFLOAT,Dim>& orig)
00088 {
00089 setup();
00090 for (int d=0; d<Dim; d++) {
00091 gridSizes[d] = ndi[d].length();
00092 }
00093 set_origin(orig);
00094 set_meshSpacing(delX);
00095 }
00096
00097
00098
00099
00100
00101 template <unsigned Dim, class MFLOAT>
00102 UniformCartesian<Dim,MFLOAT>::
00103 UniformCartesian(const Index& I)
00104 {
00105 PInsist(Dim==1,"Number of Index arguments does not match mesh dimension!!");
00106 setup();
00107 gridSizes[0] = I.length();
00108 meshSpacing[0] = I.stride();
00109 origin(0) = I.first();
00110
00111 volume = 1.0;
00112 set_Dvc();
00113 }
00114
00115 template <unsigned Dim, class MFLOAT>
00116 UniformCartesian<Dim,MFLOAT>::
00117 UniformCartesian(const Index& I, MFLOAT* const delX)
00118 {
00119 PInsist(Dim==1,"Number of Index arguments does not match mesh dimension!!");
00120 setup();
00121 gridSizes[0] = I.length();
00122 origin(0) = I.first();
00123
00124 set_meshSpacing(delX);
00125 }
00126
00127 template <unsigned Dim, class MFLOAT>
00128 UniformCartesian<Dim,MFLOAT>::
00129 UniformCartesian(const Index& I, MFLOAT* const delX,
00130 const Vektor<MFLOAT,Dim>& orig)
00131 {
00132 PInsist(Dim==1,"Number of Index arguments does not match mesh dimension!!");
00133 setup();
00134 gridSizes[0] = I.length();
00135 set_origin(orig);
00136 set_meshSpacing(delX);
00137 }
00138
00139
00140 template <unsigned Dim, class MFLOAT>
00141 UniformCartesian<Dim,MFLOAT>::
00142 UniformCartesian(const Index& I, const Index& J)
00143 {
00144 PInsist(Dim==2,"Number of Index arguments does not match mesh dimension!!");
00145 setup();
00146 gridSizes[0] = I.length();
00147 gridSizes[1] = J.length();
00148 meshSpacing[0] = I.stride();
00149 meshSpacing[1] = J.stride();
00150 origin(0) = I.first();
00151 origin(1) = J.first();
00152
00153 volume = 1.0;
00154 set_Dvc();
00155 }
00156
00157 template <unsigned Dim, class MFLOAT>
00158 UniformCartesian<Dim,MFLOAT>::
00159 UniformCartesian(const Index& I, const Index& J, MFLOAT* const delX)
00160 {
00161 PInsist(Dim==2,"Number of Index arguments does not match mesh dimension!!");
00162 setup();
00163 gridSizes[0] = I.length();
00164 gridSizes[1] = J.length();
00165 origin(0) = I.first();
00166 origin(1) = J.first();
00167 set_meshSpacing(delX);
00168 }
00169
00170 template <unsigned Dim, class MFLOAT>
00171 UniformCartesian<Dim,MFLOAT>::
00172 UniformCartesian(const Index& I, const Index& J, MFLOAT* const delX,
00173 const Vektor<MFLOAT,Dim>& orig)
00174 {
00175 PInsist(Dim==2,"Number of Index arguments does not match mesh dimension!!");
00176 setup();
00177 gridSizes[0] = I.length();
00178 gridSizes[1] = J.length();
00179 set_origin(orig);
00180 set_meshSpacing(delX);
00181 }
00182
00183
00184 template <unsigned Dim, class MFLOAT>
00185 UniformCartesian<Dim,MFLOAT>::
00186 UniformCartesian(const Index& I, const Index& J, const Index& K)
00187 {
00188 PInsist(Dim==3,"Number of Index arguments does not match mesh dimension!!");
00189 setup();
00190 gridSizes[0] = I.length();
00191 gridSizes[1] = J.length();
00192 gridSizes[2] = K.length();
00193 meshSpacing[0] = I.stride();
00194 meshSpacing[1] = J.stride();
00195 meshSpacing[2] = K.stride();
00196 origin(0) = I.first();
00197 origin(1) = J.first();
00198 origin(2) = K.first();
00199
00200 volume = 1.0;
00201 set_Dvc();
00202 }
00203
00204 template <unsigned Dim, class MFLOAT>
00205 UniformCartesian<Dim,MFLOAT>::
00206 UniformCartesian(const Index& I, const Index& J, const Index& K,
00207 MFLOAT* const delX)
00208 {
00209 PInsist(Dim==3,"Number of Index arguments does not match mesh dimension!!");
00210 setup();
00211 gridSizes[0] = I.length();
00212 gridSizes[1] = J.length();
00213 gridSizes[2] = K.length();
00214 origin(0) = I.first();
00215 origin(1) = J.first();
00216 origin(2) = K.first();
00217 set_meshSpacing(delX);
00218 }
00219
00220 template <unsigned Dim, class MFLOAT>
00221 UniformCartesian<Dim,MFLOAT>::
00222 UniformCartesian(const Index& I, const Index& J, const Index& K,
00223 MFLOAT* const delX, const Vektor<MFLOAT,Dim>& orig)
00224 {
00225 PInsist(Dim==3,"Number of Index arguments does not match mesh dimension!!");
00226 setup();
00227 gridSizes[0] = I.length();
00228 gridSizes[1] = J.length();
00229 gridSizes[2] = K.length();
00230 set_origin(orig);
00231 set_meshSpacing(delX);
00232 }
00233
00234
00235
00236
00237 template <unsigned Dim, class MFLOAT>
00238 void
00239 UniformCartesian<Dim,MFLOAT>::
00240 initialize(const NDIndex<Dim>& ndi)
00241 {
00242 setup();
00243 for (int d=0; d<Dim; d++) {
00244 gridSizes[d] = ndi[d].length();
00245 meshSpacing[d] = ndi[d].stride();
00246 origin(d) = ndi[d].first();
00247 }
00248 volume = 1.0;
00249 set_Dvc();
00250 }
00251
00252 template <unsigned Dim, class MFLOAT>
00253 void
00254 UniformCartesian<Dim,MFLOAT>::
00255 initialize(const NDIndex<Dim>& ndi, MFLOAT* const delX)
00256 {
00257 setup();
00258 for (int d=0; d<Dim; d++) {
00259 gridSizes[d] = ndi[d].length();
00260 origin(d) = ndi[d].first();
00261 }
00262 set_meshSpacing(delX);
00263 }
00264
00265 template <unsigned Dim, class MFLOAT>
00266 void
00267 UniformCartesian<Dim,MFLOAT>::
00268 initialize(const NDIndex<Dim>& ndi, MFLOAT* const delX,
00269 const Vektor<MFLOAT,Dim>& orig)
00270 {
00271 setup();
00272 for (int d=0; d<Dim; d++) {
00273 gridSizes[d] = ndi[d].length();
00274 }
00275 set_origin(orig);
00276 set_meshSpacing(delX);
00277 }
00278
00279
00280
00281
00282
00283 template <unsigned Dim, class MFLOAT>
00284 void
00285 UniformCartesian<Dim,MFLOAT>::
00286 initialize(const Index& I)
00287 {
00288 PInsist(Dim==1,"Number of Index arguments does not match mesh dimension!!");
00289 setup();
00290 gridSizes[0] = I.length();
00291 meshSpacing[0] = I.stride();
00292 origin(0) = I.first();
00293
00294 volume = 1.0;
00295 set_Dvc();
00296 }
00297
00298 template <unsigned Dim, class MFLOAT>
00299 void
00300 UniformCartesian<Dim,MFLOAT>::
00301 initialize(const Index& I, MFLOAT* const delX)
00302 {
00303 PInsist(Dim==1,"Number of Index arguments does not match mesh dimension!!");
00304 setup();
00305 gridSizes[0] = I.length();
00306 origin(0) = I.first();
00307
00308 set_meshSpacing(delX);
00309 }
00310
00311 template <unsigned Dim, class MFLOAT>
00312 void
00313 UniformCartesian<Dim,MFLOAT>::
00314 initialize(const Index& I, MFLOAT* const delX,
00315 const Vektor<MFLOAT,Dim>& orig)
00316 {
00317 PInsist(Dim==1,"Number of Index arguments does not match mesh dimension!!");
00318 setup();
00319 gridSizes[0] = I.length();
00320 set_origin(orig);
00321 set_meshSpacing(delX);
00322 }
00323
00324
00325 template <unsigned Dim, class MFLOAT>
00326 void
00327 UniformCartesian<Dim,MFLOAT>::
00328 initialize(const Index& I, const Index& J)
00329 {
00330 PInsist(Dim==2,"Number of Index arguments does not match mesh dimension!!");
00331 setup();
00332 gridSizes[0] = I.length();
00333 gridSizes[1] = J.length();
00334 meshSpacing[0] = I.stride();
00335 meshSpacing[1] = J.stride();
00336 origin(0) = I.first();
00337 origin(1) = J.first();
00338
00339 volume = 1.0;
00340 set_Dvc();
00341 }
00342
00343 template <unsigned Dim, class MFLOAT>
00344 void
00345 UniformCartesian<Dim,MFLOAT>::
00346 initialize(const Index& I, const Index& J, MFLOAT* const delX)
00347 {
00348 PInsist(Dim==2,"Number of Index arguments does not match mesh dimension!!");
00349 setup();
00350 gridSizes[0] = I.length();
00351 gridSizes[1] = J.length();
00352 origin(0) = I.first();
00353 origin(1) = J.first();
00354 set_meshSpacing(delX);
00355 }
00356
00357 template <unsigned Dim, class MFLOAT>
00358 void
00359 UniformCartesian<Dim,MFLOAT>::
00360 initialize(const Index& I, const Index& J, MFLOAT* const delX,
00361 const Vektor<MFLOAT,Dim>& orig)
00362 {
00363 PInsist(Dim==2,"Number of Index arguments does not match mesh dimension!!");
00364 setup();
00365 gridSizes[0] = I.length();
00366 gridSizes[1] = J.length();
00367 set_origin(orig);
00368 set_meshSpacing(delX);
00369 }
00370
00371
00372 template <unsigned Dim, class MFLOAT>
00373 void
00374 UniformCartesian<Dim,MFLOAT>::
00375 initialize(const Index& I, const Index& J, const Index& K)
00376 {
00377 PInsist(Dim==3,"Number of Index arguments does not match mesh dimension!!");
00378 setup();
00379 gridSizes[0] = I.length();
00380 gridSizes[1] = J.length();
00381 gridSizes[2] = K.length();
00382 meshSpacing[0] = I.stride();
00383 meshSpacing[1] = J.stride();
00384 meshSpacing[2] = K.stride();
00385 origin(0) = I.first();
00386 origin(1) = J.first();
00387 origin(2) = K.first();
00388
00389 volume = 1.0;
00390 set_Dvc();
00391 }
00392
00393 template <unsigned Dim, class MFLOAT>
00394 void
00395 UniformCartesian<Dim,MFLOAT>::
00396 initialize(const Index& I, const Index& J, const Index& K,
00397 MFLOAT* const delX)
00398 {
00399 PInsist(Dim==3,"Number of Index arguments does not match mesh dimension!!");
00400 setup();
00401 gridSizes[0] = I.length();
00402 gridSizes[1] = J.length();
00403 gridSizes[2] = K.length();
00404 origin(0) = I.first();
00405 origin(1) = J.first();
00406 origin(2) = K.first();
00407 set_meshSpacing(delX);
00408 }
00409
00410 template <unsigned Dim, class MFLOAT>
00411 void
00412 UniformCartesian<Dim,MFLOAT>::
00413 initialize(const Index& I, const Index& J, const Index& K,
00414 MFLOAT* const delX, const Vektor<MFLOAT,Dim>& orig)
00415 {
00416 PInsist(Dim==3,"Number of Index arguments does not match mesh dimension!!");
00417 setup();
00418 gridSizes[0] = I.length();
00419 gridSizes[1] = J.length();
00420 gridSizes[2] = K.length();
00421 set_origin(orig);
00422 set_meshSpacing(delX);
00423 }
00424
00425
00426
00427
00428
00429 template<unsigned Dim, class MFLOAT>
00430 void UniformCartesian<Dim,MFLOAT>::
00431 set_origin(const Vektor<MFLOAT,Dim>& o)
00432 {
00433 origin = o;
00434 this->notifyOfChange();
00435 }
00436
00437 template<unsigned Dim, class MFLOAT>
00438 Vektor<MFLOAT,Dim> UniformCartesian<Dim,MFLOAT>::
00439 get_origin() const
00440 {
00441 return origin;
00442 }
00443
00444
00445 template<unsigned Dim, class MFLOAT>
00446 void UniformCartesian<Dim,MFLOAT>::
00447 set_meshSpacing(MFLOAT* const del)
00448 {
00449 unsigned d;
00450 volume = 1.0;
00451 for (d=0; d<Dim; ++d) {
00452 meshSpacing[d] = del[d];
00453 volume *= del[d];
00454 }
00455 set_Dvc();
00456
00457 if (hasSpacingFields) storeSpacingFields();
00458 this->notifyOfChange();
00459 }
00460
00461 template<unsigned Dim, class MFLOAT>
00462 void UniformCartesian<Dim,MFLOAT>::
00463 set_Dvc()
00464 {
00465 unsigned d;
00466 MFLOAT coef = 1.0;
00467 for (d=1;d<Dim;++d) coef *= 0.5;
00468
00469 for (d=0;d<Dim;++d) {
00470 MFLOAT dvc = coef/meshSpacing[d];
00471 for (unsigned b=0; b<(1<<Dim); ++b) {
00472 int s = ( b&(1<<d) ) ? 1 : -1;
00473 Dvc[b][d] = s*dvc;
00474 }
00475 }
00476 }
00477
00478 template<unsigned Dim, class MFLOAT>
00479 MFLOAT UniformCartesian<Dim,MFLOAT>::
00480 get_meshSpacing(unsigned d) const
00481 {
00482 PAssert(d<Dim);
00483 MFLOAT ms = meshSpacing[d];
00484 return ms;
00485 }
00486
00487
00488 template<unsigned Dim, class MFLOAT>
00489 MFLOAT UniformCartesian<Dim,MFLOAT>::
00490 get_volume() const
00491 {
00492 return volume;
00493 }
00494
00496
00497
00498
00499
00500
00501 template<class T>
00502 struct OpUMeshExtrapolate
00503 {
00504 OpUMeshExtrapolate(T& o, T& s) : Offset(o), Slope(s) {}
00505 T Offset, Slope;
00506 };
00507
00508 template<class T>
00509 void PETE_apply(OpUMeshExtrapolate<T> e, T& a, T b)
00510 {
00511 a = b*e.Slope+e.Offset;
00512 }
00513
00515
00516
00517
00518
00519 template<unsigned Dim, class MFLOAT>
00520 void UniformCartesian<Dim,MFLOAT>::
00521 storeSpacingFields()
00522 {
00523
00524 e_dim_tag et[Dim];
00525 for (int d=0; d<Dim; d++) et[d] = PARALLEL;
00526 storeSpacingFields(et, -1);
00527 }
00528
00529 template<unsigned Dim, class MFLOAT>
00530 void UniformCartesian<Dim,MFLOAT>::
00531 storeSpacingFields(e_dim_tag p1, int vnodes)
00532 {
00533 e_dim_tag et[1];
00534 et[0] = p1;
00535 storeSpacingFields(et, vnodes);
00536 }
00537
00538 template<unsigned Dim, class MFLOAT>
00539 void UniformCartesian<Dim,MFLOAT>::
00540 storeSpacingFields(e_dim_tag p1, e_dim_tag p2, int vnodes)
00541 {
00542 e_dim_tag et[2];
00543 et[0] = p1;
00544 et[1] = p2;
00545 storeSpacingFields(et, vnodes);
00546 }
00547
00548 template<unsigned Dim, class MFLOAT>
00549 void UniformCartesian<Dim,MFLOAT>::
00550 storeSpacingFields(e_dim_tag p1, e_dim_tag p2, e_dim_tag p3, int vnodes)
00551 {
00552 e_dim_tag et[3];
00553 et[0] = p1;
00554 et[1] = p2;
00555 et[2] = p3;
00556 storeSpacingFields(et, vnodes);
00557 }
00558
00559 template<unsigned Dim, class MFLOAT>
00560 void UniformCartesian<Dim,MFLOAT>::
00561 storeSpacingFields(e_dim_tag* et, int vnodes)
00562 {
00563
00564 NDIndex<Dim> cells, verts;
00565 int d;
00566 for (d=0; d<Dim; d++) {
00567 cells[d] = Index(gridSizes[d]-1);
00568 verts[d] = Index(gridSizes[d]);
00569 }
00570 if (!hasSpacingFields) {
00571
00572 FlCell = new FieldLayout<Dim>(cells, et, vnodes);
00573
00574
00575
00576 VertSpacings =
00577 new BareField<Vektor<MFLOAT,Dim>,Dim>(*FlCell,GuardCellSizes<Dim>(1));
00578
00579 FlVert =
00580 new FieldLayout<Dim>(verts, et, vnodes);
00581
00582 CellSpacings =
00583 new BareField<Vektor<MFLOAT,Dim>,Dim>(*FlVert,GuardCellSizes<Dim>(1));
00584 }
00585 BareField<Vektor<MFLOAT,Dim>,Dim>& vertSpacings = *VertSpacings;
00586 Vektor<MFLOAT,Dim> vertexSpacing;
00587 for (d=0; d<Dim; d++)
00588 vertexSpacing[d] = meshSpacing[d];
00589 vertSpacings = vertexSpacing;
00590
00591
00592
00593
00594
00595 vertSpacings.fillGuardCells();
00596
00597
00598
00599
00600 Vektor<MFLOAT,Dim> v0,v1; v0 = 0.0; v1 = 1.0;
00601 int face;
00602 typedef Vektor<MFLOAT,Dim> T;
00603 typename BareField<T,Dim>::iterator_if vfill_i;
00604 int voffset;
00605
00606 for (face=0; face < 2*Dim; face++) {
00607
00608 NDIndex<Dim> vSlab = AddGuardCells(cells,vertSpacings.getGuardCellSizes());
00609
00610 d = face/2;
00611
00612
00613
00614
00615 if ( face & 1 ) {
00616 vSlab[d] = Index(cells[d].max() + 1,
00617 cells[d].max() + vertSpacings.rightGuard(d));
00618 } else {
00619 vSlab[d] = Index(cells[d].min() - vertSpacings.leftGuard(d),
00620 cells[d].min() - 1);
00621 }
00622
00623
00624
00625 if ( face & 1 ) {
00626 voffset = 2*cells[d].max() + 1 - 1;
00627 } else {
00628 voffset = 2*cells[d].min() - 1 + 1;
00629 }
00630
00631
00632 for (vfill_i=vertSpacings.begin_if();
00633 vfill_i!=vertSpacings.end_if(); ++vfill_i)
00634 {
00635
00636
00637 LField<T,Dim> &fill = *(*vfill_i).second;
00638
00639 const NDIndex<Dim> &fill_alloc = fill.getAllocated();
00640
00641
00642
00643
00644 if ( vSlab.touches( fill_alloc ) )
00645 {
00646
00647 NDIndex<Dim> dest = vSlab.intersect( fill_alloc );
00648
00649
00650
00651
00652
00653
00654 NDIndex<Dim> src = dest;
00655
00656
00657 src[d] = voffset - src[d];
00658
00659
00660
00661 typename BareField<T,Dim>::iterator_if from_i;
00662 for (from_i=vertSpacings.begin_if();
00663 from_i!=vertSpacings.end_if(); ++from_i)
00664 {
00665
00666 LField<T,Dim> &from = *(*from_i).second;
00667 const NDIndex<Dim> &from_owned = from.getOwned();
00668 const NDIndex<Dim> &from_alloc = from.getAllocated();
00669
00670 if ( src.touches( from_owned ) )
00671 {
00672 NDIndex<Dim> from_it = src.intersect( from_alloc );
00673 NDIndex<Dim> vfill_it = dest.plugBase( from_it );
00674
00675 typedef typename LField<T,Dim>::iterator LFI;
00676 LFI lhs = fill.begin(vfill_it);
00677 LFI rhs = from.begin(from_it);
00678
00679 BrickExpression<Dim,LFI,LFI,OpUMeshExtrapolate<T> >
00680 (lhs,rhs,OpUMeshExtrapolate<T>(v0,v1)).apply();
00681 }
00682 }
00683 }
00684 }
00685
00686 }
00687
00688
00689
00690
00691
00692 BareField<Vektor<MFLOAT,Dim>,Dim>& cellSpacings = *CellSpacings;
00693 cellSpacings = vertexSpacing;
00694
00695 hasSpacingFields = true;
00696 }
00697
00698
00699
00700
00701
00702
00703
00704
00705
00706 template<unsigned Dim, class MFLOAT>
00707 void UniformCartesian<Dim,MFLOAT>::
00708 storeSpacingFields(e_dim_tag p1,
00709 unsigned vnodes1,
00710 bool recurse,
00711 int vnodes) {
00712 e_dim_tag et[1];
00713 et[0] = p1;
00714 unsigned vnodesPerDirection[Dim];
00715 vnodesPerDirection[0] = vnodes1;
00716 storeSpacingFields(et, vnodesPerDirection, recurse, vnodes);
00717 }
00718
00719 template<unsigned Dim, class MFLOAT>
00720 void UniformCartesian<Dim,MFLOAT>::
00721 storeSpacingFields(e_dim_tag p1, e_dim_tag p2,
00722 unsigned vnodes1, unsigned vnodes2,
00723 bool recurse,int vnodes) {
00724 e_dim_tag et[2];
00725 et[0] = p1;
00726 et[1] = p2;
00727 unsigned vnodesPerDirection[Dim];
00728 vnodesPerDirection[0] = vnodes1;
00729 vnodesPerDirection[1] = vnodes2;
00730 storeSpacingFields(et, vnodesPerDirection, recurse, vnodes);
00731 }
00732
00733 template<unsigned Dim, class MFLOAT>
00734 void UniformCartesian<Dim,MFLOAT>::
00735 storeSpacingFields(e_dim_tag p1, e_dim_tag p2, e_dim_tag p3,
00736 unsigned vnodes1, unsigned vnodes2, unsigned vnodes3,
00737 bool recurse, int vnodes) {
00738 e_dim_tag et[3];
00739 et[0] = p1;
00740 et[1] = p2;
00741 et[2] = p3;
00742 unsigned vnodesPerDirection[Dim];
00743 vnodesPerDirection[0] = vnodes1;
00744 vnodesPerDirection[1] = vnodes2;
00745 vnodesPerDirection[2] = vnodes3;
00746 storeSpacingFields(et, vnodesPerDirection, recurse, vnodes);
00747 }
00748
00749
00750
00751
00752
00753 template<unsigned Dim, class MFLOAT>
00754 void UniformCartesian<Dim,MFLOAT>::
00755 storeSpacingFields(e_dim_tag *p,
00756 unsigned* vnodesPerDirection,
00757 bool recurse, int vnodes)
00758 {
00759
00760 NDIndex<Dim> cells, verts;
00761 int d;
00762 for (d=0; d<Dim; d++) {
00763 cells[d] = Index(gridSizes[d]-1);
00764 verts[d] = Index(gridSizes[d]);
00765 }
00766 if (!hasSpacingFields) {
00767
00768 FlCell =
00769 new FieldLayout<Dim>(cells, p, vnodesPerDirection, recurse, vnodes);
00770
00771
00772
00773 VertSpacings =
00774 new BareField<Vektor<MFLOAT,Dim>,Dim>(*FlCell,GuardCellSizes<Dim>(1));
00775
00776 FlVert =
00777 new FieldLayout<Dim>(verts, p, vnodesPerDirection, recurse, vnodes);
00778
00779 CellSpacings =
00780 new BareField<Vektor<MFLOAT,Dim>,Dim>(*FlVert,GuardCellSizes<Dim>(1));
00781 }
00782 BareField<Vektor<MFLOAT,Dim>,Dim>& vertSpacings = *VertSpacings;
00783 Vektor<MFLOAT,Dim> vertexSpacing;
00784 for (d=0; d<Dim; d++)
00785 vertexSpacing[d] = meshSpacing[d];
00786 vertSpacings = vertexSpacing;
00787
00788
00789
00790
00791
00792 vertSpacings.fillGuardCells();
00793
00794
00795
00796
00797 Vektor<MFLOAT,Dim> v0,v1; v0 = 0.0; v1 = 1.0;
00798 int face;
00799 typedef Vektor<MFLOAT,Dim> T;
00800 typename BareField<T,Dim>::iterator_if vfill_i;
00801 int voffset;
00802
00803 for (face=0; face < 2*Dim; face++) {
00804
00805 NDIndex<Dim> vSlab = AddGuardCells(cells,vertSpacings.getGuardCellSizes());
00806
00807 d = face/2;
00808
00809
00810
00811
00812 if ( face & 1 ) {
00813 vSlab[d] = Index(cells[d].max() + 1,
00814 cells[d].max() + vertSpacings.rightGuard(d));
00815 } else {
00816 vSlab[d] = Index(cells[d].min() - vertSpacings.leftGuard(d),
00817 cells[d].min() - 1);
00818 }
00819
00820
00821
00822 if ( face & 1 ) {
00823 voffset = 2*cells[d].max() + 1 - 1;
00824 } else {
00825 voffset = 2*cells[d].min() - 1 + 1;
00826 }
00827
00828
00829 for (vfill_i=vertSpacings.begin_if();
00830 vfill_i!=vertSpacings.end_if(); ++vfill_i)
00831 {
00832
00833
00834 LField<T,Dim> &fill = *(*vfill_i).second;
00835
00836 const NDIndex<Dim> &fill_alloc = fill.getAllocated();
00837
00838
00839
00840
00841 if ( vSlab.touches( fill_alloc ) )
00842 {
00843
00844 NDIndex<Dim> dest = vSlab.intersect( fill_alloc );
00845
00846
00847
00848
00849
00850
00851 NDIndex<Dim> src = dest;
00852
00853
00854 src[d] = voffset - src[d];
00855
00856
00857
00858 typename BareField<T,Dim>::iterator_if from_i;
00859 for (from_i=vertSpacings.begin_if();
00860 from_i!=vertSpacings.end_if(); ++from_i)
00861 {
00862
00863 LField<T,Dim> &from = *(*from_i).second;
00864 const NDIndex<Dim> &from_owned = from.getOwned();
00865 const NDIndex<Dim> &from_alloc = from.getAllocated();
00866
00867 if ( src.touches( from_owned ) )
00868 {
00869 NDIndex<Dim> from_it = src.intersect( from_alloc );
00870 NDIndex<Dim> vfill_it = dest.plugBase( from_it );
00871
00872 typedef typename LField<T,Dim>::iterator LFI;
00873 LFI lhs = fill.begin(vfill_it);
00874 LFI rhs = from.begin(from_it);
00875
00876 BrickExpression<Dim,LFI,LFI,OpUMeshExtrapolate<T> >
00877 (lhs,rhs,OpUMeshExtrapolate<T>(v0,v1)).apply();
00878 }
00879 }
00880 }
00881 }
00882
00883 }
00884
00885
00886
00887
00888
00889 BareField<Vektor<MFLOAT,Dim>,Dim>& cellSpacings = *CellSpacings;
00890 cellSpacings = vertexSpacing;
00891
00892 hasSpacingFields = true;
00893 }
00894
00895
00896
00897
00898
00899 template< unsigned Dim, class MFLOAT >
00900 void
00901 UniformCartesian<Dim,MFLOAT>::
00902 print(ostream& out)
00903 {
00904 out << "======UniformCartesian<" << Dim << ",MFLOAT>==begin======" << endl;
00905 int d;
00906 for (d=0; d < Dim; d++)
00907 out << "gridSizes[" << d << "] = " << gridSizes[d] << endl;
00908 out << "origin = " << origin << endl;
00909 for (d=0; d < Dim; d++)
00910 out << "meshSpacing[" << d << "] = " << meshSpacing[d] << endl;
00911 for (d=0; d < (1<<Dim); d++)
00912 out << "Dvc[" << d << "] = " << Dvc[d] << endl;
00913 out << "cell volume = " << volume << endl;
00914 out << "======UniformCartesian<" << Dim << ",MFLOAT>==end========" << endl;
00915 }
00916
00917
00918
00919
00920
00921
00922 template <unsigned Dim, class MFLOAT>
00923 MFLOAT
00924 UniformCartesian<Dim,MFLOAT>::
00925 getCellVolume(const NDIndex<Dim>& ndi) const
00926 {
00927 int d;
00928 for (d=0; d<Dim; d++)
00929 if (ndi[d].length() != 1)
00930 ERRORMSG("UniformCartesian::getCellVolume() error: arg is not a NDIndex"
00931 << "specifying a single element" << endl);
00932 return volume;
00933 }
00934
00935 template <unsigned Dim, class MFLOAT>
00936 Field<MFLOAT,Dim,UniformCartesian<Dim,MFLOAT>,Cell>&
00937 UniformCartesian<Dim,MFLOAT>::
00938 getCellVolumeField(Field<MFLOAT,Dim,UniformCartesian<Dim,MFLOAT>,Cell>&
00939 volumes) const
00940 {
00941 volumes = volume;
00942 return volumes;
00943 }
00944
00945 template <unsigned Dim, class MFLOAT>
00946 MFLOAT
00947 UniformCartesian<Dim,MFLOAT>::
00948 getVertRangeVolume(const NDIndex<Dim>& ndi) const
00949 {
00950
00951 Vektor<MFLOAT,Dim> v0, v1;
00952 NDIndex<Dim> ndi0, ndi1;
00953 int d, i0, i1;
00954 for (d=0; d<Dim; d++) {
00955 i0 = ndi[d].first();
00956 i1 = ndi[d].last();
00957 ndi0[d] = Index(i0,i0,1);
00958 ndi1[d] = Index(i1,i1,1);
00959 }
00960 v0 = getVertexPosition(ndi0);
00961 v1 = getVertexPosition(ndi1);
00962
00963 MFLOAT volume = 1.0;
00964 for (d=0; d<Dim; d++) volume *= abs(v1(d) - v0(d));
00965 return volume;
00966 }
00967
00968 template <unsigned Dim, class MFLOAT>
00969 MFLOAT
00970 UniformCartesian<Dim,MFLOAT>::
00971 getCellRangeVolume(const NDIndex<Dim>& ndi) const
00972 {
00973
00974 Vektor<MFLOAT,Dim> v0, v1;
00975 NDIndex<Dim> ndi0, ndi1;
00976 int d, i0, i1;
00977 for (d=0; d<Dim; d++) {
00978 i0 = ndi[d].first();
00979 i1 = ndi[d].last() + 1;
00980 ndi0[d] = Index(i0,i0,1);
00981 ndi1[d] = Index(i1,i1,1);
00982 }
00983 v0 = getVertexPosition(ndi0);
00984 v1 = getVertexPosition(ndi1);
00985
00986 MFLOAT volume = 1.0;
00987 for (d=0; d<Dim; d++) volume *= abs(v1(d) - v0(d));
00988 return volume;
00989 }
00990
00991
00992 template <unsigned Dim, class MFLOAT>
00993 NDIndex<Dim>
00994 UniformCartesian<Dim,MFLOAT>::
00995 getNearestVertex(const Vektor<MFLOAT,Dim>& x) const
00996 {
00997
00998
00999 NDIndex<Dim> ndi;
01000 int d, i;
01001 for (d=0; d<Dim; d++) {
01002 i = (int)((x(d) - origin(d))/meshSpacing[d] + 0.5);
01003 if (x(d) >= origin(d))
01004 ndi[d] = Index(i,i);
01005 else
01006 ndi[d] = Index(i-1,i-1);
01007 }
01008 return ndi;
01009 }
01010
01011 template <unsigned Dim, class MFLOAT>
01012 NDIndex<Dim>
01013 UniformCartesian<Dim,MFLOAT>::
01014 getVertexBelow(const Vektor<MFLOAT,Dim>& x) const
01015 {
01016
01017
01018 NDIndex<Dim> ndi;
01019 int d, i;
01020 for (d=0; d<Dim; d++) {
01021 i = (int)((x(d) - origin(d))/meshSpacing[d]);
01022 if (x(d) >= origin(d))
01023 ndi[d] = Index(i,i);
01024 else
01025 ndi[d] = Index(i-1,i-1);
01026 }
01027 return ndi;
01028 }
01029
01030 template <unsigned Dim, class MFLOAT>
01031 Vektor<MFLOAT,Dim>
01032 UniformCartesian<Dim,MFLOAT>::
01033 getVertexPosition(const NDIndex<Dim>& ndi) const
01034 {
01035 int d;
01036 for (d=0; d<Dim; d++) {
01037 if (ndi[d].length() != 1)
01038 ERRORMSG("UniformCartesian::getVertexPosition() error: arg is not a"
01039 << " NDIndex specifying a single element" << endl);
01040 }
01041
01042 Vektor<MFLOAT,Dim> vertexPosition;
01043 for (d=0; d<Dim; d++)
01044 vertexPosition(d) = ndi[d].first()*meshSpacing[d] + origin(d);
01045 return vertexPosition;
01046 }
01047
01048 template <unsigned Dim, class MFLOAT>
01049 Field<Vektor<MFLOAT,Dim>,Dim,UniformCartesian<Dim,MFLOAT>,Vert>&
01050 UniformCartesian<Dim,MFLOAT>::
01051 getVertexPositionField(Field<Vektor<MFLOAT,Dim>,Dim,
01052 UniformCartesian<Dim,MFLOAT>,Vert>& vertexPositions) const
01053 {
01054 int d;
01055 int currentLocation[Dim];
01056 Vektor<MFLOAT,Dim> vertexPosition;
01057 vertexPositions.Uncompress();
01058 typename Field<Vektor<MFLOAT,Dim>,Dim,UniformCartesian<Dim,MFLOAT>,Vert>::iterator fi,
01059 fi_end = vertexPositions.end();
01060 for (fi = vertexPositions.begin(); fi != fi_end; ++fi) {
01061 fi.GetCurrentLocation(currentLocation);
01062 for (d=0; d<Dim; d++)
01063 vertexPosition(d) = origin(d) + currentLocation[d]*meshSpacing[d];
01064 *fi = vertexPosition;
01065 }
01066 return vertexPositions;
01067 }
01068
01069
01070 template <unsigned Dim, class MFLOAT>
01071 Vektor<MFLOAT,Dim>
01072 UniformCartesian<Dim,MFLOAT>::
01073 getCellPosition(const NDIndex<Dim>& ndi) const
01074 {
01075 int d;
01076 for (d=0; d<Dim; d++) {
01077 if (ndi[d].length() != 1)
01078 ERRORMSG("UniformCartesian::getCellPosition() error: arg is not a"
01079 << " NDIndex specifying a single element" << endl);
01080 }
01081
01082 Vektor<MFLOAT,Dim> cellPosition;
01083 for (d=0; d<Dim; d++)
01084 cellPosition(d) = (ndi[d].first()+0.5)*meshSpacing[d] + origin(d);
01085 return cellPosition;
01086 }
01087
01088 template <unsigned Dim, class MFLOAT>
01089 Field<Vektor<MFLOAT,Dim>,Dim,UniformCartesian<Dim,MFLOAT>,Cell>&
01090 UniformCartesian<Dim,MFLOAT>::
01091 getCellPositionField(Field<Vektor<MFLOAT,Dim>,Dim,
01092 UniformCartesian<Dim,MFLOAT>,Cell>& cellPositions) const
01093 {
01094 int d;
01095 int currentLocation[Dim];
01096 Vektor<MFLOAT,Dim> cellPosition;
01097 cellPositions.Uncompress();
01098 typename Field<Vektor<MFLOAT,Dim>,Dim,UniformCartesian<Dim,MFLOAT>,Cell>::iterator fi,
01099 fi_end = cellPositions.end();
01100 for (fi = cellPositions.begin(); fi != fi_end; ++fi) {
01101 fi.GetCurrentLocation(currentLocation);
01102 for (d=0; d<Dim; d++)
01103 cellPosition(d) = origin(d) + (currentLocation[d]+0.5)*meshSpacing[d];
01104 *fi = cellPosition;
01105 }
01106 return cellPositions;
01107 }
01108
01109
01110 template <unsigned Dim, class MFLOAT>
01111 Vektor<MFLOAT,Dim>
01112 UniformCartesian<Dim,MFLOAT>::
01113 getDeltaVertex(const NDIndex<Dim>& ndi) const
01114 {
01115
01116 Vektor<MFLOAT,Dim> vertexVertexSpacing;
01117 for (int d=0; d<Dim; d++)
01118 vertexVertexSpacing[d] = meshSpacing[d] * ndi[d].length();
01119 return vertexVertexSpacing;
01120 }
01121
01122
01123 template <unsigned Dim, class MFLOAT>
01124 Field<Vektor<MFLOAT,Dim>,Dim,UniformCartesian<Dim,MFLOAT>,Cell>&
01125 UniformCartesian<Dim,MFLOAT>::
01126 getDeltaVertexField(Field<Vektor<MFLOAT,Dim>,Dim,
01127 UniformCartesian<Dim,MFLOAT>,Cell>& vertexSpacings) const
01128 {
01129 Vektor<MFLOAT,Dim> vertexVertexSpacing;
01130 int d;
01131 for (d=0; d<Dim; d++) vertexVertexSpacing(d) = meshSpacing[d];
01132 vertexSpacings = vertexVertexSpacing;
01133 return vertexSpacings;
01134 }
01135
01136
01137 template <unsigned Dim, class MFLOAT>
01138 Vektor<MFLOAT,Dim>
01139 UniformCartesian<Dim,MFLOAT>::
01140 getDeltaCell(const NDIndex<Dim>& ndi) const
01141 {
01142
01143 Vektor<MFLOAT,Dim> cellCellSpacing;
01144 for (int d=0; d<Dim; d++)
01145 cellCellSpacing[d] = meshSpacing[d] * ndi[d].length();
01146 return cellCellSpacing;
01147 }
01148
01149
01150 template <unsigned Dim, class MFLOAT>
01151 Field<Vektor<MFLOAT,Dim>,Dim,UniformCartesian<Dim,MFLOAT>,Vert>&
01152 UniformCartesian<Dim,MFLOAT>::
01153 getDeltaCellField(Field<Vektor<MFLOAT,Dim>,Dim,
01154 UniformCartesian<Dim,MFLOAT>,Vert>& cellSpacings) const
01155 {
01156 Vektor<MFLOAT,Dim> cellCellSpacing;
01157 int d;
01158 for (d=0; d<Dim; d++) cellCellSpacing(d) = meshSpacing[d];
01159 cellSpacings = cellCellSpacing;
01160 return cellSpacings;
01161 }
01162
01163 template <unsigned Dim, class MFLOAT>
01164 Vektor<MFLOAT,Dim>*
01165 UniformCartesian<Dim,MFLOAT>::
01166 getSurfaceNormals(const NDIndex<Dim>& ndi) const
01167 {
01168 Vektor<MFLOAT,Dim>* surfaceNormals = new Vektor<MFLOAT,Dim>[2*Dim];
01169 int d, i;
01170 for (d=0; d<Dim; d++) {
01171 for (i=0; i<Dim; i++) {
01172 surfaceNormals[2*d](i) = 0.0;
01173 surfaceNormals[2*d+1](i) = 0.0;
01174 }
01175 surfaceNormals[2*d](d) = -1.0;
01176 surfaceNormals[2*d+1](d) = 1.0;
01177 }
01178 return surfaceNormals;
01179 }
01180
01181 template <unsigned Dim, class MFLOAT>
01182 void
01183 UniformCartesian<Dim,MFLOAT>::
01184 getSurfaceNormalFields(Field<Vektor<MFLOAT,Dim>, Dim,
01185 UniformCartesian<Dim,MFLOAT>,Cell>**
01186 surfaceNormalsFields ) const
01187 {
01188 Vektor<MFLOAT,Dim>* surfaceNormals = new Vektor<MFLOAT,Dim>[2*Dim];
01189 int d, i;
01190 for (d=0; d<Dim; d++) {
01191 for (i=0; i<Dim; i++) {
01192 surfaceNormals[2*d](i) = 0.0;
01193 surfaceNormals[2*d+1](i) = 0.0;
01194 }
01195 surfaceNormals[2*d](d) = -1.0;
01196 surfaceNormals[2*d+1](d) = 1.0;
01197 }
01198 for (d=0; d<2*Dim; d++) assign((*(surfaceNormalsFields[d])),
01199 surfaceNormals[d]);
01200
01201 }
01202
01203
01204
01205
01206
01207 template <unsigned Dim, class MFLOAT>
01208 Vektor<MFLOAT,Dim>
01209 UniformCartesian<Dim,MFLOAT>::
01210 getSurfaceNormal(const NDIndex<Dim>& ndi, unsigned face) const
01211 {
01212 Vektor<MFLOAT,Dim> surfaceNormal;
01213 unsigned int d;
01214
01215
01216
01217
01218 if ( face & 1 ) {
01219 for (d=0; d<Dim; d++) {
01220 if ((face/2) == d) {
01221 surfaceNormal(face) = -1.0;
01222 } else {
01223 surfaceNormal(face) = 0.0;
01224 }
01225 }
01226 } else {
01227 for (d=0; d<Dim; d++) {
01228 if ((face/2) == d) {
01229 surfaceNormal(face) = 1.0;
01230 } else {
01231 surfaceNormal(face) = 0.0;
01232 }
01233 }
01234 }
01235 return surfaceNormal;
01236 }
01237
01238 template <unsigned Dim, class MFLOAT>
01239 Field<Vektor<MFLOAT,Dim>,Dim,UniformCartesian<Dim,MFLOAT>,Cell>&
01240 UniformCartesian<Dim,MFLOAT>::
01241 getSurfaceNormalField(Field<Vektor<MFLOAT,Dim>, Dim,
01242 UniformCartesian<Dim,MFLOAT>,Cell>& surfaceNormalField,
01243 unsigned face) const
01244 {
01245 Vektor<MFLOAT,Dim> surfaceNormal;
01246 unsigned int d;
01247
01248
01249
01250
01251 if ( face & 1 ) {
01252 for (d=0; d<Dim; d++) {
01253 if ((face/2) == d) {
01254 surfaceNormal(face) = -1.0;
01255 } else {
01256 surfaceNormal(face) = 0.0;
01257 }
01258 }
01259 } else {
01260 for (d=0; d<Dim; d++) {
01261 if ((face/2) == d) {
01262 surfaceNormal(face) = 1.0;
01263 } else {
01264 surfaceNormal(face) = 0.0;
01265 }
01266 }
01267 }
01268 surfaceNormalField = surfaceNormal;
01269 return surfaceNormalField;
01270 }
01271
01272
01273
01274
01275
01276
01277
01278
01279
01280
01281
01282
01283
01284
01285 template < class T, class MFLOAT >
01286 Field<T,1U,UniformCartesian<1U,MFLOAT>,Cell>&
01287 Div(Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& x,
01288 Field<T,1U,UniformCartesian<1U,MFLOAT>,Cell>& r)
01289 {
01290 const NDIndex<1U>& domain = r.getDomain();
01291 Index I = domain[0];
01292
01293 assign( r[I] ,
01294 dot(x[I ], x.get_mesh().Dvc[0]) +
01295 dot(x[I+1], x.get_mesh().Dvc[1]));
01296 return r;
01297 }
01298
01299 template < class T, class MFLOAT >
01300 Field<T,2U,UniformCartesian<2U,MFLOAT>,Cell>&
01301 Div(Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& x,
01302 Field<T,2U,UniformCartesian<2U,MFLOAT>,Cell>& r)
01303 {
01304 const NDIndex<2U>& domain = r.getDomain();
01305 Index I = domain[0];
01306 Index J = domain[1];
01307
01308 assign( r[I][J] ,
01309 dot(x[I ][J ], x.get_mesh().Dvc[0]) +
01310 dot(x[I+1][J ], x.get_mesh().Dvc[1]) +
01311 dot(x[I ][J+1], x.get_mesh().Dvc[2]) +
01312 dot(x[I+1][J+1], x.get_mesh().Dvc[3]));
01313 return r;
01314 }
01315
01316 template < class T, class MFLOAT >
01317 Field<T,3U,UniformCartesian<3U,MFLOAT>,Cell>&
01318 Div(Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& x,
01319 Field<T,3U,UniformCartesian<3U,MFLOAT>,Cell>& r)
01320 {
01321 const NDIndex<3U>& domain = r.getDomain();
01322 Index I = domain[0];
01323 Index J = domain[1];
01324 Index K = domain[2];
01325
01326 assign( r[I][J][K] ,
01327 dot(x[I ][J ][K ], x.get_mesh().Dvc[0]) +
01328 dot(x[I+1][J ][K ], x.get_mesh().Dvc[1]) +
01329 dot(x[I ][J+1][K ], x.get_mesh().Dvc[2]) +
01330 dot(x[I+1][J+1][K ], x.get_mesh().Dvc[3]) +
01331 dot(x[I ][J ][K+1], x.get_mesh().Dvc[4]) +
01332 dot(x[I+1][J ][K+1], x.get_mesh().Dvc[5]) +
01333 dot(x[I ][J+1][K+1], x.get_mesh().Dvc[6]) +
01334 dot(x[I+1][J+1][K+1], x.get_mesh().Dvc[7]));
01335 return r;
01336 }
01337
01338
01339
01340 template < class T, class MFLOAT >
01341 Field<T,1U,UniformCartesian<1U,MFLOAT>,Vert>&
01342 Div(Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& x,
01343 Field<T,1U,UniformCartesian<1U,MFLOAT>,Vert>& r)
01344 {
01345 const NDIndex<1U>& domain = r.getDomain();
01346 Index I = domain[0];
01347
01348 assign( r[I] ,
01349 dot(x[I-1], x.get_mesh().Dvc[0]) +
01350 dot(x[I ], x.get_mesh().Dvc[1]));
01351 return r;
01352 }
01353
01354
01355 template < class T, class MFLOAT >
01356 Field<T,2U,UniformCartesian<2U,MFLOAT>,Vert>&
01357 Div(Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& x,
01358 Field<T,2U,UniformCartesian<2U,MFLOAT>,Vert>& r)
01359 {
01360 const NDIndex<2U>& domain = r.getDomain();
01361 Index I = domain[0];
01362 Index J = domain[1];
01363
01364 assign( r[I][J] ,
01365 dot(x[I-1][J-1], x.get_mesh().Dvc[0]) +
01366 dot(x[I ][J-1], x.get_mesh().Dvc[1]) +
01367 dot(x[I-1][J ], x.get_mesh().Dvc[2]) +
01368 dot(x[I ][J ], x.get_mesh().Dvc[3]));
01369 return r;
01370 }
01371
01372 template < class T, class MFLOAT >
01373 Field<T,3U,UniformCartesian<3U,MFLOAT>,Vert>&
01374 Div(Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& x,
01375 Field<T,3U,UniformCartesian<3U,MFLOAT>,Vert>& r)
01376 {
01377 const NDIndex<3U>& domain = r.getDomain();
01378 Index I = domain[0];
01379 Index J = domain[1];
01380 Index K = domain[2];
01381
01382 assign( r[I][J][K] ,
01383 dot(x[I-1][J-1][K-1], x.get_mesh().Dvc[0]) +
01384 dot(x[I ][J-1][K-1], x.get_mesh().Dvc[1]) +
01385 dot(x[I-1][J ][K-1], x.get_mesh().Dvc[2]) +
01386 dot(x[I ][J ][K-1], x.get_mesh().Dvc[3]) +
01387 dot(x[I-1][J-1][K ], x.get_mesh().Dvc[4]) +
01388 dot(x[I ][J-1][K ], x.get_mesh().Dvc[5]) +
01389 dot(x[I-1][J ][K ], x.get_mesh().Dvc[6]) +
01390 dot(x[I ][J ][K ], x.get_mesh().Dvc[7]));
01391 return r;
01392 }
01393
01394
01395
01396 template < class T, class MFLOAT >
01397 Field<T,1U,UniformCartesian<1U,MFLOAT>,Vert>&
01398 Div(Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& x,
01399 Field<T,1U,UniformCartesian<1U,MFLOAT>,Vert>& r)
01400 {
01401 const NDIndex<1U>& domain = r.getDomain();
01402 Index I = domain[0];
01403 Vektor<T,1U> idx;
01404 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01405
01406 assign( r[I] , dot( idx , (x[I+1] - x[I-1]) ) );
01407 return r;
01408 }
01409
01410 template < class T, class MFLOAT >
01411 Field<T,2U,UniformCartesian<2U,MFLOAT>,Vert>&
01412 Div(Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& x,
01413 Field<T,2U,UniformCartesian<2U,MFLOAT>,Vert>& r)
01414 {
01415 const NDIndex<2U>& domain = r.getDomain();
01416 Index I = domain[0];
01417 Index J = domain[1];
01418 Vektor<T,2U> idx,idy;
01419 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01420 idx[1] = 0.0;
01421 idy[0] = 0.0;
01422 idy[1] = 0.5/x.get_mesh().get_meshSpacing(1);
01423
01424 assign( r[I][J] ,
01425 dot( idx , (x[I+1][J ] - x[I-1][J ])) +
01426 dot( idy , (x[I ][J+1] - x[I ][J-1])) );
01427 return r;
01428 }
01429
01430 template < class T, class MFLOAT >
01431 Field<T,3U,UniformCartesian<3U,MFLOAT>,Vert>&
01432 Div(Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& x,
01433 Field<T,3U,UniformCartesian<3U,MFLOAT>,Vert>& r)
01434 {
01435 const NDIndex<3U>& domain = r.getDomain();
01436 Index I = domain[0];
01437 Index J = domain[1];
01438 Index K = domain[2];
01439 Vektor<T,3U> idx,idy,idz;
01440 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01441 idx[1] = 0.0;
01442 idx[2] = 0.0;
01443 idy[0] = 0.0;
01444 idy[1] = 0.5/x.get_mesh().get_meshSpacing(1);
01445 idy[2] = 0.0;
01446 idz[0] = 0.0;
01447 idz[1] = 0.0;
01448 idz[2] = 0.5/x.get_mesh().get_meshSpacing(2);
01449
01450 assign( r[I][J][K] ,
01451 dot(idx , (x[I+1][J ][K ] - x[I-1][J ][K ] )) +
01452 dot(idy , (x[I ][J+1][K ] - x[I ][J-1][K ] )) +
01453 dot(idz , (x[I ][J ][K+1] - x[I ][J ][K-1] )) );
01454 return r;
01455 }
01456
01457
01458
01459 template < class T, class MFLOAT >
01460 Field<T,1U,UniformCartesian<1U,MFLOAT>,Cell>&
01461 Div(Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& x,
01462 Field<T,1U,UniformCartesian<1U,MFLOAT>,Cell>& r)
01463 {
01464 const NDIndex<1U>& domain = r.getDomain();
01465 Index I = domain[0];
01466 Vektor<T,1U> idx;
01467 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01468
01469 assign( r[I] , dot( idx , (x[I+1] - x[I-1]) ) );
01470 return r;
01471 }
01472
01473 template < class T, class MFLOAT >
01474 Field<T,2U,UniformCartesian<2U,MFLOAT>,Cell>&
01475 Div(Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& x,
01476 Field<T,2U,UniformCartesian<2U,MFLOAT>,Cell>& r)
01477 {
01478 const NDIndex<2U>& domain = r.getDomain();
01479 Index I = domain[0];
01480 Index J = domain[1];
01481 Vektor<T,2U> idx,idy;
01482 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01483 idx[1] = 0.0;
01484 idy[0] = 0.0;
01485 idy[1] = 0.5/x.get_mesh().get_meshSpacing(1);
01486
01487 assign( r[I][J] ,
01488 dot( idx , (x[I+1][J ] - x[I-1][J ])) +
01489 dot( idy , (x[I ][J+1] - x[I ][J-1])) );
01490 return r;
01491 }
01492
01493 template < class T, class MFLOAT >
01494 Field<T,3U,UniformCartesian<3U,MFLOAT>,Cell>&
01495 Div(Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& x,
01496 Field<T,3U,UniformCartesian<3U,MFLOAT>,Cell>& r)
01497 {
01498 const NDIndex<3U>& domain = r.getDomain();
01499 Index I = domain[0];
01500 Index J = domain[1];
01501 Index K = domain[2];
01502 Vektor<T,3U> idx,idy,idz;
01503 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01504 idx[1] = 0.0;
01505 idx[2] = 0.0;
01506 idy[0] = 0.0;
01507 idy[1] = 0.5/x.get_mesh().get_meshSpacing(1);
01508 idy[2] = 0.0;
01509 idz[0] = 0.0;
01510 idz[1] = 0.0;
01511 idz[2] = 0.5/x.get_mesh().get_meshSpacing(2);
01512
01513 assign( r[I][J][K] ,
01514 dot(idx , (x[I+1][J ][K ] - x[I-1][J ][K ] )) +
01515 dot(idy , (x[I ][J+1][K ] - x[I ][J-1][K ] )) +
01516 dot(idz , (x[I ][J ][K+1] - x[I ][J ][K-1] )) );
01517 return r;
01518 }
01519
01520
01521
01522 template < class T, class MFLOAT >
01523 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>&
01524 Div(Field<Tenzor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& x,
01525 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& r)
01526 {
01527 const NDIndex<1U>& domain = r.getDomain();
01528 Index I = domain[0];
01529
01530 assign( r[I] ,
01531 dot(x[I ], x.get_mesh().Dvc[0]) +
01532 dot(x[I+1], x.get_mesh().Dvc[1]));
01533 return r;
01534 }
01535
01536 template < class T, class MFLOAT >
01537 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>&
01538 Div(Field<Tenzor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& x,
01539 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& r)
01540 {
01541 const NDIndex<2U>& domain = r.getDomain();
01542 Index I = domain[0];
01543 Index J = domain[1];
01544
01545 assign( r[I][J] ,
01546 dot(x[I ][J ], x.get_mesh().Dvc[0]) +
01547 dot(x[I+1][J ], x.get_mesh().Dvc[1]) +
01548 dot(x[I ][J+1], x.get_mesh().Dvc[2]) +
01549 dot(x[I+1][J+1], x.get_mesh().Dvc[3]));
01550
01551 return r;
01552 }
01553
01554 template < class T, class MFLOAT >
01555 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>&
01556 Div(Field<Tenzor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& x,
01557 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& r)
01558 {
01559 const NDIndex<3U>& domain = r.getDomain();
01560 Index I = domain[0];
01561 Index J = domain[1];
01562 Index K = domain[2];
01563
01564 assign( r[I][J][K] ,
01565 dot(x[I ][J ][K ], x.get_mesh().Dvc[0]) +
01566 dot(x[I+1][J ][K ], x.get_mesh().Dvc[1]) +
01567 dot(x[I ][J+1][K ], x.get_mesh().Dvc[2]) +
01568 dot(x[I+1][J+1][K ], x.get_mesh().Dvc[3]) +
01569 dot(x[I ][J ][K+1], x.get_mesh().Dvc[4]) +
01570 dot(x[I+1][J ][K+1], x.get_mesh().Dvc[5]) +
01571 dot(x[I ][J+1][K+1], x.get_mesh().Dvc[6]) +
01572 dot(x[I+1][J+1][K+1], x.get_mesh().Dvc[7]));
01573
01574 return r;
01575 }
01576
01577
01578
01579 template < class T, class MFLOAT >
01580 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>&
01581 Div(Field<SymTenzor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& x,
01582 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& r)
01583 {
01584 const NDIndex<1U>& domain = r.getDomain();
01585 Index I = domain[0];
01586
01587 assign( r[I] ,
01588 dot(x[I ], x.get_mesh().Dvc[0]) +
01589 dot(x[I+1], x.get_mesh().Dvc[1]));
01590 return r;
01591 }
01592
01593 template < class T, class MFLOAT >
01594 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>&
01595 Div(Field<SymTenzor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& x,
01596 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& r)
01597 {
01598 const NDIndex<2U>& domain = r.getDomain();
01599 Index I = domain[0];
01600 Index J = domain[1];
01601
01602 assign( r[I][J] ,
01603 dot(x[I ][J ], x.get_mesh().Dvc[0]) +
01604 dot(x[I+1][J ], x.get_mesh().Dvc[1]) +
01605 dot(x[I ][J+1], x.get_mesh().Dvc[2]) +
01606 dot(x[I+1][J+1], x.get_mesh().Dvc[3]));
01607 return r;
01608 }
01609
01610 template < class T, class MFLOAT >
01611 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>&
01612 Div(Field<SymTenzor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& x,
01613 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& r)
01614 {
01615 const NDIndex<3U>& domain = r.getDomain();
01616 Index I = domain[0];
01617 Index J = domain[1];
01618 Index K = domain[2];
01619
01620 assign( r[I][J][K] ,
01621 dot(x[I ][J ][K ], x.get_mesh().Dvc[0]) +
01622 dot(x[I+1][J ][K ], x.get_mesh().Dvc[1]) +
01623 dot(x[I ][J+1][K ], x.get_mesh().Dvc[2]) +
01624 dot(x[I+1][J+1][K ], x.get_mesh().Dvc[3]) +
01625 dot(x[I ][J ][K+1], x.get_mesh().Dvc[4]) +
01626 dot(x[I+1][J ][K+1], x.get_mesh().Dvc[5]) +
01627 dot(x[I ][J+1][K+1], x.get_mesh().Dvc[6]) +
01628 dot(x[I+1][J+1][K+1], x.get_mesh().Dvc[7]));
01629 return r;
01630 }
01631
01632
01633
01634
01635 template < class T, class MFLOAT >
01636 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>&
01637 Div(Field<Tenzor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& x,
01638 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& r)
01639 {
01640 const NDIndex<1U>& domain = r.getDomain();
01641 Index I = domain[0];
01642
01643 assign( r[I] ,
01644 dot(x[I-1], x.get_mesh().Dvc[0]) +
01645 dot(x[I ], x.get_mesh().Dvc[1]));
01646 return r;
01647 }
01648
01649 template < class T, class MFLOAT >
01650 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>&
01651 Div(Field<Tenzor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& x,
01652 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& r)
01653 {
01654 const NDIndex<2U>& domain = r.getDomain();
01655 Index I = domain[0];
01656 Index J = domain[1];
01657
01658 assign( r[I][J] ,
01659 dot(x[I-1][J-1], x.get_mesh().Dvc[0]) +
01660 dot(x[I ][J-1], x.get_mesh().Dvc[1]) +
01661 dot(x[I-1][J ], x.get_mesh().Dvc[2]) +
01662 dot(x[I ][J ], x.get_mesh().Dvc[3]));
01663 return r;
01664 }
01665
01666 template < class T, class MFLOAT >
01667 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>&
01668 Div(Field<Tenzor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& x,
01669 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& r)
01670 {
01671 const NDIndex<3U>& domain = r.getDomain();
01672 Index I = domain[0];
01673 Index J = domain[1];
01674 Index K = domain[2];
01675
01676 assign( r[I][J][K] ,
01677 dot(x[I-1][J-1][K-1], x.get_mesh().Dvc[0]) +
01678 dot(x[I ][J-1][K-1], x.get_mesh().Dvc[1]) +
01679 dot(x[I-1][J ][K-1], x.get_mesh().Dvc[2]) +
01680 dot(x[I ][J ][K-1], x.get_mesh().Dvc[3]) +
01681 dot(x[I-1][J-1][K ], x.get_mesh().Dvc[4]) +
01682 dot(x[I ][J-1][K ], x.get_mesh().Dvc[5]) +
01683 dot(x[I-1][J ][K ], x.get_mesh().Dvc[6]) +
01684 dot(x[I ][J ][K ], x.get_mesh().Dvc[7]));
01685 return r;
01686 }
01687
01688
01689
01690
01691 template < class T, class MFLOAT >
01692 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>&
01693 Div(Field<SymTenzor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& x,
01694 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& r)
01695 {
01696 const NDIndex<1U>& domain = r.getDomain();
01697 Index I = domain[0];
01698
01699 assign( r[I] ,
01700 dot(x[I-1], x.get_mesh().Dvc[0]) +
01701 dot(x[I ], x.get_mesh().Dvc[1]));
01702 return r;
01703 }
01704
01705 template < class T, class MFLOAT >
01706 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>&
01707 Div(Field<SymTenzor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& x,
01708 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& r)
01709 {
01710 const NDIndex<2U>& domain = r.getDomain();
01711 Index I = domain[0];
01712 Index J = domain[1];
01713
01714 assign( r[I][J] ,
01715 dot(x[I-1][J-1], x.get_mesh().Dvc[0]) +
01716 dot(x[I ][J-1], x.get_mesh().Dvc[1]) +
01717 dot(x[I-1][J ], x.get_mesh().Dvc[2]) +
01718 dot(x[I ][J ], x.get_mesh().Dvc[3]));
01719 return r;
01720 }
01721
01722 template < class T, class MFLOAT >
01723 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>&
01724 Div(Field<SymTenzor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& x,
01725 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& r)
01726 {
01727 const NDIndex<3U>& domain = r.getDomain();
01728 Index I = domain[0];
01729 Index J = domain[1];
01730 Index K = domain[2];
01731
01732 assign( r[I][J][K] ,
01733 dot(x[I-1][J-1][K-1], x.get_mesh().Dvc[0]) +
01734 dot(x[I ][J-1][K-1], x.get_mesh().Dvc[1]) +
01735 dot(x[I-1][J ][K-1], x.get_mesh().Dvc[2]) +
01736 dot(x[I ][J ][K-1], x.get_mesh().Dvc[3]) +
01737 dot(x[I-1][J-1][K ], x.get_mesh().Dvc[4]) +
01738 dot(x[I ][J-1][K ], x.get_mesh().Dvc[5]) +
01739 dot(x[I-1][J ][K ], x.get_mesh().Dvc[6]) +
01740 dot(x[I ][J ][K ], x.get_mesh().Dvc[7]));
01741 return r;
01742 }
01743
01744
01745
01746
01747 template < class T, class MFLOAT >
01748 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>&
01749 Grad(Field<T,1U,UniformCartesian<1U,MFLOAT>,Vert>& x,
01750 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& r)
01751 {
01752 const NDIndex<1U>& domain = r.getDomain();
01753 Index I = domain[0];
01754
01755 assign( r[I] ,
01756 x[I ] * x.get_mesh().Dvc[0] +
01757 x[I+1] * x.get_mesh().Dvc[1]);
01758 return r;
01759 }
01760
01761 template < class T, class MFLOAT >
01762 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>&
01763 Grad(Field<T,2U,UniformCartesian<2U,MFLOAT>,Vert>& x,
01764 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& r)
01765 {
01766 const NDIndex<2U>& domain = r.getDomain();
01767 Index I = domain[0];
01768 Index J = domain[1];
01769
01770 assign( r[I][J] ,
01771 x[I ][J ] * x.get_mesh().Dvc[0] +
01772 x[I+1][J ] * x.get_mesh().Dvc[1] +
01773 x[I ][J+1] * x.get_mesh().Dvc[2] +
01774 x[I+1][J+1] * x.get_mesh().Dvc[3]);
01775 return r;
01776 }
01777
01778 template < class T, class MFLOAT >
01779 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>&
01780 Grad(Field<T,3U,UniformCartesian<3U,MFLOAT>,Vert>& x,
01781 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& r)
01782 {
01783 const NDIndex<3U>& domain = r.getDomain();
01784 Index I = domain[0];
01785 Index J = domain[1];
01786 Index K = domain[2];
01787
01788 assign( r[I][J][K] ,
01789 x[I ][J ][K ] * x.get_mesh().Dvc[0] +
01790 x[I+1][J ][K ] * x.get_mesh().Dvc[1] +
01791 x[I ][J+1][K ] * x.get_mesh().Dvc[2] +
01792 x[I+1][J+1][K ] * x.get_mesh().Dvc[3] +
01793 x[I ][J ][K+1] * x.get_mesh().Dvc[4] +
01794 x[I+1][J ][K+1] * x.get_mesh().Dvc[5] +
01795 x[I ][J+1][K+1] * x.get_mesh().Dvc[6] +
01796 x[I+1][J+1][K+1] * x.get_mesh().Dvc[7]);
01797
01798 return r;
01799 }
01800
01801
01802
01803 template < class T, class MFLOAT >
01804 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>&
01805 Grad(Field<T,1U,UniformCartesian<1U,MFLOAT>,Cell>& x,
01806 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& r)
01807 {
01808 const NDIndex<1U>& domain = r.getDomain();
01809 Index I = domain[0];
01810
01811 assign( r[I] ,
01812 x[I-1] * x.get_mesh().Dvc[0] +
01813 x[I ] * x.get_mesh().Dvc[1]);
01814 return r;
01815 }
01816
01817 template < class T, class MFLOAT >
01818 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>&
01819 Grad(Field<T,2U,UniformCartesian<2U,MFLOAT>,Cell>& x,
01820 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& r)
01821 {
01822 const NDIndex<2U>& domain = r.getDomain();
01823 Index I = domain[0];
01824 Index J = domain[1];
01825
01826 assign( r[I][J] ,
01827 x[I-1][J-1] * x.get_mesh().Dvc[0] +
01828 x[I ][J-1] * x.get_mesh().Dvc[1] +
01829 x[I-1][J ] * x.get_mesh().Dvc[2] +
01830 x[I ][J ] * x.get_mesh().Dvc[3]);
01831 return r;
01832 }
01833
01834 template < class T, class MFLOAT >
01835 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>&
01836 Grad(Field<T,3U,UniformCartesian<3U,MFLOAT>,Cell>& x,
01837 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& r)
01838 {
01839 const NDIndex<3U>& domain = r.getDomain();
01840 Index I = domain[0];
01841 Index J = domain[1];
01842 Index K = domain[2];
01843
01844 assign( r[I][J][K] ,
01845 x[I-1][J-1][K-1] * x.get_mesh().Dvc[0] +
01846 x[I ][J-1][K-1] * x.get_mesh().Dvc[1] +
01847 x[I-1][J ][K-1] * x.get_mesh().Dvc[2] +
01848 x[I ][J ][K-1] * x.get_mesh().Dvc[3] +
01849 x[I-1][J-1][K ] * x.get_mesh().Dvc[4] +
01850 x[I ][J-1][K ] * x.get_mesh().Dvc[5] +
01851 x[I-1][J ][K ] * x.get_mesh().Dvc[6] +
01852 x[I ][J ][K ] * x.get_mesh().Dvc[7]);
01853 return r;
01854 }
01855
01856
01857
01858 template < class T, class MFLOAT >
01859 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>&
01860 Grad(Field<T,1U,UniformCartesian<1U,MFLOAT>,Vert>& x,
01861 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& r)
01862 {
01863 const NDIndex<1U>& domain = r.getDomain();
01864 Index I = domain[0];
01865
01866 Vektor<T,1U> idx;
01867 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01868
01869 assign( r[I] , idx * (x[I+1] - x[I-1] ) );
01870 return r;
01871 }
01872
01873 template < class T, class MFLOAT >
01874 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>&
01875 Grad(Field<T,2U,UniformCartesian<2U,MFLOAT>,Vert>& x,
01876 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& r)
01877 {
01878 const NDIndex<2U>& domain = r.getDomain();
01879 Index I = domain[0];
01880 Index J = domain[1];
01881
01882 Vektor<T,2U> idx,idy;
01883 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01884 idx[1] = 0.0;
01885 idy[0] = 0.0;
01886 idy[1] = 0.5/x.get_mesh().get_meshSpacing(1);
01887
01888 assign( r[I][J] ,
01889 idx * (x[I+1][J ] - x[I-1][J ]) +
01890 idy * (x[I ][J+1] - x[I ][J-1]) );
01891 return r;
01892 }
01893
01894 template < class T, class MFLOAT >
01895 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>&
01896 Grad(Field<T,3U,UniformCartesian<3U,MFLOAT>,Vert>& x,
01897 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& r)
01898 {
01899 const NDIndex<3U>& domain = r.getDomain();
01900 Index I = domain[0];
01901 Index J = domain[1];
01902 Index K = domain[2];
01903
01904 Vektor<T,3U> idx,idy,idz;
01905 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01906 idx[1] = 0.0;
01907 idx[2] = 0.0;
01908 idy[0] = 0.0;
01909 idy[1] = 0.5/x.get_mesh().get_meshSpacing(1);
01910 idy[2] = 0.0;
01911 idz[0] = 0.0;
01912 idz[1] = 0.0;
01913 idz[2] = 0.5/x.get_mesh().get_meshSpacing(2);
01914
01915 assign(r[I][J][K] ,
01916 idx * (x[I+1][J ][K ] - x[I-1][J ][K ]) +
01917 idy * (x[I ][J+1][K ] - x[I ][J-1][K ]) +
01918 idz * (x[I ][J ][K+1] - x[I ][J ][K-1]));
01919 return r;
01920 }
01921
01922
01923
01924 template < class T, class MFLOAT >
01925 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>&
01926 Grad(Field<T,1U,UniformCartesian<1U,MFLOAT>,Cell>& x,
01927 Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& r)
01928 {
01929 const NDIndex<1U>& domain = r.getDomain();
01930 Index I = domain[0];
01931
01932 Vektor<T,1U> idx;
01933 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01934
01935 assign( r[I] , idx * (x[I+1] - x[I-1] ) );
01936 return r;
01937 }
01938
01939 template < class T, class MFLOAT >
01940 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>&
01941 Grad(Field<T,2U,UniformCartesian<2U,MFLOAT>,Cell>& x,
01942 Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& r)
01943 {
01944 const NDIndex<2U>& domain = r.getDomain();
01945 Index I = domain[0];
01946 Index J = domain[1];
01947
01948 Vektor<T,2U> idx,idy;
01949 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01950 idx[1] = 0.0;
01951 idy[0] = 0.0;
01952 idy[1] = 0.5/x.get_mesh().get_meshSpacing(1);
01953
01954 assign( r[I][J] ,
01955 idx * (x[I+1][J ] - x[I-1][J ]) +
01956 idy * (x[I ][J+1] - x[I ][J-1]) );
01957
01958 return r;
01959 }
01960
01961 template < class T, class MFLOAT >
01962 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>&
01963 Grad(Field<T,3U,UniformCartesian<3U,MFLOAT>,Cell>& x,
01964 Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& r)
01965 {
01966 const NDIndex<3U>& domain = r.getDomain();
01967 Index I = domain[0];
01968 Index J = domain[1];
01969 Index K = domain[2];
01970
01971 Vektor<T,3U> idx,idy,idz;
01972 idx[0] = 0.5/x.get_mesh().get_meshSpacing(0);
01973 idx[1] = 0.0;
01974 idx[2] = 0.0;
01975 idy[0] = 0.0;
01976 idy[1] = 0.5/x.get_mesh().get_meshSpacing(1);
01977 idy[2] = 0.0;
01978 idz[0] = 0.0;
01979 idz[1] = 0.0;
01980 idz[2] = 0.5/x.get_mesh().get_meshSpacing(2);
01981
01982 assign(r[I][J][K] ,
01983 idx * (x[I+1][J ][K ] - x[I-1][J ][K ]) +
01984 idy * (x[I ][J+1][K ] - x[I ][J-1][K ]) +
01985 idz * (x[I ][J ][K+1] - x[I ][J ][K-1]));
01986 return r;
01987 }
01988
01989
01990
01991 template < class T, class MFLOAT >
01992 Field<Tenzor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>&
01993 Grad(Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& x,
01994 Field<Tenzor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& r)
01995 {
01996 const NDIndex<1U>& domain = r.getDomain();
01997 Index I = domain[0];
01998
01999 assign( r[I] ,
02000 outerProduct( x[I ] , x.get_mesh().Dvc[0] ) +
02001 outerProduct( x[I+1] , x.get_mesh().Dvc[1])) ;
02002 return r;
02003 }
02004
02005 template < class T, class MFLOAT >
02006 Field<Tenzor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>&
02007 Grad(Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& x,
02008 Field<Tenzor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& r)
02009 {
02010 const NDIndex<2U>& domain = r.getDomain();
02011 Index I = domain[0];
02012 Index J = domain[1];
02013
02014 assign( r[I][J] ,
02015 outerProduct( x[I ][J ] , x.get_mesh().Dvc[0] ) +
02016 outerProduct( x[I+1][J ] , x.get_mesh().Dvc[1] ) +
02017 outerProduct( x[I ][J+1] , x.get_mesh().Dvc[2] ) +
02018 outerProduct( x[I+1][J+1] , x.get_mesh().Dvc[3] )) ;
02019 return r;
02020 }
02021
02022 template < class T, class MFLOAT >
02023 Field<Tenzor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>&
02024 Grad(Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& x,
02025 Field<Tenzor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& r)
02026 {
02027 const NDIndex<3U>& domain = r.getDomain();
02028 Index I = domain[0];
02029 Index J = domain[1];
02030 Index K = domain[2];
02031
02032 assign( r[I][J][K] ,
02033 outerProduct( x[I ][J ][K ] , x.get_mesh().Dvc[0] ) +
02034 outerProduct( x[I+1][J ][K ] , x.get_mesh().Dvc[1] ) +
02035 outerProduct( x[I ][J+1][K ] , x.get_mesh().Dvc[2] ) +
02036 outerProduct( x[I+1][J+1][K ] , x.get_mesh().Dvc[3] ) +
02037 outerProduct( x[I ][J ][K+1] , x.get_mesh().Dvc[4] ) +
02038 outerProduct( x[I+1][J ][K+1] , x.get_mesh().Dvc[5] ) +
02039 outerProduct( x[I ][J+1][K+1] , x.get_mesh().Dvc[6] ) +
02040 outerProduct( x[I+1][J+1][K+1] , x.get_mesh().Dvc[7] ));
02041
02042 return r;
02043 }
02044
02045
02046
02047 template < class T, class MFLOAT >
02048 Field<Tenzor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>&
02049 Grad(Field<Vektor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Cell>& x,
02050 Field<Tenzor<T,1U>,1U,UniformCartesian<1U,MFLOAT>,Vert>& r)
02051 {
02052 const NDIndex<1U>& domain = r.getDomain();
02053 Index I = domain[0];
02054
02055 assign( r[I] ,
02056 outerProduct( x[I-1] , x.get_mesh().Dvc[0] ) +
02057 outerProduct( x[I ] , x.get_mesh().Dvc[1] ));
02058 return r;
02059 }
02060
02061 template < class T, class MFLOAT >
02062 Field<Tenzor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>&
02063 Grad(Field<Vektor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Cell>& x,
02064 Field<Tenzor<T,2U>,2U,UniformCartesian<2U,MFLOAT>,Vert>& r)
02065 {
02066 const NDIndex<2U>& domain = r.getDomain();
02067 Index I = domain[0];
02068 Index J = domain[1];
02069
02070 assign( r[I][J] ,
02071 outerProduct( x[I-1][J-1] , x.get_mesh().Dvc[0] ) +
02072 outerProduct( x[I ][J-1] , x.get_mesh().Dvc[1] ) +
02073 outerProduct( x[I-1][J ] , x.get_mesh().Dvc[2] ) +
02074 outerProduct( x[I ][J ] , x.get_mesh().Dvc[3] ));
02075 return r;
02076 }
02077
02078 template < class T, class MFLOAT >
02079 Field<Tenzor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>&
02080 Grad(Field<Vektor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Cell>& x,
02081 Field<Tenzor<T,3U>,3U,UniformCartesian<3U,MFLOAT>,Vert>& r)
02082 {
02083 const NDIndex<3U>& domain = r.getDomain();
02084 Index I = domain[0];
02085 Index J = domain[1];
02086 Index K = domain[2];
02087
02088 assign( r[I][J][K] ,
02089 outerProduct( x[I-1][J-1][K-1] , x.get_mesh().Dvc[0] ) +
02090 outerProduct( x[I ][J-1][K-1] , x.get_mesh().Dvc[1] ) +
02091 outerProduct( x[I-1][J ][K-1] , x.get_mesh().Dvc[2] ) +
02092 outerProduct( x[I ][J ][K-1] , x.get_mesh().Dvc[3] ) +
02093 outerProduct( x[I-1][J-1][K ] , x.get_mesh().Dvc[4] ) +
02094 outerProduct( x[I ][J-1][K ] , x.get_mesh().Dvc[5] ) +
02095 outerProduct( x[I-1][J ][K ] , x.get_mesh().Dvc[6] ) +
02096 outerProduct( x[I ][J ][K ] , x.get_mesh().Dvc[7] ));
02097 return r;
02098 }
02099
02100
02101
02102 template < class T1, class T2, class MFLOAT >
02103 Field<T1,1U,UniformCartesian<1U,MFLOAT>,Vert>&
02104 Average(Field<T1,1U,UniformCartesian<1U,MFLOAT>,Cell>& x,
02105 Field<T2,1U,UniformCartesian<1U,MFLOAT>,Cell>& w,
02106 Field<T1,1U,UniformCartesian<1U,MFLOAT>,Vert>& r)
02107 {
02108 const NDIndex<1U>& domain = r.getDomain();
02109 Index I = domain[0];
02110 assign( r[I] ,
02111 ( x[I-1] * w[I-1] + x[I ] * w[I ] )/
02112 ( w[I-1] + w[I ] ) );
02113 return r;
02114 }
02115
02116 template < class T1, class T2, class MFLOAT >
02117 Field<T1,2U,UniformCartesian<2U,MFLOAT>,Vert>&
02118 Average(Field<T1,2U,UniformCartesian<2U,MFLOAT>,Cell>& x,
02119 Field<T2,2U,UniformCartesian<2U,MFLOAT>,Cell>& w,
02120 Field<T1,2U,UniformCartesian<2U,MFLOAT>,Vert>& r)
02121 {
02122 const NDIndex<2U>& domain = r.getDomain();
02123 Index I = domain[0];
02124 Index J = domain[1];
02125
02126 assign( r[I][J] ,
02127 ( x[I-1][J-1] * w[I-1][J-1] +
02128 x[I ][J-1] * w[I ][J-1] +
02129 x[I-1][J ] * w[I-1][J ] +
02130 x[I ][J ] * w[I ][J ] )/
02131 ( w[I-1][J-1] +
02132 w[I ][J-1] +
02133 w[I-1][J ] +
02134 w[I ][J ] ) );
02135 return r;
02136 }
02137
02138 template < class T1, class T2, class MFLOAT >
02139 Field<T1,3U,UniformCartesian<3U,MFLOAT>,Vert>&
02140 Average(Field<T1,3U,UniformCartesian<3U,MFLOAT>,Cell>& x,
02141 Field<T2,3U,UniformCartesian<3U,MFLOAT>,Cell>& w,
02142 Field<T1,3U,UniformCartesian<3U,MFLOAT>,Vert>& r)
02143 {
02144 const NDIndex<3U>& domain = r.getDomain();
02145 Index I = domain[0];
02146 Index J = domain[1];
02147 Index K = domain[2];
02148
02149 assign( r[I][J][K] ,
02150 ( x[I-1][J-1][K-1] * w[I-1][J-1][K-1] +
02151 x[I ][J-1][K-1] * w[I ][J-1][K-1] +
02152 x[I-1][J ][K-1] * w[I-1][J ][K-1] +
02153 x[I ][J ][K-1] * w[I ][J ][K-1] +
02154 x[I-1][J-1][K ] * w[I-1][J-1][K ] +
02155 x[I ][J-1][K ] * w[I ][J-1][K ] +
02156 x[I-1][J ][K ] * w[I-1][J ][K ] +
02157 x[I ][J ][K ] * w[I ][J ][K ] )/
02158 ( w[I-1][J-1][K-1] +
02159 w[I ][J-1][K-1] +
02160 w[I-1][J ][K-1] +
02161 w[I ][J ][K-1] +
02162 w[I-1][J-1][K ] +
02163 w[I ][J-1][K ] +
02164 w[I-1][J ][K ] +
02165 w[I ][J ][K ] ) );
02166 return r;
02167 }
02168
02169
02170
02171
02172 template < class T1, class T2, class MFLOAT >
02173 Field<T1,1U,UniformCartesian<1U,MFLOAT>,Cell>&
02174 Average(Field<T1,1U,UniformCartesian<1U,MFLOAT>,Vert>& x,
02175 Field<T2,1U,UniformCartesian<1U,MFLOAT>,Vert>& w,
02176 Field<T1,1U,UniformCartesian<1U,MFLOAT>,Cell>& r)
02177 {
02178 const NDIndex<1U>& domain = r.getDomain();
02179 Index I = domain[0];
02180 assign( r[I] ,
02181 ( x[I+1] * w[I+1] + x[I ] * w[I ] )/
02182 ( w[I+1] + w[I ] ) );
02183 return r;
02184 }
02185
02186 template < class T1, class T2, class MFLOAT >
02187 Field<T1,2U,UniformCartesian<2U,MFLOAT>,Cell>&
02188 Average(Field<T1,2U,UniformCartesian<2U,MFLOAT>,Vert>& x,
02189 Field<T2,2U,UniformCartesian<2U,MFLOAT>,Vert>& w,
02190 Field<T1,2U,UniformCartesian<2U,MFLOAT>,Cell>& r)
02191 {
02192 const NDIndex<2U>& domain = r.getDomain();
02193 Index I = domain[0];
02194 Index J = domain[1];
02195
02196 assign( r[I][J] ,
02197 ( x[I+1][J+1] * w[I+1][J+1] +
02198 x[I ][J+1] * w[I ][J+1] +
02199 x[I+1][J ] * w[I+1][J ] +
02200 x[I ][J ] * w[I ][J ] )/
02201 ( w[I+1][J+1] +
02202 w[I ][J+1] +
02203 w[I+1][J ] +
02204 w[I ][J ] ) );
02205 return r;
02206 }
02207
02208 template < class T1, class T2, class MFLOAT >
02209 Field<T1,3U,UniformCartesian<3U,MFLOAT>,Cell>&
02210 Average(Field<T1,3U,UniformCartesian<3U,MFLOAT>,Vert>& x,
02211 Field<T2,3U,UniformCartesian<3U,MFLOAT>,Vert>& w,
02212 Field<T1,3U,UniformCartesian<3U,MFLOAT>,Cell>& r)
02213 {
02214 const NDIndex<3U>& domain = r.getDomain();
02215 Index I = domain[0];
02216 Index J = domain[1];
02217 Index K = domain[2];
02218
02219 assign( r[I][J][K] ,
02220 ( x[I+1][J+1][K+1] * w[I+1][J+1][K+1] +
02221 x[I ][J+1][K+1] * w[I ][J+1][K+1] +
02222 x[I+1][J ][K+1] * w[I+1][J ][K+1] +
02223 x[I ][J ][K+1] * w[I ][J ][K+1] +
02224 x[I+1][J+1][K ] * w[I+1][J+1][K ] +
02225 x[I ][J+1][K ] * w[I ][J+1][K ] +
02226 x[I+1][J ][K ] * w[I+1][J ][K ] +
02227 x[I ][J ][K ] * w[I ][J ][K ] )/
02228 ( w[I+1][J+1][K+1] +
02229 w[I ][J+1][K+1] +
02230 w[I+1][J ][K+1] +
02231 w[I ][J ][K+1] +
02232 w[I+1][J+1][K ] +
02233 w[I ][J+1][K ] +
02234 w[I+1][J ][K ] +
02235 w[I ][J ][K ] ) );
02236 return r;
02237 }
02238
02239
02240
02241
02242 template < class T1, class MFLOAT >
02243 Field<T1,1U,UniformCartesian<1U,MFLOAT>,Vert>&
02244 Average(Field<T1,1U,UniformCartesian<1U,MFLOAT>,Cell>& x,
02245 Field<T1,1U,UniformCartesian<1U,MFLOAT>,Vert>& r)
02246 {
02247 const NDIndex<1U>& domain = r.getDomain();
02248 Index I = domain[0];
02249 r[I] = 0.5*(x[I-1] + x[I ]);
02250 return r;
02251 }
02252
02253 template < class T1, class MFLOAT >
02254 Field<T1,2U,UniformCartesian<2U,MFLOAT>,Vert>&
02255 Average(Field<T1,2U,UniformCartesian<2U,MFLOAT>,Cell>& x,
02256 Field<T1,2U,UniformCartesian<2U,MFLOAT>,Vert>& r)
02257 {
02258 const NDIndex<2U>& domain = r.getDomain();
02259 Index I = domain[0];
02260 Index J = domain[1];
02261 r[I][J] = 0.25*(x[I-1][J-1] + x[I ][J-1] + x[I-1][J ] + x[I ][J ]);
02262 return r;
02263 }
02264
02265 template < class T1, class MFLOAT >
02266 Field<T1,3U,UniformCartesian<3U,MFLOAT>,Vert>&
02267 Average(Field<T1,3U,UniformCartesian<3U,MFLOAT>,Cell>& x,
02268 Field<T1,3U,UniformCartesian<3U,MFLOAT>,Vert>& r)
02269 {
02270 const NDIndex<3U>& domain = r.getDomain();
02271 Index I = domain[0];
02272 Index J = domain[1];
02273 Index K = domain[2];
02274 r[I][J][K] = 0.125*(x[I-1][J-1][K-1] + x[I ][J-1][K-1] + x[I-1][J ][K-1] +
02275 x[I ][J ][K-1] + x[I-1][J-1][K ] + x[I ][J-1][K ] +
02276 x[I-1][J ][K ] + x[I ][J ][K ]);
02277 return r;
02278 }
02279
02280
02281
02282
02283 template < class T1, class MFLOAT >
02284 Field<T1,1U,UniformCartesian<1U,MFLOAT>,Cell>&
02285 Average(Field<T1,1U,UniformCartesian<1U,MFLOAT>,Vert>& x,
02286
02287 Field<T1,1U,UniformCartesian<1U,MFLOAT>,Cell>& r)
02288 {
02289 const NDIndex<1U>& domain = r.getDomain();
02290 Index I = domain[0];
02291 r[I] = 0.5*(x[I+1] + x[I ]);
02292 return r;
02293 }
02294
02295 template < class T1, class MFLOAT >
02296 Field<T1,2U,UniformCartesian<2U,MFLOAT>,Cell>&
02297 Average(Field<T1,2U,UniformCartesian<2U,MFLOAT>,Vert>& x,
02298 Field<T1,2U,UniformCartesian<2U,MFLOAT>,Cell>& r)
02299 {
02300 const NDIndex<2U>& domain = r.getDomain();
02301 Index I = domain[0];
02302 Index J = domain[1];
02303 r[I][J] = 0.25*(x[I+1][J+1] + x[I ][J+1] + x[I+1][J ] + x[I ][J ]);
02304 return r;
02305 }
02306
02307 template < class T1, class MFLOAT >
02308 Field<T1,3U,UniformCartesian<3U,MFLOAT>,Cell>&
02309 Average(Field<T1,3U,UniformCartesian<3U,MFLOAT>,Vert>& x,
02310 Field<T1,3U,UniformCartesian<3U,MFLOAT>,Cell>& r)
02311 {
02312 const NDIndex<3U>& domain = r.getDomain();
02313 Index I = domain[0];
02314 Index J = domain[1];
02315 Index K = domain[2];
02316 r[I][J][K] = 0.125*(x[I+1][J+1][K+1] + x[I ][J+1][K+1] + x[I+1][J ][K+1] +
02317 x[I ][J ][K+1] + x[I+1][J+1][K ] + x[I ][J+1][K ] +
02318 x[I+1][J ][K ] + x[I ][J ][K ]);
02319 return r;
02320 }
02321
02322
02323
02324
02325