]> SALOME platform Git repositories - tools/medcoupling.git/commitdiff
Salome HOME
MEDfileMesh::getNonEmptyLevels()
authorageay <ageay>
Fri, 24 Feb 2012 11:31:45 +0000 (11:31 +0000)
committerageay <ageay>
Fri, 24 Feb 2012 11:31:45 +0000 (11:31 +0000)
src/MEDLoader/MEDFileField.cxx
src/MEDLoader/MEDFileField.hxx
src/MEDLoader/Swig/MEDLoader.i
src/MEDLoader/Swig/MEDLoaderTest3.py

index d48dc5a17d0c1be69efba455aecf7408dce64580..134f1369404ecc861b93aa368d75cca29099bbc3 100644 (file)
@@ -2104,6 +2104,63 @@ std::vector<std::string>& MEDFileField1TSWithoutDAS::getInfo()
   return arr->getInfoOnComponents();
 }
 
+/*!
+ * This method has one input 'mname'. It can be null if the user is the general case where there is only one meshName lying on 'this'
+ * This method returns two things.
+ * - The absolute dimension of 'this' in first parameter. 
+ * - The available ext levels relative to the absolute dimension returned in first parameter. These relative levels are relative
+ *   to the first output parameter. The values in 'levs' will be returned in decreasing order.
+ *
+ * This method is designed for MEDFileField1TS instances that have a discritization ON_CELLS, ON_GAUSS_NE and ON_GAUSS.
+ * Only these 3 discretizations will be taken into account here.
+ *
+ * If 'this' is empty this method will throw an INTERP_KERNEL::Exception.
+ * If there is \b only node fields defined in 'this' -1 is returned and 'levs' output parameter will be empty. In this
+ * case the caller has to know the underlying mesh it refers to. By defaut it is the level 0 of the corresponding mesh.
+ *
+ * This method is usefull to make the link between meshDimension of the underlying mesh in 'this' and the levels on 'this'.
+ * It is possible (even if it is not common) that the highest level in 'this' were not equal to the meshDimension of the underlying mesh in 'this'.
+ * 
+ * Let's consider the typical following case :
+ * - a mesh 'm1' has a meshDimension 3 and has the following non empty levels
+ * [0,-1,-2] for example 'm1' lies on TETRA4, HEXA8 TRI3 and SEG2
+ * - 'f1' lies on 'm1' and is defined on 3D and 1D cells for example
+ *   TETRA4 and SEG2
+ * - 'f2' lies on 'm1' too and is defined on 2D and 1D cells for example TRI3 and SEG2
+ *
+ * In this case f1->getNonEmptyLevelsExt will return (3,[0,-2]) and f2->getNonEmptyLevelsExt will return (2,[0,-1])
+ * 
+ * To retrieve the highest level of f1 it should be done, f1->getFieldAtLevel(ON_CELLS,3-3+0);//absDim-meshDim+relativeLev
+ * To retrieve the lowest level of f1 it should be done, f1->getFieldAtLevel(ON_CELLS,3-3+(-2));//absDim-meshDim+relativeLev
+ * To retrieve the highest level of f2 it should be done, f1->getFieldAtLevel(ON_CELLS,2-3+0);//absDim-meshDim+relativeLev
+ * To retrieve the lowest level of f2 it should be done, f1->getFieldAtLevel(ON_CELLS,2-3+(-1));//absDim-meshDim+relativeLev
+ */
+int MEDFileField1TSWithoutDAS::getNonEmptyLevels(const char *mname, std::vector<int>& levs) const throw(INTERP_KERNEL::Exception)
+{
+  levs.clear();
+  int meshId=getMeshIdFromMeshName(mname);
+  std::vector<INTERP_KERNEL::NormalizedCellType> types;
+  std::vector< std::vector<TypeOfField> > typesF;
+  std::vector< std::vector<std::string> > pfls, locs;
+  _field_per_mesh[meshId]->getFieldSplitedByType(types,typesF,pfls,locs);
+  if(types.empty())
+    throw INTERP_KERNEL::Exception("MEDFileField1TSWithoutDAS::getNonEmptyLevels : 'this' is empty !");
+  std::set<INTERP_KERNEL::NormalizedCellType> st(types.begin(),types.end());
+  if(st.size()==1 && (*st.begin())==INTERP_KERNEL::NORM_ERROR)
+    return -1;
+  st.erase(INTERP_KERNEL::NORM_ERROR);
+  std::set<int> ret1;
+  for(std::set<INTERP_KERNEL::NormalizedCellType>::const_iterator it=st.begin();it!=st.end();it++)
+    {
+      const INTERP_KERNEL::CellModel& cm=INTERP_KERNEL::CellModel::GetCellModel(*it);
+      ret1.insert((int)cm.getDimension());
+    }
+  int ret=*std::max_element(ret1.begin(),ret1.end());
+  std::copy(ret1.rbegin(),ret1.rend(),std::back_insert_iterator<std::vector<int> >(levs));
+  std::transform(levs.begin(),levs.end(),levs.begin(),std::bind2nd(std::plus<int>(),-ret));
+  return ret;
+}
+
 std::vector<TypeOfField> MEDFileField1TSWithoutDAS::getTypesOfFieldAvailable() const throw(INTERP_KERNEL::Exception)
 {
   std::vector<TypeOfField> ret;
@@ -2445,6 +2502,8 @@ int MEDFileField1TSWithoutDAS::getMeshIdFromMeshName(const char *mName) const th
 {
   if(_field_per_mesh.empty())
     throw INTERP_KERNEL::Exception("MEDFileField1TSWithoutDAS::getMeshIdFromMeshName : No field set !");
+  if(mName==0)
+    return 0;
   std::string mName2(mName);
   int ret=0;
   std::vector<std::string> msg;
@@ -2867,6 +2926,42 @@ std::vector< std::pair<int,int> > MEDFileFieldMultiTSWithoutDAS::getIterations()
   return ret;
 }
 
+/*!
+ * This method has 3 inputs 'iteration' 'order' 'mname'. 'mname' can be null if the user is the general case where there is only one meshName lying on 'this'
+ * This method returns two things.
+ * - The absolute dimension of 'this' in first parameter. 
+ * - The available ext levels relative to the absolute dimension returned in first parameter. These relative levels are relative
+ *   to the first output parameter. The values in 'levs' will be returned in decreasing order.
+ *
+ * This method is designed for MEDFileFieldMultiTS instances that have a discritization ON_CELLS, ON_GAUSS_NE and ON_GAUSS.
+ * Only these 3 discretizations will be taken into account here.
+ *
+ * If 'this' is empty this method will throw an INTERP_KERNEL::Exception.
+ * If there is \b only node fields defined in 'this' -1 is returned and 'levs' output parameter will be empty. In this
+ * case the caller has to know the underlying mesh it refers to. By defaut it is the level 0 of the corresponding mesh.
+ *
+ * This method is usefull to make the link between meshDimension of the underlying mesh in 'this' and the levels on 'this'.
+ * It is possible (even if it is not common) that the highest level in 'this' were not equal to the meshDimension of the underlying mesh in 'this'.
+ * 
+ * Let's consider the typical following case :
+ * - a mesh 'm1' has a meshDimension 3 and has the following non empty levels
+ * [0,-1,-2] for example 'm1' lies on TETRA4, HEXA8 TRI3 and SEG2
+ * - 'f1' lies on 'm1' and is defined on 3D and 1D cells for example
+ *   TETRA4 and SEG2
+ * - 'f2' lies on 'm1' too and is defined on 2D and 1D cells for example TRI3 and SEG2
+ *
+ * In this case f1->getNonEmptyLevelsExt will return (3,[0,-2]) and f2->getNonEmptyLevelsExt will return (2,[0,-1])
+ * 
+ * To retrieve the highest level of f1 it should be done, f1->getFieldAtLevel(ON_CELLS,3-3+0);//absDim-meshDim+relativeLev
+ * To retrieve the lowest level of f1 it should be done, f1->getFieldAtLevel(ON_CELLS,3-3+(-2));//absDim-meshDim+relativeLev
+ * To retrieve the highest level of f2 it should be done, f1->getFieldAtLevel(ON_CELLS,2-3+0);//absDim-meshDim+relativeLev
+ * To retrieve the lowest level of f2 it should be done, f1->getFieldAtLevel(ON_CELLS,2-3+(-1));//absDim-meshDim+relativeLev
+ */
+int MEDFileFieldMultiTSWithoutDAS::getNonEmptyLevels(int iteration, int order, const char *mname, std::vector<int>& levs) const throw(INTERP_KERNEL::Exception)
+{
+  return getTimeStepEntry(iteration,order).getNonEmptyLevels(mname,levs);
+}
+
 std::vector< std::vector<TypeOfField> > MEDFileFieldMultiTSWithoutDAS::getTypesOfFieldAvailable() const throw(INTERP_KERNEL::Exception)
 {
   int lgth=_time_steps.size();
index 4bbc0570b822ce5ddfd882beacd55dbb071ee402..e31abf114534fad365602155f46aced088d18776 100644 (file)
@@ -350,6 +350,7 @@ namespace ParaMEDMEM
     void setFieldNoProfileSBT(const MEDCouplingFieldDouble *field, MEDFieldFieldGlobsReal& glob) throw(INTERP_KERNEL::Exception);
     void setFieldProfile(const MEDCouplingFieldDouble *field, const MEDFileMesh *mesh, int meshDimRelToMax, const DataArrayInt *profile, MEDFieldFieldGlobsReal& glob) throw(INTERP_KERNEL::Exception);
   public:
+    int getNonEmptyLevels(const char *mname, std::vector<int>& levs) const throw(INTERP_KERNEL::Exception);
     std::vector<TypeOfField> getTypesOfFieldAvailable() const throw(INTERP_KERNEL::Exception);
     std::vector< std::vector<std::pair<int,int> > > getFieldSplitedByType(const char *mname, std::vector<INTERP_KERNEL::NormalizedCellType>& types, std::vector< std::vector<TypeOfField> >& typesF, std::vector< std::vector<std::string> >& pfls, std::vector< std::vector<std::string> >& locs) const throw(INTERP_KERNEL::Exception);
     std::vector< std::vector<DataArrayDouble *> > getFieldSplitedByType2(const char *mname, std::vector<INTERP_KERNEL::NormalizedCellType>& types, std::vector< std::vector<TypeOfField> >& typesF, std::vector< std::vector<std::string> >& pfls, std::vector< std::vector<std::string> >& locs) const throw(INTERP_KERNEL::Exception);
@@ -413,6 +414,7 @@ namespace ParaMEDMEM
     static MEDFileFieldMultiTSWithoutDAS *New(med_idt fid, const char *fieldName, int id, int ft, const std::vector<std::string>& infos, int nbOfStep) throw(INTERP_KERNEL::Exception);
     int getNumberOfTS() const;
     std::vector< std::pair<int,int> > getIterations() const;
+    int getNonEmptyLevels(int iteration, int order, const char *mname, std::vector<int>& levs) const throw(INTERP_KERNEL::Exception);
     std::vector< std::vector<TypeOfField> > getTypesOfFieldAvailable() const throw(INTERP_KERNEL::Exception);
     std::vector< std::vector< std::pair<int,int> > > getFieldSplitedByType(int iteration, int order, const char *mname, std::vector<INTERP_KERNEL::NormalizedCellType>& types, std::vector< std::vector<TypeOfField> >& typesF, std::vector< std::vector<std::string> >& pfls, std::vector< std::vector<std::string> >& locs) const throw(INTERP_KERNEL::Exception);
     std::vector< std::vector<DataArrayDouble *> > getFieldSplitedByType2(int iteration, int order, const char *mname, std::vector<INTERP_KERNEL::NormalizedCellType>& types, std::vector< std::vector<TypeOfField> >& typesF, std::vector< std::vector<std::string> >& pfls, std::vector< std::vector<std::string> >& locs) const throw(INTERP_KERNEL::Exception);
index b83fbfeb9bbab5820b373d84dc7d98211a835ba5..893661373842925dea8008288df7023c4a92bc68 100644 (file)
@@ -701,6 +701,16 @@ namespace ParaMEDMEM
            return ret2;
          }
 
+         PyObject *getNonEmptyLevels(const char *mname=0) const throw(INTERP_KERNEL::Exception)
+         {
+           std::vector<int> ret1;
+           int ret0=self->getNonEmptyLevels(mname,ret1);
+           PyObject *elt=PyTuple_New(2);
+           PyTuple_SetItem(elt,0,SWIG_From_int(ret0));
+           PyTuple_SetItem(elt,1,convertIntArrToPyList2(ret1));
+           return elt;
+         }
+
          PyObject *getFieldSplitedByType(const char *mname=0) const throw(INTERP_KERNEL::Exception)
          {
            std::vector<INTERP_KERNEL::NormalizedCellType> types;
@@ -891,6 +901,16 @@ namespace ParaMEDMEM
            return ret2;
          }
 
+         PyObject *getNonEmptyLevels(int iteration, int order, const char *mname=0) const throw(INTERP_KERNEL::Exception)
+         {
+           std::vector<int> ret1;
+           int ret0=self->getNonEmptyLevels(iteration,order,mname,ret1);
+           PyObject *elt=PyTuple_New(2);
+           PyTuple_SetItem(elt,0,SWIG_From_int(ret0));
+           PyTuple_SetItem(elt,1,convertIntArrToPyList2(ret1));
+           return elt;
+         }
+
          PyObject *getFieldSplitedByType(int iteration, int order, const char *mname=0) const throw(INTERP_KERNEL::Exception)
          {
            std::vector<INTERP_KERNEL::NormalizedCellType> types;
index 79e6a639ec67653d3abc91ae03225549eac2f0a9..08b84a70bac6ae8e5320f094a3e07d0e89070371 100644 (file)
@@ -659,6 +659,7 @@ class MEDLoaderTest(unittest.TestCase):
         da=DataArrayInt.New(); da.setValues([1,2,4,5,7,8],6,1) ; da.setName("sup1Node")
         #
         ff1.setFieldProfile(f1,mm1,0,da)
+        self.assertEqual(ff1.getNonEmptyLevels(),(-1, []))
         ff1.write(fname,0)
         #
         vals,pfl=ff1.getFieldWithProfile(ON_NODES,0,mm1) ; vals.setName("")
@@ -972,6 +973,76 @@ class MEDLoaderTest(unittest.TestCase):
         f4=MEDLoader.ReadFieldCell(fname,"3DSurfMesh_2",0,"VectorFieldOnCells2",0,1)
         self.assertTrue(f4.isEqual(f2,1e-12,1e-12))
         pass
+
+    def testMEDLoaderMultiLevelCellField1(self):
+        fname="Pyfile42.med"
+        m2,m1,m0,f2,f1,f0,p,n2,n1,n0,fns,fids,grpns,famIdsPerGrp=MEDLoaderDataForTest.buildMultiLevelMesh_1()
+        m=MEDFileUMesh.New()
+        m.setCoords(m2.getCoords())
+        m.setMeshAtLevel(0,m2)
+        m.setMeshAtLevel(-1,m1)
+        m.setMeshAtLevel(-2,m0)
+        m.write(fname,2)
+        #
+        FieldName1="Field1"
+        compNames1=["comp1","comp2","comp3"]
+        ff1=MEDFileField1TS.New()
+        da2=DataArrayDouble.New()
+        da2.alloc(m2.getNumberOfCells()*len(compNames1),1)
+        da2.iota(7.)
+        da2.rearrange(len(compNames1))
+        da2.setInfoOnComponents(compNames1)
+        f2=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME) ; f2.setName(FieldName1) ; f2.setArray(da2) ; f2.setMesh(m2) ; f2.checkCoherency()
+        ff1.setFieldNoProfileSBT(f2)
+        self.assertEqual(ff1.getNonEmptyLevels(),(2, [0]))
+        da0=DataArrayDouble.New()
+        da0.alloc(m0.getNumberOfCells()*len(compNames1),1)
+        da0.iota(190.)
+        da0.rearrange(len(compNames1))
+        da0.setInfoOnComponents(compNames1)
+        f0=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME) ; f0.setName(FieldName1) ; f0.setArray(da0) ; f0.setMesh(m0) ; f0.checkCoherency()
+        ff1.setFieldNoProfileSBT(f0)
+        self.assertEqual(ff1.getNonEmptyLevels(),(2, [0,-2]))
+        da1=DataArrayDouble.New()
+        da1.alloc(m1.getNumberOfCells()*len(compNames1),1)
+        da1.iota(90.)
+        da1.rearrange(len(compNames1))
+        da1.setInfoOnComponents(compNames1)
+        f1=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME) ; f1.setName(FieldName1) ; f1.setArray(da1) ; f1.setMesh(m1) ; f1.checkCoherency()
+        ff1.setFieldNoProfileSBT(f1)
+        self.assertEqual(ff1.getNonEmptyLevels(),(2, [0,-1,-2]))
+        #
+        ff1.write(fname,0)
+        #
+        FieldName2="Field2"
+        compNames2=["comp11","comp22"]
+        ff2=MEDFileField1TS.New()
+        da0=DataArrayDouble.New()
+        da0.alloc(m0.getNumberOfCells()*2,1)
+        da0.iota(-190.)
+        da0.rearrange(2)
+        da0.setInfoOnComponents(compNames2)
+        f0=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME) ; f0.setName(FieldName2) ; f0.setArray(da0) ; f0.setMesh(m0) ; f0.checkCoherency()
+        ff2.setFieldNoProfileSBT(f0)
+        self.assertEqual(ff2.getNonEmptyLevels(),(0, [0]))
+        da1=DataArrayDouble.New()
+        da1.alloc(m1.getNumberOfCells()*len(compNames2),1)
+        da1.iota(-90.)
+        da1.rearrange(len(compNames2))
+        da1.setInfoOnComponents(compNames2)
+        f1=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME) ; f1.setName(FieldName2) ; f1.setArray(da1) ; f1.setMesh(m1) ; f1.checkCoherency()
+        ff2.setFieldNoProfileSBT(f1)
+        self.assertEqual(ff2.getNonEmptyLevels(),(1, [0,-1]))
+        #
+        ff2.write(fname,0)
+        #
+        ff1=MEDFileField1TS.New(fname,FieldName1,-1,-1)
+        self.assertEqual(ff1.getNonEmptyLevels(),(2, [0,-1,-2]))
+        self.assertEqual(ff1.getFieldSplitedByType(),[(0, [(0, (0, 4), '', '')]), (1, [(0, (4, 84), '', '')]), (3, [(0, (84, 148), '', '')]), (4, [(0, (148, 212), '', '')])])
+        ff2=MEDFileField1TS.New(fname,FieldName2,-1,-1)
+        self.assertEqual(ff2.getNonEmptyLevels(),(1, [0,-1]))
+        self.assertEqual(ff2.getFieldSplitedByType(),[(0, [(0, (0, 4), '', '')]), (1, [(0, (4, 84), '', '')])])
+        pass
     pass
 
 unittest.main()