1 // Copyright (C) 2007-2012 CEA/DEN, EDF R&D
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License.
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 // Lesser General Public License for more details.
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
19 // Author : Anthony Geay (CEA/DEN)
21 #include "MEDCouplingCMesh.hxx"
22 #include "MEDCouplingUMesh.hxx"
23 #include "MEDCouplingMemArray.hxx"
24 #include "MEDCouplingFieldDouble.hxx"
31 using namespace ParaMEDMEM;
33 MEDCouplingCMesh::MEDCouplingCMesh():_x_array(0),_y_array(0),_z_array(0)
37 MEDCouplingCMesh::MEDCouplingCMesh(const MEDCouplingCMesh& other, bool deepCopy):MEDCouplingMesh(other)
42 _x_array=other._x_array->deepCpy();
46 _y_array=other._y_array->deepCpy();
50 _z_array=other._z_array->deepCpy();
56 _x_array=other._x_array;
59 _y_array=other._y_array;
62 _z_array=other._z_array;
68 MEDCouplingCMesh::~MEDCouplingCMesh()
78 MEDCouplingCMesh *MEDCouplingCMesh::New()
80 return new MEDCouplingCMesh;
83 MEDCouplingCMesh *MEDCouplingCMesh::New(const char *meshName)
85 MEDCouplingCMesh *ret=new MEDCouplingCMesh;
86 ret->setName(meshName);
90 MEDCouplingMesh *MEDCouplingCMesh::deepCpy() const
95 MEDCouplingCMesh *MEDCouplingCMesh::clone(bool recDeepCpy) const
97 return new MEDCouplingCMesh(*this,recDeepCpy);
100 void MEDCouplingCMesh::updateTime() const
103 updateTimeWith(*_x_array);
105 updateTimeWith(*_y_array);
107 updateTimeWith(*_z_array);
111 * This method copyies all tiny strings from other (name and components name).
112 * @throw if other and this have not same mesh type.
114 void MEDCouplingCMesh::copyTinyStringsFrom(const MEDCouplingMesh *other) throw(INTERP_KERNEL::Exception)
116 const MEDCouplingCMesh *otherC=dynamic_cast<const MEDCouplingCMesh *>(other);
118 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::copyTinyStringsFrom : meshes have not same type !");
119 MEDCouplingMesh::copyTinyStringsFrom(other);
120 if(_x_array && otherC->_x_array)
121 _x_array->copyStringInfoFrom(*otherC->_x_array);
122 if(_y_array && otherC->_y_array)
123 _y_array->copyStringInfoFrom(*otherC->_y_array);
124 if(_z_array && otherC->_z_array)
125 _z_array->copyStringInfoFrom(*otherC->_z_array);
128 bool MEDCouplingCMesh::isEqualIfNotWhy(const MEDCouplingMesh *other, double prec, std::string& reason) const throw(INTERP_KERNEL::Exception)
131 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::isEqualIfNotWhy : input other pointer is null !");
132 const MEDCouplingCMesh *otherC=dynamic_cast<const MEDCouplingCMesh *>(other);
135 reason="mesh given in input is not castable in MEDCouplingCMesh !";
138 if(!MEDCouplingMesh::isEqualIfNotWhy(other,prec,reason))
140 const DataArrayDouble *thisArr[3]={_x_array,_y_array,_z_array};
141 const DataArrayDouble *otherArr[3]={otherC->_x_array,otherC->_y_array,otherC->_z_array};
142 std::ostringstream oss; oss.precision(15);
145 if((thisArr[i]!=0 && otherArr[i]==0) || (thisArr[i]==0 && otherArr[i]!=0))
147 oss << "Only one CMesh between the two this and other has its coordinates of rank" << i << " defined !";
152 if(!thisArr[i]->isEqualIfNotWhy(*otherArr[i],prec,reason))
154 oss << "Coordinates DataArrayDouble of rank #" << i << " differ :";
155 reason.insert(0,oss.str());
162 bool MEDCouplingCMesh::isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const
164 const MEDCouplingCMesh *otherC=dynamic_cast<const MEDCouplingCMesh *>(other);
167 const DataArrayDouble *thisArr[3]={_x_array,_y_array,_z_array};
168 const DataArrayDouble *otherArr[3]={otherC->_x_array,otherC->_y_array,otherC->_z_array};
171 if((thisArr[i]!=0 && otherArr[i]==0) || (thisArr[i]==0 && otherArr[i]!=0))
174 if(!thisArr[i]->isEqualWithoutConsideringStr(*otherArr[i],prec))
180 void MEDCouplingCMesh::checkDeepEquivalWith(const MEDCouplingMesh *other, int cellCompPol, double prec,
181 DataArrayInt *&cellCor, DataArrayInt *&nodeCor) const throw(INTERP_KERNEL::Exception)
183 if(!isEqualWithoutConsideringStr(other,prec))
184 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::checkDeepEquivalWith : Meshes are not the same !");
188 * Nothing is done here (except to check that the other is a ParaMEDMEM::MEDCouplingCMesh instance too).
189 * The user intend that the nodes are the same, so by construction of ParaMEDMEM::MEDCouplingCMesh, 'this' and 'other' are the same !
191 void MEDCouplingCMesh::checkDeepEquivalOnSameNodesWith(const MEDCouplingMesh *other, int cellCompPol, double prec,
192 DataArrayInt *&cellCor) const throw(INTERP_KERNEL::Exception)
194 const MEDCouplingCMesh *otherC=dynamic_cast<const MEDCouplingCMesh *>(other);
196 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::checkDeepEquivalOnSameNodesWith : other is NOT a cartesian mesh ! Impossible to check equivalence !");
199 void MEDCouplingCMesh::checkCoherency() const throw(INTERP_KERNEL::Exception)
201 const char msg0[]="Invalid ";
202 const char msg1[]=" array ! Must contain more than 1 element.";
203 const char msg2[]=" array ! Must be with only one component.";
206 if(_x_array->getNbOfElems()<2)
208 std::ostringstream os; os << msg0 << 'X' << msg1;
209 throw INTERP_KERNEL::Exception(os.str().c_str());
211 if(_x_array->getNumberOfComponents()!=1)
213 std::ostringstream os; os << msg0 << 'X' << msg2;
214 throw INTERP_KERNEL::Exception(os.str().c_str());
219 if(_y_array->getNbOfElems()<2)
221 std::ostringstream os; os << msg0 << 'Y' << msg1;
222 throw INTERP_KERNEL::Exception(os.str().c_str());
224 if(_y_array->getNumberOfComponents()!=1)
226 std::ostringstream os; os << msg0 << 'Y' << msg2;
227 throw INTERP_KERNEL::Exception(os.str().c_str());
233 if(_z_array->getNbOfElems()<2)
235 std::ostringstream os; os << msg0 << 'Z' << msg1;
236 throw INTERP_KERNEL::Exception(os.str().c_str());
238 if(_z_array->getNumberOfComponents()!=1)
240 std::ostringstream os; os << msg0 << 'Z' << msg2;
241 throw INTERP_KERNEL::Exception(os.str().c_str());
246 void MEDCouplingCMesh::checkCoherency1(double eps) const throw(INTERP_KERNEL::Exception)
250 _x_array->checkMonotonic(true, eps);
252 _y_array->checkMonotonic(true, eps);
254 _z_array->checkMonotonic(true, eps);
257 void MEDCouplingCMesh::checkCoherency2(double eps) const throw(INTERP_KERNEL::Exception)
259 checkCoherency1(eps);
262 int MEDCouplingCMesh::getNumberOfCells() const
266 ret*=_x_array->getNbOfElems()-1;
268 ret*=_y_array->getNbOfElems()-1;
270 ret*=_z_array->getNbOfElems()-1;
274 int MEDCouplingCMesh::getNumberOfNodes() const
278 ret*=_x_array->getNbOfElems();
280 ret*=_y_array->getNbOfElems();
282 ret*=_z_array->getNbOfElems();
286 void MEDCouplingCMesh::getSplitCellValues(int *res) const
288 int spaceDim=getSpaceDimension();
289 for(int l=0;l<spaceDim;l++)
292 for(int p=0;p<spaceDim-l-1;p++)
293 val*=getCoordsAt(p)->getNbOfElems()-1;
294 res[spaceDim-l-1]=val;
298 void MEDCouplingCMesh::getSplitNodeValues(int *res) const
300 int spaceDim=getSpaceDimension();
301 for(int l=0;l<spaceDim;l++)
304 for(int p=0;p<spaceDim-l-1;p++)
305 val*=getCoordsAt(p)->getNbOfElems();
306 res[spaceDim-l-1]=val;
310 int MEDCouplingCMesh::getCellIdFromPos(int i, int j, int k) const
314 int spaceDim=getSpaceDimension();
315 getSplitCellValues(tmp2);
316 std::transform(tmp,tmp+spaceDim,tmp2,tmp,std::multiplies<int>());
317 return std::accumulate(tmp,tmp+spaceDim,0);
320 int MEDCouplingCMesh::getNodeIdFromPos(int i, int j, int k) const
324 int spaceDim=getSpaceDimension();
325 getSplitNodeValues(tmp2);
326 std::transform(tmp,tmp+spaceDim,tmp2,tmp,std::multiplies<int>());
327 return std::accumulate(tmp,tmp+spaceDim,0);
330 void MEDCouplingCMesh::GetPosFromId(int nodeId, int spaceDim, const int *split, int *res)
333 for(int i=spaceDim-1;i>=0;i--)
335 int pos=work/split[i];
341 int MEDCouplingCMesh::getSpaceDimension() const
353 int MEDCouplingCMesh::getMeshDimension() const
355 return getSpaceDimension();
358 INTERP_KERNEL::NormalizedCellType MEDCouplingCMesh::getTypeOfCell(int cellId) const
360 switch(getMeshDimension())
363 return INTERP_KERNEL::NORM_HEXA8;
365 return INTERP_KERNEL::NORM_QUAD4;
367 return INTERP_KERNEL::NORM_SEG2;
369 throw INTERP_KERNEL::Exception("Unexpected dimension for MEDCouplingCMesh::getTypeOfCell !");
373 std::set<INTERP_KERNEL::NormalizedCellType> MEDCouplingCMesh::getAllGeoTypes() const
375 INTERP_KERNEL::NormalizedCellType ret;
376 switch(getMeshDimension())
379 ret=INTERP_KERNEL::NORM_HEXA8;
382 ret=INTERP_KERNEL::NORM_QUAD4;
385 ret=INTERP_KERNEL::NORM_SEG2;
388 throw INTERP_KERNEL::Exception("Unexpected dimension for MEDCouplingCMesh::getAllGeoTypes !");
390 std::set<INTERP_KERNEL::NormalizedCellType> ret2;
395 int MEDCouplingCMesh::getNumberOfCellsWithType(INTERP_KERNEL::NormalizedCellType type) const
397 int ret=getNumberOfCells();
398 int dim=getMeshDimension();
401 case INTERP_KERNEL::NORM_HEXA8:
404 case INTERP_KERNEL::NORM_QUAD4:
407 case INTERP_KERNEL::NORM_SEG2:
411 throw INTERP_KERNEL::Exception("Unexpected dimension for MEDCouplingCMesh::getTypeOfCell !");
416 void MEDCouplingCMesh::getNodeIdsOfCell(int cellId, std::vector<int>& conn) const
418 int spaceDim=getSpaceDimension();
419 int tmpCell[3],tmpNode[3];
420 getSplitCellValues(tmpCell);
421 getSplitNodeValues(tmpNode);
423 GetPosFromId(cellId,spaceDim,tmpCell,tmp2);
427 conn.push_back(tmp2[0]); conn.push_back(tmp2[0]+1);
430 conn.push_back(tmp2[1]*tmpCell[1]+tmp2[0]); conn.push_back(tmp2[1]*tmpCell[1]+tmp2[0]+1);
431 conn.push_back((tmp2[1]+1)*(tmpCell[1]+1)+tmp2[0]+1); conn.push_back((tmp2[1]+1)*(tmpCell[1]+1)+tmp2[0]);
434 conn.push_back(tmp2[1]*tmpCell[1]+tmp2[0]+tmp2[2]*tmpNode[2]); conn.push_back(tmp2[1]*tmpCell[1]+tmp2[0]+1+tmp2[2]*tmpNode[2]);
435 conn.push_back((tmp2[1]+1)*tmpNode[1]+tmp2[0]+1+tmp2[2]*tmpNode[2]); conn.push_back((tmp2[1]+1)*tmpNode[1]+tmp2[0]+tmp2[2]*tmpNode[2]);
436 conn.push_back(tmp2[1]*tmpCell[1]+tmp2[0]+(tmp2[2]+1)*tmpNode[2]); conn.push_back(tmp2[1]*tmpCell[1]+tmp2[0]+1+(tmp2[2]+1)*tmpNode[2]);
437 conn.push_back((tmp2[1]+1)*tmpNode[1]+tmp2[0]+1+(tmp2[2]+1)*tmpNode[2]); conn.push_back((tmp2[1]+1)*tmpNode[1]+tmp2[0]+(tmp2[2]+1)*tmpNode[2]);
440 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::getNodeIdsOfCell : big problem spacedim must be in 1,2 or 3 !");
444 void MEDCouplingCMesh::getCoordinatesOfNode(int nodeId, std::vector<double>& coo) const throw(INTERP_KERNEL::Exception)
447 int spaceDim=getSpaceDimension();
448 getSplitNodeValues(tmp);
449 const DataArrayDouble *tabs[3]={getCoordsAt(0),getCoordsAt(1),getCoordsAt(2)};
451 GetPosFromId(nodeId,spaceDim,tmp,tmp2);
452 for(int j=0;j<spaceDim;j++)
454 coo.push_back(tabs[j]->getConstPointer()[tmp2[j]]);
457 std::string MEDCouplingCMesh::simpleRepr() const
459 std::ostringstream ret;
460 ret << "Cartesian mesh with name : \"" << getName() << "\"\n";
461 ret << "Description of mesh : \"" << getDescription() << "\"\n";
463 double tt=getTime(tmpp1,tmpp2);
464 ret << "Time attached to the mesh [unit] : " << tt << " [" << getTimeUnit() << "]\n";
465 ret << "Iteration : " << tmpp1 << " Order : " << tmpp2 << "\n";
466 ret << "Mesh and SpaceDimension dimension : " << getSpaceDimension() << "\n\nArrays :\n________\n\n";
469 ret << "X Array :\n";
470 _x_array->reprZipWithoutNameStream(ret);
474 ret << "Y Array :\n";
475 _y_array->reprZipWithoutNameStream(ret);
479 ret << "Z Array :\n";
480 _z_array->reprZipWithoutNameStream(ret);
485 std::string MEDCouplingCMesh::advancedRepr() const
490 const DataArrayDouble *MEDCouplingCMesh::getCoordsAt(int i) const throw(INTERP_KERNEL::Exception)
501 throw INTERP_KERNEL::Exception("Invalid rank specified must be 0 or 1 or 2.");
505 DataArrayDouble *MEDCouplingCMesh::getCoordsAt(int i) throw(INTERP_KERNEL::Exception)
516 throw INTERP_KERNEL::Exception("Invalid rank specified must be 0 or 1 or 2.");
520 void MEDCouplingCMesh::setCoordsAt(int i, const DataArrayDouble *arr) throw(INTERP_KERNEL::Exception)
523 arr->checkNbOfComps(1,"MEDCouplingCMesh::setCoordsAt");
524 DataArrayDouble **thisArr[3]={&_x_array,&_y_array,&_z_array};
526 throw INTERP_KERNEL::Exception("Invalid rank specified must be 0 or 1 or 2.");
527 if(arr!=*(thisArr[i]))
530 (*(thisArr[i]))->decrRef();
531 (*(thisArr[i]))=const_cast<DataArrayDouble *>(arr);
533 (*(thisArr[i]))->incrRef();
538 void MEDCouplingCMesh::setCoords(const DataArrayDouble *coordsX, const DataArrayDouble *coordsY, const DataArrayDouble *coordsZ)
541 coordsX->checkNbOfComps(1,"MEDCouplingCMesh::setCoords : coordsX");
543 coordsY->checkNbOfComps(1,"MEDCouplingCMesh::setCoords : coordsY");
545 coordsZ->checkNbOfComps(1,"MEDCouplingCMesh::setCoords : coordsZ");
548 _x_array=const_cast<DataArrayDouble *>(coordsX);
553 _y_array=const_cast<DataArrayDouble *>(coordsY);
558 _z_array=const_cast<DataArrayDouble *>(coordsZ);
565 * See MEDCouplingUMesh::getDistributionOfTypes for more information
567 std::vector<int> MEDCouplingCMesh::getDistributionOfTypes() const throw(INTERP_KERNEL::Exception)
569 //only one type of cell
570 std::vector<int> ret(3);
571 ret[0]=getTypeOfCell(0);
572 ret[1]=getNumberOfCells();
573 ret[2]=0; //ret[3*k+2]==0 because it has no sense here
578 * See MEDCouplingUMesh::checkTypeConsistencyAndContig for more information
580 DataArrayInt *MEDCouplingCMesh::checkTypeConsistencyAndContig(const std::vector<int>& code, const std::vector<const DataArrayInt *>& idsPerType) const throw(INTERP_KERNEL::Exception)
583 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::checkTypeConsistencyAndContig : code is empty, should not !");
584 std::size_t sz=code.size();
586 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::checkTypeConsistencyAndContig : code should be of size 3 exactly !");
588 int nbCells=getNumberOfCellsWithType((INTERP_KERNEL::NormalizedCellType)code[0]);
594 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::checkTypeConsistencyAndContig : number of cells mismatch !");
599 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::checkTypeConsistencyAndContig : code[2]<-1 mismatch !");
600 if(code[2]>=(int)idsPerType.size())
601 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::checkTypeConsistencyAndContig : code[2]>size idsPerType !");
602 return idsPerType[code[2]]->deepCpy();
607 * See MEDCouplingUMesh::splitProfilePerType for more information
609 void MEDCouplingCMesh::splitProfilePerType(const DataArrayInt *profile, std::vector<int>& code, std::vector<DataArrayInt *>& idsInPflPerType, std::vector<DataArrayInt *>& idsPerType) const throw(INTERP_KERNEL::Exception)
611 int nbCells=getNumberOfCells();
613 code[0]=(int)getTypeOfCell(0);
616 idsInPflPerType.push_back(profile->deepCpy());
617 idsPerType.push_back(profile->deepCpy());
620 MEDCouplingUMesh *MEDCouplingCMesh::buildUnstructured() const throw(INTERP_KERNEL::Exception)
622 int spaceDim=getSpaceDimension();
623 MEDCouplingUMesh *ret=MEDCouplingUMesh::New(getName(),spaceDim);
624 DataArrayDouble *coords=getCoordinatesAndOwner();
625 ret->setCoords(coords);
630 fill1DUnstructuredMesh(ret);
633 fill2DUnstructuredMesh(ret);
636 fill3DUnstructuredMesh(ret);
639 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::buildUnstructured : big problem spacedim must be in 1,2 or 3 !");
644 MEDCouplingMesh *MEDCouplingCMesh::buildPart(const int *start, const int *end) const
646 MEDCouplingUMesh *um=buildUnstructured();
647 MEDCouplingMesh *ret=um->buildPart(start,end);
652 MEDCouplingMesh *MEDCouplingCMesh::buildPartAndReduceNodes(const int *start, const int *end, DataArrayInt*& arr) const
654 MEDCouplingUMesh *um=buildUnstructured();
655 MEDCouplingMesh *ret=um->buildPartAndReduceNodes(start,end,arr);
660 DataArrayInt *MEDCouplingCMesh::simplexize(int policy) throw(INTERP_KERNEL::Exception)
662 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::simplexize : not available for Cartesian mesh !");
665 void MEDCouplingCMesh::getBoundingBox(double *bbox) const
667 int dim=getSpaceDimension();
669 for (int idim=0; idim<dim; idim++)
671 const DataArrayDouble *c=getCoordsAt(idim);
674 const double *coords=c->getConstPointer();
675 int nb=c->getNbOfElems();
677 bbox[2*j+1]=coords[nb-1];
683 MEDCouplingFieldDouble *MEDCouplingCMesh::getMeasureField(bool isAbs) const
685 std::string name="MeasureOfMesh_";
687 int nbelem=getNumberOfCells();
688 MEDCouplingFieldDouble *field=MEDCouplingFieldDouble::New(ON_CELLS);
689 field->setName(name.c_str());
690 DataArrayDouble* array=DataArrayDouble::New();
691 array->alloc(nbelem,1);
692 double *area_vol=array->getPointer();
693 field->setArray(array) ;
695 field->setMesh(const_cast<MEDCouplingCMesh *>(this));
697 getSplitCellValues(tmp);
698 int dim=getSpaceDimension();
699 const double **thisArr=new const double *[dim];
700 const DataArrayDouble *thisArr2[3]={_x_array,_y_array,_z_array};
701 for(int i=0;i<dim;i++)
702 thisArr[i]=thisArr2[i]->getConstPointer();
703 for(int icell=0;icell<nbelem;icell++)
706 GetPosFromId(icell,dim,tmp,tmp2);
708 for(int i=0;i<dim;i++)
709 area_vol[icell]*=thisArr[i][tmp2[i]+1]-thisArr[i][tmp2[i]];
716 * not implemented yet !
718 MEDCouplingFieldDouble *MEDCouplingCMesh::getMeasureFieldOnNode(bool isAbs) const
720 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::getMeasureFieldOnNode : not implemented yet !");
724 MEDCouplingFieldDouble *MEDCouplingCMesh::buildOrthogonalField() const
726 if(getMeshDimension()!=2)
727 throw INTERP_KERNEL::Exception("Expected a cmesh with meshDim == 2 !");
728 MEDCouplingFieldDouble *ret=MEDCouplingFieldDouble::New(ON_CELLS,NO_TIME);
729 DataArrayDouble *array=DataArrayDouble::New();
730 int nbOfCells=getNumberOfCells();
731 array->alloc(nbOfCells,3);
732 double *vals=array->getPointer();
733 for(int i=0;i<nbOfCells;i++)
734 { vals[3*i]=0.; vals[3*i+1]=0.; vals[3*i+2]=1.; }
735 ret->setArray(array);
741 int MEDCouplingCMesh::getCellContainingPoint(const double *pos, double eps) const
743 int dim=getSpaceDimension();
746 for(int i=0;i<dim;i++)
748 const double *d=getCoordsAt(i)->getConstPointer();
749 int nbOfNodes=getCoordsAt(i)->getNbOfElems();
751 const double *w=std::find_if(d,d+nbOfNodes,std::bind2nd(std::greater_equal<double>(),ref));
752 int w2=(int)std::distance(d,w);
771 void MEDCouplingCMesh::rotate(const double *center, const double *vector, double angle)
773 throw INTERP_KERNEL::Exception("No rotation available on CMesh : Traduce it to StructuredMesh to apply it !");
776 void MEDCouplingCMesh::translate(const double *vector)
779 std::transform(_x_array->getConstPointer(),_x_array->getConstPointer()+_x_array->getNbOfElems(),
780 _x_array->getPointer(),std::bind2nd(std::plus<double>(),vector[0]));
782 std::transform(_y_array->getConstPointer(),_y_array->getConstPointer()+_y_array->getNbOfElems(),
783 _y_array->getPointer(),std::bind2nd(std::plus<double>(),vector[1]));
785 std::transform(_z_array->getConstPointer(),_z_array->getConstPointer()+_z_array->getNbOfElems(),
786 _z_array->getPointer(),std::bind2nd(std::plus<double>(),vector[2]));
789 void MEDCouplingCMesh::scale(const double *point, double factor)
793 DataArrayDouble *c=getCoordsAt(i);
796 double *coords=c->getPointer();
797 int lgth=c->getNbOfElems();
798 std::transform(coords,coords+lgth,coords,std::bind2nd(std::minus<double>(),point[i]));
799 std::transform(coords,coords+lgth,coords,std::bind2nd(std::multiplies<double>(),factor));
800 std::transform(coords,coords+lgth,coords,std::bind2nd(std::plus<double>(),point[i]));
807 MEDCouplingMesh *MEDCouplingCMesh::mergeMyselfWith(const MEDCouplingMesh *other) const
809 //not implemented yet !
813 DataArrayDouble *MEDCouplingCMesh::getCoordinatesAndOwner() const
815 DataArrayDouble *ret=DataArrayDouble::New();
816 int spaceDim=getSpaceDimension();
817 int nbNodes=getNumberOfNodes();
818 ret->alloc(nbNodes,spaceDim);
819 double *pt=ret->getPointer();
821 getSplitNodeValues(tmp);
822 const DataArrayDouble *tabs[3]={getCoordsAt(0),getCoordsAt(1),getCoordsAt(2)};
823 const double *tabsPtr[3];
824 for(int j=0;j<spaceDim;j++)
826 tabsPtr[j]=tabs[j]->getConstPointer();
827 ret->setInfoOnComponent(j,tabs[j]->getInfoOnComponent(0).c_str());
830 for(int i=0;i<nbNodes;i++)
832 GetPosFromId(i,spaceDim,tmp,tmp2);
833 for(int j=0;j<spaceDim;j++)
834 pt[i*spaceDim+j]=tabsPtr[j][tmp2[j]];
839 DataArrayDouble *MEDCouplingCMesh::getBarycenterAndOwner() const
841 DataArrayDouble *ret=DataArrayDouble::New();
842 int spaceDim=getSpaceDimension();
843 int nbCells=getNumberOfCells();
844 ret->alloc(nbCells,spaceDim);
845 double *pt=ret->getPointer();
847 getSplitCellValues(tmp);
848 const DataArrayDouble *tabs[3]={getCoordsAt(0),getCoordsAt(1),getCoordsAt(2)};
849 std::vector<double> tabsPtr[3];
850 for(int j=0;j<spaceDim;j++)
852 int sz=tabs[j]->getNbOfElems()-1;
853 ret->setInfoOnComponent(j,tabs[j]->getInfoOnComponent(0).c_str());
854 const double *srcPtr=tabs[j]->getConstPointer();
855 tabsPtr[j].insert(tabsPtr[j].end(),srcPtr,srcPtr+sz);
856 std::transform(tabsPtr[j].begin(),tabsPtr[j].end(),srcPtr+1,tabsPtr[j].begin(),std::plus<double>());
857 std::transform(tabsPtr[j].begin(),tabsPtr[j].end(),tabsPtr[j].begin(),std::bind2nd(std::multiplies<double>(),0.5));
860 for(int i=0;i<nbCells;i++)
862 GetPosFromId(i,spaceDim,tmp,tmp2);
863 for(int j=0;j<spaceDim;j++)
864 pt[i*spaceDim+j]=tabsPtr[j][tmp2[j]];
869 void MEDCouplingCMesh::renumberCells(const int *old2NewBg, bool check) throw(INTERP_KERNEL::Exception)
871 throw INTERP_KERNEL::Exception("Functionnality of renumbering cell not available for CMesh !");
874 void MEDCouplingCMesh::fill1DUnstructuredMesh(MEDCouplingUMesh *m) const
876 const DataArrayDouble *c=getCoordsAt(0);
877 int nbOfCells=c->getNbOfElems()-1;
878 DataArrayInt *connI=DataArrayInt::New();
879 connI->alloc(nbOfCells+1,1);
880 int *ci=connI->getPointer();
881 DataArrayInt *conn=DataArrayInt::New();
882 conn->alloc(3*nbOfCells,1);
884 int *cp=conn->getPointer();
885 for(int i=0;i<nbOfCells;i++)
887 cp[3*i]=(int)INTERP_KERNEL::NORM_SEG2;
892 m->setConnectivity(conn,connI,true);
897 void MEDCouplingCMesh::fill2DUnstructuredMesh(MEDCouplingUMesh *m) const
899 const DataArrayDouble *c1=getCoordsAt(0);
900 const DataArrayDouble *c2=getCoordsAt(1);
901 int n1=c1->getNbOfElems()-1;
902 int n2=c2->getNbOfElems()-1;
903 DataArrayInt *connI=DataArrayInt::New();
904 connI->alloc(n1*n2+1,1);
905 int *ci=connI->getPointer();
906 DataArrayInt *conn=DataArrayInt::New();
907 conn->alloc(5*n1*n2,1);
909 int *cp=conn->getPointer();
911 for(int j=0;j<n2;j++)
912 for(int i=0;i<n1;i++,pos++)
914 cp[5*pos]=(int)INTERP_KERNEL::NORM_QUAD4;
915 cp[5*pos+1]=i+1+j*(n1+1);
916 cp[5*pos+2]=i+j*(n1+1);
917 cp[5*pos+3]=i+(j+1)*(n1+1);
918 cp[5*pos+4]=i+1+(j+1)*(n1+1);
921 m->setConnectivity(conn,connI,true);
926 void MEDCouplingCMesh::fill3DUnstructuredMesh(MEDCouplingUMesh *m) const
928 const DataArrayDouble *c1=getCoordsAt(0);
929 const DataArrayDouble *c2=getCoordsAt(1);
930 const DataArrayDouble *c3=getCoordsAt(2);
931 int n1=c1->getNbOfElems()-1;
932 int n2=c2->getNbOfElems()-1;
933 int n3=c3->getNbOfElems()-1;
934 DataArrayInt *connI=DataArrayInt::New();
935 connI->alloc(n1*n2*n3+1,1);
936 int *ci=connI->getPointer();
937 DataArrayInt *conn=DataArrayInt::New();
938 conn->alloc(9*n1*n2*n3,1);
940 int *cp=conn->getPointer();
942 for(int k=0;k<n3;k++)
943 for(int j=0;j<n2;j++)
944 for(int i=0;i<n1;i++,pos++)
946 cp[9*pos]=(int)INTERP_KERNEL::NORM_HEXA8;
947 int tmp=(n1+1)*(n2+1);
948 cp[9*pos+1]=i+1+j*(n1+1)+k*tmp;
949 cp[9*pos+2]=i+j*(n1+1)+k*tmp;
950 cp[9*pos+3]=i+(j+1)*(n1+1)+k*tmp;
951 cp[9*pos+4]=i+1+(j+1)*(n1+1)+k*tmp;
952 cp[9*pos+5]=i+1+j*(n1+1)+(k+1)*tmp;
953 cp[9*pos+6]=i+j*(n1+1)+(k+1)*tmp;
954 cp[9*pos+7]=i+(j+1)*(n1+1)+(k+1)*tmp;
955 cp[9*pos+8]=i+1+(j+1)*(n1+1)+(k+1)*tmp;
958 m->setConnectivity(conn,connI,true);
963 void MEDCouplingCMesh::getTinySerializationInformation(std::vector<double>& tinyInfoD, std::vector<int>& tinyInfo, std::vector<std::string>& littleStrings) const
966 double time=getTime(it,order);
969 littleStrings.clear();
970 littleStrings.push_back(getName());
971 littleStrings.push_back(getDescription());
972 littleStrings.push_back(getTimeUnit());
973 const DataArrayDouble *thisArr[3]={_x_array,_y_array,_z_array};
980 val=thisArr[i]->getNumberOfTuples();
981 st=thisArr[i]->getInfoOnComponent(0);
983 tinyInfo.push_back(val);
984 littleStrings.push_back(st);
986 tinyInfo.push_back(it);
987 tinyInfo.push_back(order);
988 tinyInfoD.push_back(time);
991 void MEDCouplingCMesh::resizeForUnserialization(const std::vector<int>& tinyInfo, DataArrayInt *a1, DataArrayDouble *a2, std::vector<std::string>& littleStrings) const
1001 void MEDCouplingCMesh::serialize(DataArrayInt *&a1, DataArrayDouble *&a2) const
1003 a1=DataArrayInt::New();
1005 const DataArrayDouble *thisArr[3]={_x_array,_y_array,_z_array};
1007 for(int i=0;i<3;i++)
1010 sz+=thisArr[i]->getNumberOfTuples();
1012 a2=DataArrayDouble::New();
1014 double *a2Ptr=a2->getPointer();
1015 for(int i=0;i<3;i++)
1017 a2Ptr=std::copy(thisArr[i]->getConstPointer(),thisArr[i]->getConstPointer()+thisArr[i]->getNumberOfTuples(),a2Ptr);
1020 void MEDCouplingCMesh::unserialization(const std::vector<double>& tinyInfoD, const std::vector<int>& tinyInfo, const DataArrayInt *a1, DataArrayDouble *a2,
1021 const std::vector<std::string>& littleStrings)
1023 setName(littleStrings[0].c_str());
1024 setDescription(littleStrings[1].c_str());
1025 setTimeUnit(littleStrings[2].c_str());
1026 DataArrayDouble **thisArr[3]={&_x_array,&_y_array,&_z_array};
1027 const double *data=a2->getConstPointer();
1028 for(int i=0;i<3;i++)
1032 (*(thisArr[i]))=DataArrayDouble::New();
1033 (*(thisArr[i]))->alloc(tinyInfo[i],1);
1034 (*(thisArr[i]))->setInfoOnComponent(0,littleStrings[i+3].c_str());
1035 std::copy(data,data+tinyInfo[i],(*(thisArr[i]))->getPointer());
1039 setTime(tinyInfoD[0],tinyInfo[3],tinyInfo[4]);
1042 void MEDCouplingCMesh::writeVTKLL(std::ostream& ofs, const std::string& cellData, const std::string& pointData) const throw(INTERP_KERNEL::Exception)
1044 throw INTERP_KERNEL::Exception("MEDCouplingCMesh::writeVTKLL : not implemented yet !");
1047 std::string MEDCouplingCMesh::getVTKDataSetType() const throw(INTERP_KERNEL::Exception)
1049 return std::string("RectilinearGrid");