From d7efc960e2828a22293123258e1cae3ac36061a2 Mon Sep 17 00:00:00 2001 From: vsr Date: Fri, 12 Nov 2010 12:07:46 +0000 Subject: [PATCH] Merge from V5_1_5_BR branch 12/11/2010 --- doc/doxygen/Doxyfile_med_user.in | 8 + doc/doxygen/Makefile.am | 7 +- doc/doxygen/interpkernel.dox | 55 +- doc/doxygen/main.dox | 2 + doc/doxygen/medloader.dox | 357 ++++ src/INTERP_KERNEL/GenMathFormulae.hxx | 6 +- src/INTERP_KERNEL/InterpKernelMeshQuality.cxx | 209 +++ src/INTERP_KERNEL/InterpKernelMeshQuality.hxx | 37 + src/INTERP_KERNEL/Makefile.am | 4 +- src/INTERP_KERNEL/VolSurfUser.txx | 29 +- .../MEDCouplingAutoRefCountObjectPtr.hxx | 4 +- src/MEDCoupling/MEDCouplingCMesh.cxx | 248 ++- src/MEDCoupling/MEDCouplingCMesh.hxx | 9 + src/MEDCoupling/MEDCouplingExtrudedMesh.cxx | 28 + src/MEDCoupling/MEDCouplingExtrudedMesh.hxx | 4 + src/MEDCoupling/MEDCouplingField.cxx | 23 +- src/MEDCoupling/MEDCouplingField.hxx | 3 +- .../MEDCouplingFieldDiscretization.cxx | 165 +- .../MEDCouplingFieldDiscretization.hxx | 19 +- src/MEDCoupling/MEDCouplingFieldDouble.cxx | 198 ++- src/MEDCoupling/MEDCouplingFieldDouble.hxx | 8 + src/MEDCoupling/MEDCouplingMemArray.cxx | 269 ++- src/MEDCoupling/MEDCouplingMemArray.hxx | 21 +- src/MEDCoupling/MEDCouplingMemArray.txx | 2 + src/MEDCoupling/MEDCouplingMesh.cxx | 122 +- src/MEDCoupling/MEDCouplingMesh.hxx | 5 + src/MEDCoupling/MEDCouplingNatureOfField.hxx | 3 +- src/MEDCoupling/MEDCouplingPointSet.cxx | 31 +- src/MEDCoupling/MEDCouplingPointSet.hxx | 6 +- src/MEDCoupling/MEDCouplingRemapper.cxx | 8 +- .../MEDCouplingTimeDiscretization.cxx | 128 ++ .../MEDCouplingTimeDiscretization.hxx | 9 +- src/MEDCoupling/MEDCouplingUMesh.cxx | 419 ++++- src/MEDCoupling/MEDCouplingUMesh.hxx | 25 +- src/MEDCoupling/MEDCouplingUMeshDesc.cxx | 6 + src/MEDCoupling/MEDCouplingUMeshDesc.hxx | 2 + .../Test/MEDCouplingBasicsTest.hxx | 38 + .../Test/MEDCouplingBasicsTest1.cxx | 12 +- .../Test/MEDCouplingBasicsTest2.cxx | 964 ++++++++++- src/MEDCoupling_Swig/MEDCouplingBasicsTest.py | 1448 +++++++++++++++-- src/MEDCoupling_Swig/MEDCouplingTypemaps.i | 93 +- src/MEDCoupling_Swig/libMEDCoupling_Swig.i | 361 +++- src/MEDLoader/MEDLoader.cxx | 315 +++- src/MEDLoader/MEDLoader.hxx | 5 + src/MEDLoader/MEDLoaderBase.cxx | 25 +- src/MEDLoader/Makefile.am | 5 +- src/MEDLoader/Swig/MEDLoaderTest.py | 150 ++ src/MEDLoader/Swig/libMEDLoader_Swig.i | 13 + src/MEDLoader/Test/MEDLoaderTest.cxx | 186 ++- src/MEDLoader/Test/MEDLoaderTest.hxx | 8 + src/ParaMEDMEMTest/Makefile.am | 7 +- src/ParaMEDMEMTest/ParaMEDMEMTest.hxx | 2 + .../ParaMEDMEMTest_InterpKernelDEC.cxx | 4 +- .../ParaMEDMEMTest_NonCoincidentDEC.cxx | 3 + 54 files changed, 5647 insertions(+), 471 deletions(-) create mode 100644 doc/doxygen/medloader.dox create mode 100644 src/INTERP_KERNEL/InterpKernelMeshQuality.cxx create mode 100644 src/INTERP_KERNEL/InterpKernelMeshQuality.hxx diff --git a/doc/doxygen/Doxyfile_med_user.in b/doc/doxygen/Doxyfile_med_user.in index 95bbc0d62..ef07e414c 100644 --- a/doc/doxygen/Doxyfile_med_user.in +++ b/doc/doxygen/Doxyfile_med_user.in @@ -73,6 +73,7 @@ INPUT = @srcdir@ \ @srcdir@/../../src/INTERP_KERNEL \ @srcdir@/../../src/INTERP_KERNEL/Geometric2D \ @srcdir@/../../src/MEDCoupling \ + @srcdir@/../../src/MEDLoader \ @srcdir@/../../src/MEDMEM FILE_PATTERNS = MEDMEM_Mesh.* \ @@ -95,6 +96,7 @@ FILE_PATTERNS = MEDMEM_Mesh.* \ PlanarIntersector.* \ TargetIntersector.* \ Interpolation.* \ + InterpolationOptions.* \ InterpKernelGeo2DAbstractEdge.* \ InterpKernelGeo2DEdge.* \ InterpKernelGeo2DEdgeArcCircle.* \ @@ -111,8 +113,14 @@ FILE_PATTERNS = MEDMEM_Mesh.* \ MEDCouplingCMesh.* \ MEDCouplingExtrudedMesh.* \ MEDCouplingFieldDouble.* \ + MEDCouplingField.* \ MEDCouplingFieldDiscretization.* \ MEDCouplingTimeDiscretization.* \ + MEDCouplingTimeLabel.* \ + MEDCouplingRefCountObject.* \ + MEDCouplingMemArray.* \ + MEDCouplingRemapper.* \ + MEDLoader.* \ *.dox RECURSIVE = NO EXCLUDE = CVS diff --git a/doc/doxygen/Makefile.am b/doc/doxygen/Makefile.am index 0e2909df1..178b3c688 100644 --- a/doc/doxygen/Makefile.am +++ b/doc/doxygen/Makefile.am @@ -28,7 +28,12 @@ guidoc_DATA = images/head.png install-data-local : html-local $(INSTALL) -d $(DESTDIR)$(docdir)/gui/MED - cp -rp doc_ref_user/html/*.* $(DESTDIR)$(docdir)/gui/MED + @if test -d doc_ref_user/html ; then \ + for filen in `find doc_ref_user/html -maxdepth 1 -type f` ; do\ + echo "Installing $${filen}" ; \ + cp -rp $${filen} $(DESTDIR)$(docdir)/gui/MED ; \ + done ; \ + fi ; uninstall-local: rm -rf $(DESTDIR)$(docdir)/gui/MED diff --git a/doc/doxygen/interpkernel.dox b/doc/doxygen/interpkernel.dox index afe4b70c3..bfed9661f 100644 --- a/doc/doxygen/interpkernel.dox +++ b/doc/doxygen/interpkernel.dox @@ -214,10 +214,33 @@ interpolation. To be able to be filled by the interpolator the \c MatrixType cla \subsection InterpKerHighLevUsage high-level usage -This the simplest mode of usage of interpolator. This way is strongly -linked with MED data-structure. All interpolators is completely hidden -to you. Even sparse interpolation matrix is hidden. An exemple of -usage : +The simplest mode of usage of interpolator in sequential mode is to use REMAPPER classes. These classes fulfill HXX2SALOME rules to allow the user to use it +in coupling graphs. 2 REMAPPERS exist, ParaMEDMEM::MEDCouplingRemapper and Remapper. These classes are strongly linked to their corresponding data structure, respectively +MEDCoupling and MEDMEM. In return, all interpolation request and spare interpolation matrix are hidden from you. Here two examples of REMAPPER classes : + +- If you intend to use MEDCoupling data struture, ParaMEDMEM::MEDCouplingRemapper class should be used : + +\code +... +const char sourceFileName[]="source.med"; +MEDCouplingFieldDouble *sourceField=MEDLoader::ReadFieldCell(sourceFileName,"Source_Mesh",0,"Density",/*iteration*/0,/*order*/0); +const char targetFileName[]="target.med"; +MEDCouplingUMesh *med_target_mesh=MEDLoader::ReadUMeshFromFile(targetFileName,"Target_Mesh",0); +// +sourceField->setNature(ConservativeVolumic);//Specify nature is needed to allow remapper object to apply correct policy for denominator computation ! +MEDCouplingRemapper remapper; +remapper.setPrecision(1e-12); +remapper.setIntersectionType(INTERP_KERNEL::Triangulation); +remapper.prepare(sourceField->getMesh(),med_target_mesh,"P0P0"); +MEDCouplingFieldDouble *targetField=remapper.transferField(sourceField,/*default_value*/4.57);//Any target cell not intercepted by any source cell will have value set to 4.57. +... +// clean-up +targetField->decrRef(); +sourceField->decrRef(); +med_target_mesh->decrRef(); +\endcode + +- If you intend to use MEDMEM data structure, Remapper class should be used : \code ... @@ -244,7 +267,29 @@ As consequence of genericity of interpolators, they are usable only by instanciating an underneath mesh data structure. The two following examples show how to use interpolator at this level. -- The simplest way to use the interpolator with MED datastructure is : +- The simplest way to use interpolator with MEDCoupling datastruture is put in the following example. Note that this code is close to those used by ParaMEDMEM +to perform synchronization of meshes between processes of a MPI communicator : + +\code +... +MEDCouplingUMesh *med_source_mesh=MEDLoader::ReadUMeshFromFile("source.med","Source_mesh",0); +MEDCouplingUMesh *med_target_mesh=MEDLoader::ReadUMeshFromFile("target.med","Target_mesh",0); +MEDCouplingNormalizedUnstructuredMesh<2,2> wrap_source_mesh(med_source_mesh); +MEDCouplingNormalizedUnstructuredMesh<2,2> wrap_target_mesh(med_target_mesh); +// Go for interpolation... +INTERP_KERNEL::Interpolation2D myInterpolator; +myInterpolator.setPrecision(1e-7); +myInterpolator.setIntersectionType(INTERP_KERNEL::Geometric2D); +std::vector > resultMatrix; +INTERP_KERNEL::Matrix resultMatrix2; +// here the interpolation is performed twice for this code to show the capability of storing data of out matrix in 2 different data structures. +myInterpolator.interpolateMeshes(wrap_source_mesh,wrap_target_mesh,resultMatrix,"P0P0"); +myInterpolator.interpolateMeshes(wrap_source_mesh,wrap_target_mesh,resultMatrix2,"P0P0"); +//Ok resultMatrix and resultMatrix2 contain matrix now +... +\endcode + +- An another way to use the interpolator with MEDMEM datastructure is : \code ... diff --git a/doc/doxygen/main.dox b/doc/doxygen/main.dox index 69d054975..d7e4c3893 100644 --- a/doc/doxygen/main.dox +++ b/doc/doxygen/main.dox @@ -19,6 +19,8 @@ localization library. - Chapter \ref medcoupling describes DataStructures used for cross process exchange of meshes and fields. - Chapter \ref paramedmem describes its MPI implementation, which is called %ParaMEDMEM. +- Chapter \ref medloader describes API for I/O from or to a MED file +coming from a \ref medcoupling data structure. - Chapter \ref tools describes various tools based on MEDMEM that can be helpful for handling MED files (conversion tools and splitting tools). diff --git a/doc/doxygen/medloader.dox b/doc/doxygen/medloader.dox new file mode 100644 index 000000000..9cb490e52 --- /dev/null +++ b/doc/doxygen/medloader.dox @@ -0,0 +1,357 @@ +/*! +\page medloader MEDLoader + +\section MEDLoaderIntro Introduction + +MEDLoader is a package in charge of loading from a file or write to a file +in MED format a \ref medcoupling data structure. The fact that these +functionalities are not merged in \ref medcoupling is explained by a +willingness of reducing as much as possible the dependancies of \ref medcoupling libraries. + +As a MED file can combine several \ref medcoupling aspects in one (for exemple meshes in +MED file on different mesh dimension with families and groups) the API of MEDLoader is much more rich than simply read and write. + +MEDLoader offers \b static methods whose method names have the first +character in capital. You are intended to use these methods. The following +chapters will try to describe in details some of important ones. + +The basic idea of MEDLoader is to exploite as much as possible MED +file capabilities to store MEDCoupling data file in a MED file and +reversely to load from a MED file into a MEDCoupling data structure. +Basically, the info on components of ParaMEDMEM::DataArrayDouble +instances are stores into components and units into MED files. The +name of meshes and fields are used by MEDLoader to use it as this into +MED file. A field f with \ref ParaMEDMEM::MEDCouplingTimeDiscretization +"time discretization" set to ONE_TIME, the value of +\c f->getTime(time,iteration,order) are used by MEDLoader to store +identifies the field into MED file. All strings used by MEDLoader to +use it into MED file should fulfill the rules of MED file where length +are limited. +That's why the user should be aware of these constaints when trying to read/write a MED file using MEDLoader. +MEDLoader tries to manage that by protecting the user by throwing exceptions when the rules are not followed. + +\section MEDLoaderMainC Main concepts of MED files + +Here we will describes some of basic concepts of MED files in order to +use the best methods proposed by MEDLoader API. + +\subsection MEDLoaderMEDFileGen Basics in MED files + +First of all MEDLoader \b will \b not read MED files whose version is +\b lower \b than \b 2.2. The MEDLoader::CheckFileForRead will perform +the check of that before any attempt of read. + + +For new comers in MED file world some of basics principles are +recalled here. Let's recall basic principles that explains some of the aspect of MEDLoade API. +\anchor MEDLoaderMeshNameConstraint MED file can contain several meshes. These meshes are +discriminated by their names (two meshes could not have the same +names). By the same way a MED file can contain several fields in MED. +So MEDLoader propose to you the MEDLoader::GetMeshNames method to +discover all the mesh names contained in your file. + +A field is also discriminated by its name. The method MEDLoader::GetCellFieldNamesOnMesh and MEDLoader::GetNodeFieldNamesOnMesh are available to know all fields +respectively on cells and on nodes lying on a specified mesh. + + A field is defined by several time steps discriminated by a pair of int +(iteration,order). It is \b not possible to store 2 time steps of a same +field having the same iteration and order +number. The floatting point value attached on this couple of ids (iteration,order) is only present for information. +Static methods MEDLoader::GetCellFieldIterations and +MEDLoader::GetNodeFieldIterations return a vector of pair containing +each respectively iteration and order. + +A time step of a field lyies on one \b or \b more mesh(es) specified by its \b or \b their name. A time step of a field in +MED file could be defined on point \b and on cell \b and, \b or on gauss points \b and, \b or on point per element. + +This recalled specificities of MED file explains that it is necessary to specify +each time, at field-read time, the type of field, the iteration and order +number the mesh you are interested in. + +\subsection MEDLoaderMEDFileMesh Meshes in MED files + +In MED file meshes could combine in one unstructured mesh cells that +have different dimension. For example it is possible to mix +MED_TETRA4, MED_TRIA6, MED_SEG2, MED_POINT0, MED_POLYGON, +MED_POLYHEDRA in a same mesh. In MEDCouplingUMesh such a mix is not +allowed as described \ref MEDCouplingUMeshes "here". So to \b read such mesh it +is important to know which meshdimension you are interested to. In API +the parameter \b meshDimRelToMax discreminates the meshdim you are +interested to relatively to the maximal dimension of cells contained +in the mesh in file. + +Let's take 2 examples : + +- If you have a mesh called "MyMesh" in file "file1.med" with +MED_POLYGON, MED_TRI3, MED_SEG2 and MED_SEG3 : The max dimension of +cells is 2 (for MED_POLYGON and MED_TRI3). So if you want exclusively +cells with type MED_POLYGON and MED_TRI3 you should use : + +\code +MEDCouplingUMesh *m2D=MEDLoader::ReadUMeshFromFile("file1.med","MyMesh",0); +\endcode + +If you are interested in MED_SEG2 and MED_SEG3 you should use : + +\code +MEDCouplingUMesh *m1D=MEDLoader::ReadUMeshFromFile("file1.med","MyMesh",-1); +\endcode + +The method MEDLoader::ReadUMeshDimFromFile could +help you to have this mesh dimension. +\anchor MEDLoaderExample2 +- Consider an another mesh called "Example2" in file "file2.med" +containing MED_POLYHEDRA, MED_TETRA4, MED_QUAD8, MED_TRI6, MED_SEG2 +and MED_POINT0. In this case you will have : + +\code +assert(3==MEDLoader::ReadUMeshDimFromFile("file2.med","Example2")); +\endcode + +To get 3D cells (MED_POLYHEDRA and MED_TETRA4) you should type : +\code +MEDCouplingUMesh *m3D=MEDLoader::ReadUMeshFromFile("file2.med","Example2",0); +\endcode + +To get 2D cells (MED_TRI6 and MED_QUAD8) you should type : + +\code +MEDCouplingUMesh *m2D=MEDLoader::ReadUMeshFromFile("file2.med","Example2",-1); +\endcode + +To get 1D cells (MED_SEG2) you should type : + +\code +MEDCouplingUMesh *m1D=MEDLoader::ReadUMeshFromFile("file2.med","Example2",-2); +\endcode + +And finally for 0D cells (MED_POINT0) you will write : + +\code +MEDCouplingUMesh *m0D=MEDLoader::ReadUMeshFromFile("file2.med","Example2",-3); +\endcode + +To finish this subsection, it is important to know that MEDLoader +takes into account of the cell numbers stored in a mesh of a med +file. This renumbering allows MEDLoader to conserve the order of +MEDCoupling cells into the file. So if the renumbering of cells in MED +file is not correct an exception will be thrown. + +\subsection MEDLoaderMEDFilePoMesh Part of meshes in MED files + +A mesh contains one or more families on nodes and/or on cells. A family is a partition +(mathematical sense) of the mesh it lies to. A family can be described +by an integer field on \b all nodes and on \b all cells of a same mesh. +All cells and nodes having the same ids defines this family. This id +is called the familyId. A family is discriminated by its id. MED file +attach a name to its id to be more userfriendly. So by construction, 2 different +families could not share anything. The user can retrieve all the +families names available on a mesh with the static method MEDLoader::GetMeshFamiliesNames. + +A group is a set of families. So groups can overlap each other, +contrary to families. Groups are also discriminated by a name. As for +families the static method to retrieves the groups of a specified mesh is MEDLoader::GetMeshGroupsNames. + +MEDLoader allows you to retrieve the +corresponding "part of meshes" thanks to static methods +MEDLoader::ReadUMeshFromFamilies and MEDLoader::ReadUMeshFromGroups. +This method allows you to combine several families and groups in the +same returned mesh. + +\subsection MEDLoaderMEDFileField Reading a field at one time step in MED files + +A field at one time step on one mesh, with one entity (cell, node) +lies on all mesh on on a part of it. In this last case a definition of +a profile is needed. Even if the notions of profile on mesh and group +on mesh could appear close, these two concepts are totally +disconnected in MED file. +The aspect of profile is managed by MEDLoader, thats why this +aspect does not appear in the MEDLoader API. +So to retrieve a field on 3D cell called "F1Cell" in example file +\ref MEDLoaderExample2 "file2.med (seen in meshes section)" on a mesh "Example2" on time +step defined by iteration number 2 and iteration 3 the request will be : + +\code +MEDCouplingFieldDouble *f1Cell_3D=MEDLoader::ReadFieldCell("file2.med","Example2",0,"F1Cell",2,3); +\endcode + +To retrive the same field (same iteration) on 2D cells only the call will be : + +\code +MEDCouplingFieldDouble *f1Cell_2D=MEDLoader::ReadFieldCell("file2.med","Example2",-1,"F1Cell",2,3); +\endcode + +\subsection MEDLoaderMEDFieldsRead Reading several field time steps at a time in MED files + +It is possible with MEDLoader to read several time steps of a field at +a time. +The advantage with this approach is to avoid to read and load several +time a same mesh. This is typically recommanded to use the following +code when you desire to load all time steps of a field on cell "myField" lying on +same mesh "mesh1" in one shot : + +\code + +std::vector > timeStepsIds=MEDLoader::GetCellFieldIterations("file4.med"); +std::vector fs=MEDLoader::ReadFieldsCellOnSameMesh("file4.med","mesh1",0,"myField",timeStepsIds); + +\endcode + +\section MEDLoaderWriteMain Writing a MED file with MEDLoader + +As MEDMEM and MED file do, MEDLoader write process separates clearly +meshes from fields. The reason is that a common use case in write mode +is to write in a first time a mesh and then writes several time steps +of a same field in appended mode. + +The fact that the write process is rarely in a one shot put a +constraint on API (as MEDMEM does) to precise to MEDLoader if you intend +to append data to an existing file, or if you want to create a new +file from scratch. This explains the presence of boolean parameter \b +writeFromScratch in API of MEDLoader starting with \b +MEDLoader::Write* . + +If \b writeFromScratch parameter is set to \b true and if the file +already exists the file will be crashed and replaced by the new +corresponding data. If \b writeFromScratch parameter is set to \b false and if the +file does \b not \b exist the new file is created, but if the file +exists MEDLoader will enter in appended mode. + +Two classes of MEDLoader write methods exists when \b writeFromScratch +is set to \b false : + +- Methods \b MEDLoader::Write*Dep : The behaviour is as MEDMEM, that + is to say, the write is done without any question in file. The + responsability is let to the user because the MED file could be + corrupted. The advantage of this method is that it is faster + because no check is done. +- Methods \b MEDLoader::Write* : MEDLoader will not corrupt your file + by always trying to append data. The consequence of that is that a + read of part (and data processing) of MED file could be needed before any attempt of + writing. So these methods could be in some cases much time and memory consuming. + +The behaviour of MEDLoader when \b writeFromScratch is set to false will be precised +for each \b MEDLoader::Write* methods is the next subsections. + +\subsection MEDLoaderWriteMesh Writing one mesh in a MED file with MEDLoader + +The first think to know is that MEDLoader is using the \b meshName in +ParaMEDMEM::MEDCouplingMesh instance to put it in MED file. + +As explained in previous section \ref MEDLoaderMeshNameConstraint "here", +a mesh in MED file is discriminated by a name, so the \b meshName +\b should \b be \b non \b empty. If it is the case an +INTERP_KERNEL::Exception will be thrown. + +To write one mesh \b myMesh with name \b "myMeshName" in a MED file \b "wfile1.med" the following code should be typed : + +\code + +MEDCouplingUMesh *myMesh=...; +myMesh->setName("myMeshName"); +MEDLoader::WriteUMesh("wFile1.med",myMesh,true); + +\endcode + +With the previous code, if "wFile1.med" file existed the file is +crashed and will contain after the call only the content of myMesh +instance. + +If you desire to append a mesh in "wFile1.med" you should type : + +\code + +MEDCouplingUMesh *myMesh=...; +myMesh->setName("myMeshName"); +MEDLoader::WriteUMesh("wFile1.med",myMesh,false); + +\endcode + +With the previous code, if the "wFile1.med" had already a mesh called "myMeshName" an +INTERP_KERNEL::Exception will be thrown. + +\subsection MEDLoaderWriteMeshes Writing several meshes in a MED file with MEDLoader + +It could be interesting to write several meshes in one shot. Two +possiblities are possible : + +- Write several instances of ParaMEDMEM::MEDCouplingUMesh + lying \b on \b same \b coords \b with \b different \b mesh \b dimension. In this case the + use of MEDLoader::WriteUMeshes is the method you should + use. Typically this method should be used to write such of file + defined \ref MEDLoaderExample2 "here". + This method first checks that all instances share the same + ParaMEDMEM::DataArrayDouble instance as coords. If not an + INTERP_KERNEL::Exception will be thrown and an invocation on + ParaMEDMEM::MEDCouplingPointSet::tryToShareSameCoords will be necessary. + +- Write a partition of meshes having \b same \b mesh \b dimension, that is to say a set of + groups and families from given meshes. As in the previous case the + check of same coords will be done (if not an INTERP_KERNEL::Exception is + thrown). After this step this method will + merge (by concerving the order in input) and will simplify the + merged mesh. After this operation, the groups will be constituted by + assigning the groups names with the conresponding names of + instance. That's why all meshes have to have a not empty name and + different each other. The method to use in this case is + MEDLoader::WriteUMeshesPartition. + +For these 2 described methods the semantic of \b writeFromScratch when +\b false is the same, that is to say : no writing +(INTERP_KERNEL::Exception thrown) will be done if the +file already exists and contains already a mesh with name 'meshName' +for MEDLoader::WriteUMeshesPartition method and the name of the first +of the vector of unstructured meshes passed as first parameter of +MEDLoader::WriteUMeshes. + +\subsection MEDLoaderWriteField Writing one time step of a field in a MED file with MEDLoader + +To write \b one \b time \b step of a field from scratch with MEDLoader is to +use MEDLoader::WriteField method. The behviour of this method depends +on the value of the \b writeFromScratch paramter : + +- When \b writeFromScratch equals to \b true, this method performs two things, it +writes the underlying mesh and write the specified time step on it. + +- When \b writeFromScatch equals to \b false, this method looks that + the underlying mesh exists (by looking the content of \c field->getMesh()->getName() ) in file. If not, the behaviour is the + same that previous case with \b writeFromScratch parameter set to + \b true. If the mesh already exists, MEDLoader reads the field and + tries to apply field on it. This operation could be rather time + consuming because a read operation is performed and a reorder + operation too. If the file already contains the same field at the + same time step (iteration and order ids) the corresponding time step + will be replaced by the field passed in parameter. + +\subsection MEDLoaderWriteFields Writing several time steps of a field in a MED file with MEDLoader + +To write a serie of time steps in a "file3.med" file lying on the same +unstructured mesh the typical code +to write is the following : + +\code + +MEDCouplingFieldDouble *f=...; +MEDLoader::WriteUMesh("file3.med",static_castf->getMesh(),true); +f->setTime(1.2,1,0); +//Writing first time step with iteration==1 and order==0 +MEDLoader::WriteFieldUsingAlreadyWrittenMesh("file3.med",f); +f->setTime(1.3,2,0); +f->applyFunc("sqrt(x)"); +//Writing second time step with iteration==2 and order==0 +MEDLoader::WriteFieldUsingAlreadyWrittenMesh("file3.med",f); + +\endcode + +In the previous code, it is important to note that the values of pair +(iteration,order) should be different between two calls to avoid that +a call to MEDLoader::WriteFieldUsingAlreadyWrittenMesh overwrites a +previous call. +An another important thing is the fact that \c f->getMesh() does not be +modified. +This method of writing presents the big advantage to be fast, because +no check neither read is performed by this method. That's why contrary +to other MEDLoader::Write* method the parameter of \b writeFromScratch +is not needed here. + +*/ diff --git a/src/INTERP_KERNEL/GenMathFormulae.hxx b/src/INTERP_KERNEL/GenMathFormulae.hxx index 92de33f7c..42ce4f43f 100644 --- a/src/INTERP_KERNEL/GenMathFormulae.hxx +++ b/src/INTERP_KERNEL/GenMathFormulae.hxx @@ -61,7 +61,7 @@ namespace INTERP_KERNEL */ void computeEigenVectorForEigenValue6(const double *matrix, double eigenVal, double eps, double *eigenVector) throw(INTERP_KERNEL::Exception) { - if(fabs(eigenVal)>eps) + //if(fabs(eigenVal)>eps) { const double m9[9]={matrix[0]-eigenVal,matrix[3],matrix[5],matrix[3],matrix[1]-eigenVal,matrix[4],matrix[5],matrix[4],matrix[2]-eigenVal}; for(int i=0;i<3;i++) @@ -81,14 +81,14 @@ namespace INTERP_KERNEL } } } - else + //else { eigenVector[0]=0.; eigenVector[1]=0.; eigenVector[2]=0.; return; } - throw INTERP_KERNEL::Exception("computeEigenVector : Do not succed in finding eigen vector !"); + //throw INTERP_KERNEL::Exception("computeEigenVector : Do not succed in finding eigen vector !"); } } diff --git a/src/INTERP_KERNEL/InterpKernelMeshQuality.cxx b/src/INTERP_KERNEL/InterpKernelMeshQuality.cxx new file mode 100644 index 000000000..271771edd --- /dev/null +++ b/src/INTERP_KERNEL/InterpKernelMeshQuality.cxx @@ -0,0 +1,209 @@ +// Copyright (C) 2007-2010 CEA/DEN, EDF R&D +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + +#include "InterpKernelMeshQuality.hxx" + +#include +#include +#include +#include + +double INTERP_KERNEL::quadSkew(const double *coo) +{ + double pa0[3]={ + coo[3]+coo[6]-coo[0]-coo[9], + coo[4]+coo[7]-coo[1]-coo[10], + coo[5]+coo[8]-coo[2]-coo[11] + }; + double pa1[3]={ + coo[6]+coo[9]-coo[0]-coo[3], + coo[7]+coo[10]-coo[1]-coo[4], + coo[8]+coo[11]-coo[2]-coo[5], + }; + double l0=sqrt(pa0[0]*pa0[0]+pa0[1]*pa0[1]+pa0[2]*pa0[2]); + double l1=sqrt(pa1[0]*pa1[0]+pa1[1]*pa1[1]+pa1[2]*pa1[2]); + if(l0<1.e-15) + return 0.; + if(l1<1.e-15) + return 0.; + pa0[0]/=l0; pa0[1]/=l0; pa0[2]/=l0; + pa1[0]/=l1; pa1[1]/=l1; pa1[2]/=l1; + return pa0[0]*pa1[0]+pa0[1]*pa1[1]+pa0[2]*pa1[2]; +} + +double INTERP_KERNEL::quadEdgeRatio(const double *coo) +{ + double a2=(coo[3]-coo[0])*(coo[3]-coo[0])+(coo[4]-coo[1])*(coo[4]-coo[1])+(coo[5]-coo[2])*(coo[5]-coo[2]); + double b2=(coo[6]-coo[3])*(coo[6]-coo[3])+(coo[7]-coo[4])*(coo[7]-coo[4])+(coo[8]-coo[5])*(coo[8]-coo[5]); + double c2=(coo[9]-coo[6])*(coo[9]-coo[6])+(coo[10]-coo[7])*(coo[10]-coo[7])+(coo[11]-coo[8])*(coo[11]-coo[8]); + double d2=(coo[0]-coo[9])*(coo[0]-coo[9])+(coo[1]-coo[10])*(coo[1]-coo[10])+(coo[2]-coo[11])*(coo[2]-coo[11]); + double mab=a2Mcd?Mab:Mcd; + if(m2>1.e-15) + return sqrt(M2/m2); + else + return std::numeric_limits::max(); +} + +double INTERP_KERNEL::quadAspectRatio(const double *coo) +{ + double a=sqrt((coo[3]-coo[0])*(coo[3]-coo[0])+(coo[4]-coo[1])*(coo[4]-coo[1])+(coo[5]-coo[2])*(coo[5]-coo[2])); + double b=sqrt((coo[6]-coo[3])*(coo[6]-coo[3])+(coo[7]-coo[4])*(coo[7]-coo[4])+(coo[8]-coo[5])*(coo[8]-coo[5])); + double c=sqrt((coo[9]-coo[6])*(coo[9]-coo[6])+(coo[10]-coo[7])*(coo[10]-coo[7])+(coo[11]-coo[8])*(coo[11]-coo[8])); + double d=sqrt((coo[0]-coo[9])*(coo[0]-coo[9])+(coo[1]-coo[10])*(coo[1]-coo[10])+(coo[2]-coo[11])*(coo[2]-coo[11])); + double ma=a>b?a:b; + double mb=c>d?c:d; + double hm=ma>mb?ma:mb; + double ab[3]={(coo[4]-coo[1])*(coo[8]-coo[5])-(coo[7]-coo[4])*(coo[5]-coo[2]), + (coo[5]-coo[2])*(coo[6]-coo[3])-(coo[3]-coo[0])*(coo[8]-coo[5]), + (coo[3]-coo[0])*(coo[7]-coo[4])-(coo[4]-coo[1])*(coo[6]-coo[3])}; + double cd[3]={(coo[10]-coo[7])*(coo[2]-coo[11])-(coo[1]-coo[10])*(coo[11]-coo[8]), + (coo[11]-coo[8])*(coo[0]-coo[9])-(coo[9]-coo[6])*(coo[2]-coo[11]), + (coo[9]-coo[6])*(coo[1]-coo[10])-(coo[10]-coo[7])*(coo[0]-coo[9])}; + double e=sqrt(ab[0]*ab[0]+ab[1]*ab[1]+ab[2]*ab[2])+sqrt(cd[0]*cd[0]+cd[1]*cd[1]+cd[2]*cd[2]); + if(d>1e-15) + return 0.5*(a+b+c+d)*hm/e; + else + return std::numeric_limits::max(); +} + +double INTERP_KERNEL::quadWarp(const double *coo) +{ + double e0[3]={coo[3]-coo[0],coo[4]-coo[1],coo[5]-coo[2]}; + double e1[3]={coo[6]-coo[3],coo[7]-coo[4],coo[8]-coo[5]}; + double e2[3]={coo[9]-coo[6],coo[10]-coo[7],coo[11]-coo[8]}; + double e3[3]={coo[0]-coo[9],coo[1]-coo[10],coo[2]-coo[11]}; + + double n0[3]={e3[1]*e0[2]-e3[2]*e0[1],e3[2]*e0[0]-e3[0]*e0[2],e3[0]*e0[1]-e3[1]*e0[0]}; + double n1[3]={e0[1]*e1[2]-e0[2]*e1[1],e0[2]*e1[0]-e0[0]*e1[2],e0[0]*e1[1]-e0[1]*e1[0]}; + double n2[3]={e1[1]*e2[2]-e1[2]*e2[1],e1[2]*e2[0]-e1[0]*e2[2],e1[0]*e2[1]-e1[1]*e2[0]}; + double n3[3]={e2[1]*e3[2]-e2[2]*e3[1],e2[2]*e3[0]-e2[0]*e3[2],e2[0]*e3[1]-e2[1]*e3[0]}; + + double l0=sqrt(n0[0]*n0[0]+n0[1]*n0[1]+n0[2]*n0[2]); + double l1=sqrt(n1[0]*n1[0]+n1[1]*n1[1]+n1[2]*n1[2]); + double l2=sqrt(n2[0]*n2[0]+n2[1]*n2[1]+n2[2]*n2[2]); + double l3=sqrt(n3[0]*n3[0]+n3[1]*n3[1]+n3[2]*n3[2]); + + if(l0<1.e-15 || l1<1.e-15 || l2<1.e-15 || l3<1e-15) + return std::numeric_limits::min(); + + double warp=std::min(n0[0]/l0*n2[0]/l2+n0[1]/l0*n2[1]/l2+n0[2]/l0*n2[2]/l2,n1[0]/l1*n3[0]/l3+n1[1]/l1*n3[1]/l3+n1[2]/l1*n3[2]/l3); + return warp*warp*warp; +} + +double INTERP_KERNEL::triEdgeRatio(const double *coo) +{ + double a2=(coo[3]-coo[0])*(coo[3]-coo[0])+(coo[4]-coo[1])*(coo[4]-coo[1])+(coo[5]-coo[2])*(coo[5]-coo[2]); + double b2=(coo[6]-coo[3])*(coo[6]-coo[3])+(coo[7]-coo[4])*(coo[7]-coo[4])+(coo[8]-coo[5])*(coo[8]-coo[5]); + double c2=(coo[0]-coo[6])*(coo[0]-coo[6])+(coo[1]-coo[7])*(coo[1]-coo[7])+(coo[2]-coo[8])*(coo[2]-coo[8]); + double mab=a2mab?mab:c2; + double M2=c2>Mab?c2:Mab; + if(m2>1.e-15) + return sqrt(M2/m2); + else + return std::numeric_limits::max(); +} + +double INTERP_KERNEL::triAspectRatio(const double *coo) +{ + double a=sqrt((coo[3]-coo[0])*(coo[3]-coo[0])+(coo[4]-coo[1])*(coo[4]-coo[1])+(coo[5]-coo[2])*(coo[5]-coo[2])); + double b=sqrt((coo[6]-coo[3])*(coo[6]-coo[3])+(coo[7]-coo[4])*(coo[7]-coo[4])+(coo[8]-coo[5])*(coo[8]-coo[5])); + double c=sqrt((coo[0]-coo[6])*(coo[0]-coo[6])+(coo[1]-coo[7])*(coo[1]-coo[7])+(coo[2]-coo[8])*(coo[2]-coo[8])); + + double hm=a>b?a:b; + hm=hm>c?hm:c; + + double ab[3]={(coo[4]-coo[1])*(coo[8]-coo[5])-(coo[7]-coo[4])*(coo[5]-coo[2]), + (coo[5]-coo[2])*(coo[6]-coo[3])-(coo[3]-coo[0])*(coo[8]-coo[5]), + (coo[3]-coo[0])*(coo[7]-coo[4])-(coo[4]-coo[1])*(coo[6]-coo[3])}; + double d=sqrt(ab[0]*ab[0]+ab[1]*ab[1]+ab[2]*ab[2]); + static const double normalizeCoeff=sqrt(3.)/6.; + if(d>1.e-15) + return normalizeCoeff*hm*(a+b+c)/d; + else + return std::numeric_limits::max(); +} + +double INTERP_KERNEL::tetraEdgeRatio(const double *coo) +{ + double a[3]={coo[3]-coo[0],coo[4]-coo[1],coo[5]-coo[2]}; + double b[3]={coo[6]-coo[3],coo[7]-coo[4],coo[8]-coo[5]}; + double c[3]={coo[0]-coo[6],coo[1]-coo[7],coo[2]-coo[8]}; + double d[3]={coo[9]-coo[0],coo[10]-coo[1],coo[11]-coo[2]}; + double e[3]={coo[9]-coo[3],coo[10]-coo[4],coo[11]-coo[5]}; + double f[3]={coo[9]-coo[6],coo[10]-coo[7],coo[11]-coo[8]}; + + double l2[6]= + {a[0]*a[0]+a[1]*a[1]+a[2]*a[2], + b[0]*b[0]+b[1]*b[1]+b[2]*b[2], + c[0]*c[0]+c[1]*c[1]+c[2]*c[2], + d[0]*d[0]+d[1]*d[1]+d[2]*d[2], + e[0]*e[0]+e[1]*e[1]+e[2]*e[2], + f[0]*f[0]+f[1]*f[1]+f[2]*f[2]}; + + double M2=*std::max_element(l2,l2+6); + double m2=*std::min_element(l2,l2+6); + if(m2>1e-15) + return sqrt(M2/m2); + else + return std::numeric_limits::max(); +} + +double INTERP_KERNEL::tetraAspectRatio(const double *coo) +{ + static const double normalizeCoeff=sqrt(6.)/12.; + double ab[3]={coo[3]-coo[0],coo[4]-coo[1],coo[5]-coo[2]}; + double ac[3]={coo[6]-coo[0],coo[7]-coo[1],coo[8]-coo[2]}; + double ad[3]={coo[9]-coo[0],coo[10]-coo[1],coo[11]-coo[2]}; + double detTet=(ab[0]*(ac[1]*ad[2]-ac[2]*ad[1]))+(ab[1]*(ac[2]*ad[0]-ac[0]*ad[2]))+(ab[2]*(ac[0]*ad[1]-ac[1]*ad[0])); + //if(detTet<1.e-15) + // return std::numeric_limits::max(); + double bc[3]={coo[6]-coo[3],coo[7]-coo[4],coo[8]-coo[5]}; + double bd[3]={coo[9]-coo[3],coo[10]-coo[4],coo[11]-coo[5]}; + double cd[3]={coo[9]-coo[6],coo[10]-coo[7],coo[11]-coo[8]}; + + double ab2=ab[0]*ab[0]+ab[1]*ab[1]+ab[2]*ab[2]; + double bc2=bc[0]*bc[0]+bc[1]*bc[1]+bc[2]*bc[2]; + double ac2=ac[0]*ac[0]+ac[1]*ac[1]+ac[2]*ac[2]; + double ad2=ad[0]*ad[0]+ad[1]*ad[1]+ad[2]*ad[2]; + double bd2=bd[0]*bd[0]+bd[1]*bd[1]+bd[2]*bd[2]; + double cd2=cd[0]*cd[0]+cd[1]*cd[1]+cd[2]*cd[2]; + + double A=ab2>bc2?ab2:bc2; + double B=ac2>ad2?ac2:ad2; + double C=bd2>cd2?bd2:cd2; + double D=A>B?A:B; + double hm=D>C?sqrt(D):sqrt(C); + + bd[0]=ab[1]*bc[2]-ab[2]*bc[1]; bd[1]=ab[2]*bc[0]-ab[0]*bc[2]; bd[2]=ab[0]*bc[1]-ab[1]*bc[0]; + A=sqrt(bd[0]*bd[0]+bd[1]*bd[1]+bd[2]*bd[2]); + bd[0]=ab[1]*ad[2]-ab[2]*ad[1]; bd[1]=ab[2]*ad[0]-ab[0]*ad[2]; bd[2]=ab[0]*ad[1]-ab[1]*ad[0]; + B=sqrt(bd[0]*bd[0]+bd[1]*bd[1]+bd[2]*bd[2]); + bd[0]=ac[1]*ad[2]-ac[2]*ad[1]; bd[1]=ac[2]*ad[0]-ac[0]*ad[2]; bd[2]=ac[0]*ad[1]-ac[1]*ad[0]; + C=sqrt(bd[0]*bd[0]+bd[1]*bd[1]+bd[2]*bd[2]); + bd[0]=bc[1]*cd[2]-bc[2]*cd[1]; bd[1]=bc[2]*cd[0]-bc[0]*cd[2]; bd[2]=bc[0]*cd[1]-bc[1]*cd[0]; + D=sqrt(bd[0]*bd[0]+bd[1]*bd[1]+bd[2]*bd[2]); + return normalizeCoeff*hm*(A+B+C+D)/fabs(detTet); +} diff --git a/src/INTERP_KERNEL/InterpKernelMeshQuality.hxx b/src/INTERP_KERNEL/InterpKernelMeshQuality.hxx new file mode 100644 index 000000000..2f11bb4d1 --- /dev/null +++ b/src/INTERP_KERNEL/InterpKernelMeshQuality.hxx @@ -0,0 +1,37 @@ +// Copyright (C) 2007-2010 CEA/DEN, EDF R&D +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + +#ifndef __INTERPKERNELMESHQUALITY_HXX_ +#define __INTERPKERNELMESHQUALITY_HXX__ + +#include "INTERPKERNELDefines.hxx" + +namespace INTERP_KERNEL +{ + INTERPKERNEL_EXPORT double quadSkew(const double *coo); + INTERPKERNEL_EXPORT double quadEdgeRatio(const double *coo); + INTERPKERNEL_EXPORT double quadAspectRatio(const double *coo); + INTERPKERNEL_EXPORT double quadWarp(const double *coo); + INTERPKERNEL_EXPORT double triEdgeRatio(const double *coo); + INTERPKERNEL_EXPORT double triAspectRatio(const double *coo); + INTERPKERNEL_EXPORT double tetraEdgeRatio(const double *coo); + INTERPKERNEL_EXPORT double tetraAspectRatio(const double *coo); +} + +#endif diff --git a/src/INTERP_KERNEL/Makefile.am b/src/INTERP_KERNEL/Makefile.am index afbe7285d..e3dfc56cb 100644 --- a/src/INTERP_KERNEL/Makefile.am +++ b/src/INTERP_KERNEL/Makefile.am @@ -43,6 +43,7 @@ PointLocator2DIntersector.hxx \ PointLocator2DIntersector.txx \ INTERPKERNELDefines.hxx \ InterpKernelMatrix.hxx \ +InterpKernelMeshQuality.hxx \ Interpolation.hxx \ Interpolation.txx \ Interpolation2D.hxx \ @@ -187,7 +188,8 @@ dist_libinterpkernel_la_SOURCES = \ CellModel.cxx \ UnitTetraIntersectionBary.cxx \ InterpolationOptions.cxx \ - DirectedBoundingBox.cxx + DirectedBoundingBox.cxx \ + InterpKernelMeshQuality.cxx libinterpkernel_la_CPPFLAGS=-I$(srcdir)/Geometric2D -I$(srcdir)/Bases diff --git a/src/INTERP_KERNEL/VolSurfUser.txx b/src/INTERP_KERNEL/VolSurfUser.txx index 5a0109a43..f14ba420a 100644 --- a/src/INTERP_KERNEL/VolSurfUser.txx +++ b/src/INTERP_KERNEL/VolSurfUser.txx @@ -240,10 +240,35 @@ namespace INTERP_KERNEL case NORM_PYRA5: { double tmp[3]; - computePolygonBarycenter3D(connec,lgth,coords,tmp); + computePolygonBarycenter3D(connec,lgth-1,coords,tmp); res[0]=(coords[3*OTT::coo2C(connec[4])]+3.*tmp[0])/4.; res[1]=(coords[3*OTT::coo2C(connec[4])+1]+3.*tmp[1])/4.; - res[1]=(coords[3*OTT::coo2C(connec[4])+2]+3.*tmp[2])/4.; + res[2]=(coords[3*OTT::coo2C(connec[4])+2]+3.*tmp[2])/4.; + break; + } + case NORM_HEXA8: + { + const int conn[29]={ + OTT::coo2C(connec[0]),OTT::coo2C(connec[1]),OTT::coo2C(connec[2]),OTT::coo2C(connec[3]),-1, + OTT::coo2C(connec[4]),OTT::coo2C(connec[7]),OTT::coo2C(connec[6]),OTT::coo2C(connec[5]),-1, + OTT::coo2C(connec[0]),OTT::coo2C(connec[3]),OTT::coo2C(connec[7]),OTT::coo2C(connec[4]),-1, + OTT::coo2C(connec[3]),OTT::coo2C(connec[2]),OTT::coo2C(connec[6]),OTT::coo2C(connec[7]),-1, + OTT::coo2C(connec[2]),OTT::coo2C(connec[1]),OTT::coo2C(connec[5]),OTT::coo2C(connec[6]),-1, + OTT::coo2C(connec[0]),OTT::coo2C(connec[4]),OTT::coo2C(connec[5]),OTT::coo2C(connec[1]), + }; + barycenterOfPolyhedron(conn,29,coords,res); + break; + } + case NORM_PENTA6: + { + const int conn[22]={ + OTT::coo2C(connec[0]),OTT::coo2C(connec[1]),OTT::coo2C(connec[2]),-1, + OTT::coo2C(connec[3]),OTT::coo2C(connec[5]),OTT::coo2C(connec[4]),-1, + OTT::coo2C(connec[0]),OTT::coo2C(connec[2]),OTT::coo2C(connec[5]),OTT::coo2C(connec[3]),-1, + OTT::coo2C(connec[2]),OTT::coo2C(connec[1]),OTT::coo2C(connec[4]),OTT::coo2C(connec[5]),-1, + OTT::coo2C(connec[1]),OTT::coo2C(connec[0]),OTT::coo2C(connec[3]),OTT::coo2C(connec[4]) + }; + barycenterOfPolyhedron(conn,22,coords,res); break; } case NORM_POLYHED: diff --git a/src/MEDCoupling/MEDCouplingAutoRefCountObjectPtr.hxx b/src/MEDCoupling/MEDCouplingAutoRefCountObjectPtr.hxx index 1d65fd240..9a30b7d8f 100644 --- a/src/MEDCoupling/MEDCouplingAutoRefCountObjectPtr.hxx +++ b/src/MEDCoupling/MEDCouplingAutoRefCountObjectPtr.hxx @@ -31,8 +31,8 @@ namespace ParaMEDMEM MEDCouplingAutoRefCountObjectPtr(const MEDCouplingAutoRefCountObjectPtr& other):_ptr(0) { referPtr(other._ptr); } MEDCouplingAutoRefCountObjectPtr(T *ptr=0):_ptr(ptr) { } ~MEDCouplingAutoRefCountObjectPtr() { destroyPtr(); } - MEDCouplingAutoRefCountObjectPtr &operator=(const MEDCouplingAutoRefCountObjectPtr& other) { destroyPtr(); referPtr(other._ptr); return *this; } - MEDCouplingAutoRefCountObjectPtr &operator=(T *ptr) { destroyPtr(); _ptr=ptr; return *this; } + MEDCouplingAutoRefCountObjectPtr &operator=(const MEDCouplingAutoRefCountObjectPtr& other) { if(_ptr!=other._ptr) { destroyPtr(); referPtr(other._ptr); } return *this; } + MEDCouplingAutoRefCountObjectPtr &operator=(T *ptr) { if(_ptr!=ptr) { destroyPtr(); _ptr=ptr; } return *this; } T *operator->() { return _ptr ; } const T *operator->() const { return _ptr; } T& operator*() { return *_ptr; } diff --git a/src/MEDCoupling/MEDCouplingCMesh.cxx b/src/MEDCoupling/MEDCouplingCMesh.cxx index a69362f47..e7d9bcd3a 100644 --- a/src/MEDCoupling/MEDCouplingCMesh.cxx +++ b/src/MEDCoupling/MEDCouplingCMesh.cxx @@ -18,6 +18,7 @@ // #include "MEDCouplingCMesh.hxx" +#include "MEDCouplingUMesh.hxx" #include "MEDCouplingMemArray.hxx" #include "MEDCouplingFieldDouble.hxx" @@ -129,12 +130,36 @@ bool MEDCouplingCMesh::isEqual(const MEDCouplingMesh *other, double prec) const return true; } +bool MEDCouplingCMesh::isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const +{ + const MEDCouplingCMesh *otherC=dynamic_cast(other); + if(!otherC) + return false; + const DataArrayDouble *thisArr[3]={_x_array,_y_array,_z_array}; + const DataArrayDouble *otherArr[3]={otherC->_x_array,otherC->_y_array,otherC->_z_array}; + for(int i=0;i<3;i++) + { + if((thisArr[i]!=0 && otherArr[i]==0) || (thisArr[i]==0 && otherArr[i]!=0)) + return false; + if(thisArr[i]) + if(!thisArr[i]->isEqualWithoutConsideringStr(*otherArr[i],prec)) + return false; + } + return true; +} + void MEDCouplingCMesh::checkDeepEquivalWith(const MEDCouplingMesh *other, int cellCompPol, double prec, DataArrayInt *&cellCor, DataArrayInt *&nodeCor) const throw(INTERP_KERNEL::Exception) { throw INTERP_KERNEL::Exception("Not implemented yet !"); } +void MEDCouplingCMesh::checkDeepEquivalOnSameNodesWith(const MEDCouplingMesh *other, int cellCompPol, double prec, + DataArrayInt *&cellCor) const throw(INTERP_KERNEL::Exception) +{ + throw INTERP_KERNEL::Exception("Not implemented yet !"); +} + void MEDCouplingCMesh::checkCoherency() const throw(INTERP_KERNEL::Exception) { const char msg0[]="Invalid "; @@ -212,7 +237,7 @@ void MEDCouplingCMesh::getSplitCellValues(int *res) const for(int l=0;lgetNbOfElems()-1; res[spaceDim-l-1]=val; } @@ -224,7 +249,7 @@ void MEDCouplingCMesh::getSplitNodeValues(int *res) const for(int l=0;lgetNbOfElems(); res[spaceDim-l-1]=val; } @@ -321,7 +346,15 @@ void MEDCouplingCMesh::getNodeIdsOfCell(int cellId, std::vector& conn) cons void MEDCouplingCMesh::getCoordinatesOfNode(int nodeId, std::vector& coo) const { - //not implemented yet + int tmp[3]; + int spaceDim=getSpaceDimension(); + getSplitNodeValues(tmp); + const DataArrayDouble *tabs[3]={getCoordsAt(0),getCoordsAt(1),getCoordsAt(2)}; + int tmp2[3]; + getPosFromId(nodeId,spaceDim,tmp,tmp2); + for(int j=0;jgetConstPointer()[tmp2[j]]); } std::string MEDCouplingCMesh::simpleRepr() const @@ -403,27 +436,94 @@ void MEDCouplingCMesh::setCoords(DataArrayDouble *coordsX, DataArrayDouble *coor declareAsNew(); } +MEDCouplingUMesh *MEDCouplingCMesh::buildUnstructured() const +{ + int spaceDim=getSpaceDimension(); + MEDCouplingUMesh *ret=MEDCouplingUMesh::New(getName(),spaceDim); + DataArrayDouble *coords=getCoordinatesAndOwner(); + ret->setCoords(coords); + coords->decrRef(); + switch(spaceDim) + { + case 1: + fill1DUnstructuredMesh(ret); + break; + case 2: + fill2DUnstructuredMesh(ret); + break; + case 3: + fill3DUnstructuredMesh(ret); + break; + default: + throw INTERP_KERNEL::Exception("MEDCouplingCMesh::buildUnstructured : big problem spacedim must be in 1,2 or 3 !"); + }; + return ret; +} + MEDCouplingMesh *MEDCouplingCMesh::buildPart(const int *start, const int *end) const { - //not implemented yet ! - return 0; + MEDCouplingUMesh *um=buildUnstructured(); + MEDCouplingMesh *ret=um->buildPart(start,end); + um->decrRef(); + return ret; } MEDCouplingMesh *MEDCouplingCMesh::buildPartAndReduceNodes(const int *start, const int *end, DataArrayInt*& arr) const { - //not implemented yet ! - return 0; + MEDCouplingUMesh *um=buildUnstructured(); + MEDCouplingMesh *ret=um->buildPartAndReduceNodes(start,end,arr); + um->decrRef(); + return ret; } void MEDCouplingCMesh::getBoundingBox(double *bbox) const { - //not implemented yet ! + int dim=getSpaceDimension(); + int j=0; + for (int idim=0; idimgetConstPointer(); + int nb=c->getNbOfElems(); + bbox[2*j]=coords[0]; + bbox[2*j+1]=coords[nb-1]; + j++; + } + } } MEDCouplingFieldDouble *MEDCouplingCMesh::getMeasureField(bool isAbs) const { - //not implemented yet ! - return 0; + std::string name="MeasureOfMesh_"; + name+=getName(); + int nbelem=getNumberOfCells(); + MEDCouplingFieldDouble *field=MEDCouplingFieldDouble::New(ON_CELLS); + field->setName(name.c_str()); + DataArrayDouble* array=DataArrayDouble::New(); + array->alloc(nbelem,1); + double *area_vol=array->getPointer(); + field->setArray(array) ; + array->decrRef(); + field->setMesh(const_cast(this)); + int tmp[3]; + getSplitCellValues(tmp); + int dim=getSpaceDimension(); + const double **thisArr=new const double *[dim]; + const DataArrayDouble *thisArr2[3]={_x_array,_y_array,_z_array}; + for(int i=0;igetConstPointer(); + for(int icell=0;icellgetConstPointer(); + int nbOfNodes=getCoordsAt(i)->getNbOfElems(); + double ref=pos[i]; + const double *w=std::find_if(d,d+nbOfNodes,std::bind2nd(std::greater(),ref)); + int w2=std::distance(d,w); + if(w2getPointer(),std::bind2nd(std::plus(),vector[2])); } +void MEDCouplingCMesh::scale(const double *point, double factor) +{ + for(int i=0;i<3;i++) + { + DataArrayDouble *c=getCoordsAt(i); + if(c) + { + double *coords=c->getPointer(); + int lgth=c->getNbOfElems(); + std::transform(coords,coords+lgth,coords,std::bind2nd(std::minus(),point[i])); + std::transform(coords,coords+lgth,coords,std::bind2nd(std::multiplies(),factor)); + std::transform(coords,coords+lgth,coords,std::bind2nd(std::plus(),point[i])); + c->declareAsNew(); + } + } + updateTime(); +} + MEDCouplingMesh *MEDCouplingCMesh::mergeMyselfWith(const MEDCouplingMesh *other) const { //not implemented yet ! @@ -536,6 +671,95 @@ void MEDCouplingCMesh::renumberCells(const int *old2NewBg, bool check) throw(INT throw INTERP_KERNEL::Exception("Functionnality of renumbering cell not available for CMesh !"); } +void MEDCouplingCMesh::fill1DUnstructuredMesh(MEDCouplingUMesh *m) const +{ + const DataArrayDouble *c=getCoordsAt(0); + int nbOfCells=c->getNbOfElems()-1; + DataArrayInt *connI=DataArrayInt::New(); + connI->alloc(nbOfCells+1,1); + int *ci=connI->getPointer(); + DataArrayInt *conn=DataArrayInt::New(); + conn->alloc(3*nbOfCells,1); + ci[0]=0; + int *cp=conn->getPointer(); + for(int i=0;isetConnectivity(conn,connI,true); + conn->decrRef(); + connI->decrRef(); +} + +void MEDCouplingCMesh::fill2DUnstructuredMesh(MEDCouplingUMesh *m) const +{ + const DataArrayDouble *c1=getCoordsAt(0); + const DataArrayDouble *c2=getCoordsAt(1); + int n1=c1->getNbOfElems()-1; + int n2=c2->getNbOfElems()-1; + DataArrayInt *connI=DataArrayInt::New(); + connI->alloc(n1*n2+1,1); + int *ci=connI->getPointer(); + DataArrayInt *conn=DataArrayInt::New(); + conn->alloc(5*n1*n2,1); + ci[0]=0; + int *cp=conn->getPointer(); + int pos=0; + for(int j=0;jsetConnectivity(conn,connI,true); + conn->decrRef(); + connI->decrRef(); +} + +void MEDCouplingCMesh::fill3DUnstructuredMesh(MEDCouplingUMesh *m) const +{ + const DataArrayDouble *c1=getCoordsAt(0); + const DataArrayDouble *c2=getCoordsAt(1); + const DataArrayDouble *c3=getCoordsAt(2); + int n1=c1->getNbOfElems()-1; + int n2=c2->getNbOfElems()-1; + int n3=c3->getNbOfElems()-1; + DataArrayInt *connI=DataArrayInt::New(); + connI->alloc(n1*n2*n3+1,1); + int *ci=connI->getPointer(); + DataArrayInt *conn=DataArrayInt::New(); + conn->alloc(9*n1*n2*n3,1); + ci[0]=0; + int *cp=conn->getPointer(); + int pos=0; + for(int k=0;ksetConnectivity(conn,connI,true); + conn->decrRef(); + connI->decrRef(); +} + void MEDCouplingCMesh::getTinySerializationInformation(std::vector& tinyInfo, std::vector& littleStrings) const { tinyInfo.clear(); diff --git a/src/MEDCoupling/MEDCouplingCMesh.hxx b/src/MEDCoupling/MEDCouplingCMesh.hxx index 754f5b54d..434091f41 100644 --- a/src/MEDCoupling/MEDCouplingCMesh.hxx +++ b/src/MEDCoupling/MEDCouplingCMesh.hxx @@ -26,6 +26,7 @@ namespace ParaMEDMEM { class DataArrayDouble; + class MEDCouplingUMesh; class MEDCOUPLING_EXPORT MEDCouplingCMesh : public MEDCouplingMesh { @@ -37,8 +38,11 @@ namespace ParaMEDMEM MEDCouplingMeshType getType() const { return CARTESIAN; } void copyTinyStringsFrom(const MEDCouplingMesh *other) throw(INTERP_KERNEL::Exception); bool isEqual(const MEDCouplingMesh *other, double prec) const; + bool isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const; void checkDeepEquivalWith(const MEDCouplingMesh *other, int cellCompPol, double prec, DataArrayInt *&cellCor, DataArrayInt *&nodeCor) const throw(INTERP_KERNEL::Exception); + void checkDeepEquivalOnSameNodesWith(const MEDCouplingMesh *other, int cellCompPol, double prec, + DataArrayInt *&cellCor) const throw(INTERP_KERNEL::Exception); void checkCoherency() const throw(INTERP_KERNEL::Exception); int getNumberOfCells() const; int getNumberOfNodes() const; @@ -59,6 +63,7 @@ namespace ParaMEDMEM DataArrayDouble *coordsY=0, DataArrayDouble *coordsZ=0); // tools + MEDCouplingUMesh *buildUnstructured() const; MEDCouplingMesh *buildPart(const int *start, const int *end) const; MEDCouplingMesh *buildPartAndReduceNodes(const int *start, const int *end, DataArrayInt*& arr) const; void getBoundingBox(double *bbox) const; @@ -68,10 +73,14 @@ namespace ParaMEDMEM int getCellContainingPoint(const double *pos, double eps) const; void rotate(const double *center, const double *vector, double angle); void translate(const double *vector); + void scale(const double *point, double factor); MEDCouplingMesh *mergeMyselfWith(const MEDCouplingMesh *other) const; DataArrayDouble *getCoordinatesAndOwner() const; DataArrayDouble *getBarycenterAndOwner() const; void renumberCells(const int *old2NewBg, bool check) throw(INTERP_KERNEL::Exception); + void fill1DUnstructuredMesh(MEDCouplingUMesh *m) const; + void fill2DUnstructuredMesh(MEDCouplingUMesh *m) const; + void fill3DUnstructuredMesh(MEDCouplingUMesh *m) const; //some useful methods void getSplitCellValues(int *res) const; void getSplitNodeValues(int *res) const; diff --git a/src/MEDCoupling/MEDCouplingExtrudedMesh.cxx b/src/MEDCoupling/MEDCouplingExtrudedMesh.cxx index a95d38e4e..d01e29149 100644 --- a/src/MEDCoupling/MEDCouplingExtrudedMesh.cxx +++ b/src/MEDCoupling/MEDCouplingExtrudedMesh.cxx @@ -168,12 +168,34 @@ bool MEDCouplingExtrudedMesh::isEqual(const MEDCouplingMesh *other, double prec) return true; } +bool MEDCouplingExtrudedMesh::isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const +{ + const MEDCouplingExtrudedMesh *otherC=dynamic_cast(other); + if(!otherC) + return false; + if(!_mesh2D->isEqualWithoutConsideringStr(otherC->_mesh2D,prec)) + return false; + if(!_mesh1D->isEqualWithoutConsideringStr(otherC->_mesh1D,prec)) + return false; + if(!_mesh3D_ids->isEqualWithoutConsideringStr(*otherC->_mesh3D_ids)) + return false; + if(_cell_2D_id!=otherC->_cell_2D_id) + return false; + return true; +} + void MEDCouplingExtrudedMesh::checkDeepEquivalWith(const MEDCouplingMesh *other, int cellCompPol, double prec, DataArrayInt *&cellCor, DataArrayInt *&nodeCor) const throw(INTERP_KERNEL::Exception) { throw INTERP_KERNEL::Exception("MEDCouplingExtrudedMesh::checkDeepEquivalWith : not implemented yet !"); } +void MEDCouplingExtrudedMesh::checkDeepEquivalOnSameNodesWith(const MEDCouplingMesh *other, int cellCompPol, double prec, + DataArrayInt *&cellCor) const throw(INTERP_KERNEL::Exception) +{ + throw INTERP_KERNEL::Exception("MEDCouplingExtrudedMesh::checkDeepEquivalOnSameNodesWith : not implemented yet !"); +} + INTERP_KERNEL::NormalizedCellType MEDCouplingExtrudedMesh::getTypeOfCell(int cellId) const { const int *ids=_mesh3D_ids->getConstPointer(); @@ -540,6 +562,12 @@ void MEDCouplingExtrudedMesh::translate(const double *vector) _mesh1D->translate(vector); } +void MEDCouplingExtrudedMesh::scale(const double *point, double factor) +{ + _mesh2D->scale(point,factor); + _mesh1D->scale(point,factor); +} + MEDCouplingMesh *MEDCouplingExtrudedMesh::buildPart(const int *start, const int *end) const { // not implemented yet ! diff --git a/src/MEDCoupling/MEDCouplingExtrudedMesh.hxx b/src/MEDCoupling/MEDCouplingExtrudedMesh.hxx index 916beae9b..39a0dbf47 100644 --- a/src/MEDCoupling/MEDCouplingExtrudedMesh.hxx +++ b/src/MEDCoupling/MEDCouplingExtrudedMesh.hxx @@ -46,8 +46,11 @@ namespace ParaMEDMEM MEDCouplingMesh *deepCpy() const; MEDCouplingExtrudedMesh *clone(bool recDeepCpy) const; bool isEqual(const MEDCouplingMesh *other, double prec) const; + bool isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const; void checkDeepEquivalWith(const MEDCouplingMesh *other, int cellCompPol, double prec, DataArrayInt *&cellCor, DataArrayInt *&nodeCor) const throw(INTERP_KERNEL::Exception); + void checkDeepEquivalOnSameNodesWith(const MEDCouplingMesh *other, int cellCompPol, double prec, + DataArrayInt *&cellCor) const throw(INTERP_KERNEL::Exception); INTERP_KERNEL::NormalizedCellType getTypeOfCell(int cellId) const; int getNumberOfCellsWithType(INTERP_KERNEL::NormalizedCellType type) const; void getNodeIdsOfCell(int cellId, std::vector& conn) const; @@ -72,6 +75,7 @@ namespace ParaMEDMEM MEDCouplingUMesh *&m1r, MEDCouplingUMesh *&m2r, double *v) throw(INTERP_KERNEL::Exception); void rotate(const double *center, const double *vector, double angle); void translate(const double *vector); + void scale(const double *point, double factor); MEDCouplingMesh *buildPart(const int *start, const int *end) const; MEDCouplingMesh *buildPartAndReduceNodes(const int *start, const int *end, DataArrayInt*& arr) const; MEDCouplingMesh *mergeMyselfWith(const MEDCouplingMesh *other) const; diff --git a/src/MEDCoupling/MEDCouplingField.cxx b/src/MEDCoupling/MEDCouplingField.cxx index abcd4d22a..41c3029f3 100644 --- a/src/MEDCoupling/MEDCouplingField.cxx +++ b/src/MEDCoupling/MEDCouplingField.cxx @@ -40,6 +40,19 @@ bool MEDCouplingField::isEqual(const MEDCouplingField *other, double meshPrec, d return _mesh->isEqual(other->_mesh,meshPrec); } +bool MEDCouplingField::isEqualWithoutConsideringStr(const MEDCouplingField *other, double meshPrec, double valsPrec) const +{ + if(!_type->isEqualWithoutConsideringStr(other->_type,valsPrec)) + return false; + if(_mesh==0 && other->_mesh==0) + return true; + if(_mesh==0 || other->_mesh==0) + return false; + if(_mesh==other->_mesh) + return true; + return _mesh->isEqualWithoutConsideringStr(other->_mesh,meshPrec); +} + /*! * This method states if 'this' and 'other' are compatibles each other before performing any treatment. * This method is good for methods like : mergeFields. @@ -79,14 +92,14 @@ TypeOfField MEDCouplingField::getTypeOfField() const } /*! - * This method retrieves the weighting field of 'this'. If no '_mesh' is defined an exception will be thrown. + * This method retrieves the measure field of 'this'. If no '_mesh' is defined an exception will be thrown. * Warning the retrieved field life cycle is the responsability of caller. */ -MEDCouplingFieldDouble *MEDCouplingField::buildWeightingField(bool isAbs) const throw(INTERP_KERNEL::Exception) +MEDCouplingFieldDouble *MEDCouplingField::buildMeasureField(bool isAbs) const throw(INTERP_KERNEL::Exception) { if(_mesh==0) - throw INTERP_KERNEL::Exception("MEDCouplingField::getWeightingField : no mesh defined !!!"); - return _type->getWeightingField(_mesh,isAbs); + throw INTERP_KERNEL::Exception("MEDCouplingField::getMeasureField : no mesh defined !!!"); + return _type->getMeasureField(_mesh,isAbs); } void MEDCouplingField::setMesh(const MEDCouplingMesh *mesh) @@ -251,7 +264,7 @@ MEDCouplingField::MEDCouplingField(const MEDCouplingField& other):_name(other._n /*! * This method returns a submesh of 'mesh' instance constituting cell ids contained in array defined as an interval [start;end). - * @ param di is an array returned that specifies entity ids (nodes, cells ids...) in mesh 'mesh' of entity in returned submesh. + * @param di is an array returned that specifies entity ids (nodes, cells ids...) in mesh 'mesh' of entity in returned submesh. */ MEDCouplingMesh *MEDCouplingField::buildSubMeshData(const int *start, const int *end, DataArrayInt *&di) const { diff --git a/src/MEDCoupling/MEDCouplingField.hxx b/src/MEDCoupling/MEDCouplingField.hxx index e36951121..e6eedb5bc 100644 --- a/src/MEDCoupling/MEDCouplingField.hxx +++ b/src/MEDCoupling/MEDCouplingField.hxx @@ -44,6 +44,7 @@ namespace ParaMEDMEM virtual bool areCompatibleForMerge(const MEDCouplingField *other) const; virtual bool areStrictlyCompatible(const MEDCouplingField *other) const; virtual bool isEqual(const MEDCouplingField *other, double meshPrec, double valsPrec) const; + virtual bool isEqualWithoutConsideringStr(const MEDCouplingField *other, double meshPrec, double valsPrec) const; void setMesh(const ParaMEDMEM::MEDCouplingMesh *mesh); const ParaMEDMEM::MEDCouplingMesh *getMesh() const { return _mesh; } void setName(const char *name) { _name=name; } @@ -51,7 +52,7 @@ namespace ParaMEDMEM void setDescription(const char *desc) { _desc=desc; } const char *getName() const { return _name.c_str(); } TypeOfField getTypeOfField() const; - MEDCouplingFieldDouble *buildWeightingField(bool isAbs) const throw(INTERP_KERNEL::Exception); + MEDCouplingFieldDouble *buildMeasureField(bool isAbs) const throw(INTERP_KERNEL::Exception); MEDCouplingMesh *buildSubMeshData(const int *start, const int *end, DataArrayInt *&di) const; MEDCouplingFieldDiscretization *getDiscretization() const { return _type; } // Gauss point specific methods diff --git a/src/MEDCoupling/MEDCouplingFieldDiscretization.cxx b/src/MEDCoupling/MEDCouplingFieldDiscretization.cxx index 77a958052..dfa7049cc 100644 --- a/src/MEDCoupling/MEDCouplingFieldDiscretization.cxx +++ b/src/MEDCoupling/MEDCouplingFieldDiscretization.cxx @@ -84,6 +84,11 @@ TypeOfField MEDCouplingFieldDiscretization::getTypeOfFieldFromStringRepr(const c throw INTERP_KERNEL::Exception("Representation does not match with any field discretization !"); } +bool MEDCouplingFieldDiscretization::isEqualWithoutConsideringStr(const MEDCouplingFieldDiscretization *other, double eps) const +{ + return isEqual(other,eps); +} + /*! * Excepted for MEDCouplingFieldDiscretizationPerCell no underlying TimeLabel object : nothing to do in generally. */ @@ -94,11 +99,11 @@ void MEDCouplingFieldDiscretization::updateTime() /*! * Computes normL1 of DataArrayDouble instance arr. * @param res output parameter expected to be of size arr->getNumberOfComponents(); - * @throw when the field discretization fails on getWeighting fields (gauss points for example) + * @throw when the field discretization fails on getMeasure fields (gauss points for example) */ void MEDCouplingFieldDiscretization::normL1(const MEDCouplingMesh *mesh, const DataArrayDouble *arr, double *res) const throw(INTERP_KERNEL::Exception) { - MEDCouplingFieldDouble *vol=getWeightingField(mesh,true); + MEDCouplingFieldDouble *vol=getMeasureField(mesh,true); int nbOfCompo=arr->getNumberOfComponents(); int nbOfElems=getNumberOfTuples(mesh); std::fill(res,res+nbOfCompo,0.); @@ -115,11 +120,11 @@ void MEDCouplingFieldDiscretization::normL1(const MEDCouplingMesh *mesh, const D /*! * Computes normL2 of DataArrayDouble instance arr. * @param res output parameter expected to be of size arr->getNumberOfComponents(); - * @throw when the field discretization fails on getWeighting fields (gauss points for example) + * @throw when the field discretization fails on getMeasure fields (gauss points for example) */ void MEDCouplingFieldDiscretization::normL2(const MEDCouplingMesh *mesh, const DataArrayDouble *arr, double *res) const throw(INTERP_KERNEL::Exception) { - MEDCouplingFieldDouble *vol=getWeightingField(mesh,true); + MEDCouplingFieldDouble *vol=getMeasureField(mesh,true); int nbOfCompo=arr->getNumberOfComponents(); int nbOfElems=getNumberOfTuples(mesh); std::fill(res,res+nbOfCompo,0.); @@ -137,11 +142,11 @@ void MEDCouplingFieldDiscretization::normL2(const MEDCouplingMesh *mesh, const D /*! * Computes integral of DataArrayDouble instance arr. * @param res output parameter expected to be of size arr->getNumberOfComponents(); - * @throw when the field discretization fails on getWeighting fields (gauss points for example) + * @throw when the field discretization fails on getMeasure fields (gauss points for example) */ void MEDCouplingFieldDiscretization::integral(const MEDCouplingMesh *mesh, const DataArrayDouble *arr, bool isWAbs, double *res) const throw(INTERP_KERNEL::Exception) { - MEDCouplingFieldDouble *vol=getWeightingField(mesh,isWAbs); + MEDCouplingFieldDouble *vol=getMeasureField(mesh,isWAbs); int nbOfCompo=arr->getNumberOfComponents(); int nbOfElems=getNumberOfTuples(mesh); std::fill(res,res+nbOfCompo,0.); @@ -249,6 +254,40 @@ void MEDCouplingFieldDiscretization::getCellIdsHavingGaussLocalization(int locId throw INTERP_KERNEL::Exception("Invalid method for the corresponding field discretization : available only for GaussPoint discretization !"); } +void MEDCouplingFieldDiscretization::renumberEntitiesFromO2NArr(const int *old2NewPtr, DataArrayDouble *arr, const char *msg) +{ + int oldNbOfElems=arr->getNumberOfTuples(); + int nbOfComp=arr->getNumberOfComponents(); + int newNbOfTuples=(*std::max_element(old2NewPtr,old2NewPtr+oldNbOfElems))+1; + DataArrayDouble *arrCpy=arr->deepCopy(); + const double *ptSrc=arrCpy->getConstPointer(); + arr->reAlloc(newNbOfTuples); + double *ptToFill=arr->getPointer(); + std::fill(ptToFill,ptToFill+nbOfComp*newNbOfTuples,std::numeric_limits::max()); + for(int i=0;i=0)//if newNb<0 the node is considered as out. + { + if(std::find_if(ptToFill+newNb*nbOfComp,ptToFill+(newNb+1)*nbOfComp,std::bind2nd(std::not_equal_to(),std::numeric_limits::max())) + ==ptToFill+(newNb+1)*nbOfComp) + std::copy(ptSrc+i*nbOfComp,ptSrc+(i+1)*nbOfComp,ptToFill+newNb*nbOfComp); + else + { + if(!std::equal(ptSrc+i*nbOfComp,ptSrc+(i+1)*nbOfComp,ptToFill+newNb*nbOfComp)) + { + arrCpy->decrRef(); + std::ostringstream oss; + oss << msg << " " << i << " and " << std::find(old2NewPtr,old2NewPtr+i,newNb)-old2NewPtr + << " have been merged and " << msg << " field on them are different !"; + throw INTERP_KERNEL::Exception(oss.str().c_str()); + } + } + } + } + arrCpy->decrRef(); +} + MEDCouplingFieldDiscretization::~MEDCouplingFieldDiscretization() { } @@ -322,7 +361,7 @@ void MEDCouplingFieldDiscretizationP0::checkCoherencyBetween(const MEDCouplingMe } } -MEDCouplingFieldDouble *MEDCouplingFieldDiscretizationP0::getWeightingField(const MEDCouplingMesh *mesh, bool isAbs) const +MEDCouplingFieldDouble *MEDCouplingFieldDiscretizationP0::getMeasureField(const MEDCouplingMesh *mesh, bool isAbs) const { return mesh->getMeasureField(isAbs); } @@ -351,9 +390,14 @@ void MEDCouplingFieldDiscretizationP0::renumberValuesOnNodes(const int *, DataAr { } +void MEDCouplingFieldDiscretizationP0::renumberValuesOnCells(const MEDCouplingMesh *mesh, const int *old2New, DataArrayDouble *arr) const +{ + renumberEntitiesFromO2NArr(old2New,arr,"Cell"); +} + /*! * This method returns a submesh of 'mesh' instance constituting cell ids contained in array defined as an interval [start;end). - * @ param di is an array returned that specifies entity ids (here cells ids) in mesh 'mesh' of entity in returned submesh. + * @param di is an array returned that specifies entity ids (here cells ids) in mesh 'mesh' of entity in returned submesh. * Example : The first cell id of returned mesh has the (*di)[0] id in 'mesh' */ MEDCouplingMesh *MEDCouplingFieldDiscretizationP0::buildSubMeshData(const MEDCouplingMesh *mesh, const int *start, const int *end, DataArrayInt *&di) const @@ -408,24 +452,7 @@ DataArrayDouble *MEDCouplingFieldDiscretizationP1::getLocalizationOfDiscValues(c void MEDCouplingFieldDiscretizationP1::computeMeshRestrictionFromTupleIds(const MEDCouplingMesh *mesh, const int *partBg, const int *partEnd, DataArrayInt *&cellRest) { - std::vector crest; - std::vector conn; - std::set p(partBg,partEnd); - int nbOfCells=mesh->getNumberOfCells(); - for(int i=0;i conn; - mesh->getNodeIdsOfCell(i,conn); - bool cont=true; - for(std::vector::const_iterator iter=conn.begin();iter!=conn.end() && cont;iter++) - if(p.find(*iter)==p.end()) - cont=false; - if(cont) - crest.push_back(i); - } - cellRest=DataArrayInt::New(); - cellRest->alloc(crest.size(),1); - std::copy(crest.begin(),crest.end(),cellRest->getPointer()); + cellRest=mesh->getCellIdsFullyIncludedInNodeIds(partBg,partEnd); } void MEDCouplingFieldDiscretizationP1::checkCompatibilityWithNature(NatureOfField nat) const throw(INTERP_KERNEL::Exception) @@ -440,12 +467,12 @@ void MEDCouplingFieldDiscretizationP1::checkCoherencyBetween(const MEDCouplingMe { std::ostringstream message; message << "Field on nodes invalid because there are " << mesh->getNumberOfNodes(); - message << " cells in mesh and " << da->getNumberOfTuples() << " tuples in field !"; + message << " nodes in mesh and " << da->getNumberOfTuples() << " tuples in field !"; throw INTERP_KERNEL::Exception(message.str().c_str()); } } -MEDCouplingFieldDouble *MEDCouplingFieldDiscretizationP1::getWeightingField(const MEDCouplingMesh *mesh, bool isAbs) const +MEDCouplingFieldDouble *MEDCouplingFieldDiscretizationP1::getMeasureField(const MEDCouplingMesh *mesh, bool isAbs) const { return mesh->getMeasureFieldOnNode(isAbs); } @@ -494,43 +521,27 @@ void MEDCouplingFieldDiscretizationP1::getValueOnPos(const DataArrayDouble *arr, void MEDCouplingFieldDiscretizationP1::renumberValuesOnNodes(const int *old2NewPtr, DataArrayDouble *arr) const { - int oldNbOfElems=arr->getNumberOfTuples(); - int nbOfComp=arr->getNumberOfComponents(); - int newNbOfTuples=(*std::max_element(old2NewPtr,old2NewPtr+oldNbOfElems))+1; - DataArrayDouble *arrCpy=arr->deepCopy(); - const double *ptSrc=arrCpy->getConstPointer(); - arr->reAlloc(newNbOfTuples); - double *ptToFill=arr->getPointer(); - std::fill(ptToFill,ptToFill+nbOfComp*newNbOfTuples,std::numeric_limits::max()); - for(int i=0;i(),std::numeric_limits::max())) - ==ptToFill+(newNb+1)*nbOfComp) - std::copy(ptSrc+i*nbOfComp,ptSrc+(i+1)*nbOfComp,ptToFill+newNb*nbOfComp); - else - { - if(!std::equal(ptSrc+i*nbOfComp,ptSrc+(i+1)*nbOfComp,ptToFill+newNb*nbOfComp)) - { - arrCpy->decrRef(); - std::ostringstream oss; - oss << "Node " << i << " and " << std::find(old2NewPtr,old2NewPtr+i,newNb)-old2NewPtr - << " have been merged and nodal field on them are different !"; - throw INTERP_KERNEL::Exception(oss.str().c_str()); - } - } - } - arrCpy->decrRef(); + renumberEntitiesFromO2NArr(old2NewPtr,arr,"Node"); +} + +/*! + * Nothing to do it's not a bug. + */ +void MEDCouplingFieldDiscretizationP1::renumberValuesOnCells(const MEDCouplingMesh *mesh, const int *old2New, DataArrayDouble *arr) const +{ } /*! * This method returns a submesh of 'mesh' instance constituting cell ids contained in array defined as an interval [start;end). -* @ param di is an array returned that specifies entity ids (here nodes ids) in mesh 'mesh' of entity in returned submesh. +* @param di is an array returned that specifies entity ids (here nodes ids) in mesh 'mesh' of entity in returned submesh. * Example : The first node id of returned mesh has the (*di)[0] id in 'mesh' */ MEDCouplingMesh *MEDCouplingFieldDiscretizationP1::buildSubMeshData(const MEDCouplingMesh *mesh, const int *start, const int *end, DataArrayInt *&di) const { MEDCouplingMesh *ret=mesh->buildPartAndReduceNodes(start,end,di); + DataArrayInt *di2=di->invertArrayO2N2N2O(ret->getNumberOfNodes()); + di->decrRef(); + di=di2; return ret; } @@ -578,6 +589,18 @@ bool MEDCouplingFieldDiscretizationPerCell::isEqual(const MEDCouplingFieldDiscre return _discr_per_cell->isEqual(*otherC->_discr_per_cell); } +bool MEDCouplingFieldDiscretizationPerCell::isEqualWithoutConsideringStr(const MEDCouplingFieldDiscretization *other, double eps) const +{ + const MEDCouplingFieldDiscretizationPerCell *otherC=dynamic_cast(other); + if(!otherC) + return false; + if(_discr_per_cell==0) + return otherC->_discr_per_cell==0; + if(otherC->_discr_per_cell==0) + return false; + return _discr_per_cell->isEqualWithoutConsideringStr(*otherC->_discr_per_cell); +} + /*! * This method is typically the first step of renumbering. The impact on _discr_per_cell is necessary here. * virtualy by this method. @@ -638,6 +661,22 @@ bool MEDCouplingFieldDiscretizationGauss::isEqual(const MEDCouplingFieldDiscreti return true; } +bool MEDCouplingFieldDiscretizationGauss::isEqualWithoutConsideringStr(const MEDCouplingFieldDiscretization *other, double eps) const +{ + const MEDCouplingFieldDiscretizationGauss *otherC=dynamic_cast(other); + if(!otherC) + return false; + if(!MEDCouplingFieldDiscretizationPerCell::isEqualWithoutConsideringStr(other,eps)) + return false; + if(_loc.size()!=otherC->_loc.size()) + return false; + int sz=_loc.size(); + for(int i=0;i_loc[i],eps)) + return false; + return true; +} + MEDCouplingFieldDiscretization *MEDCouplingFieldDiscretizationGauss::clone() const { return new MEDCouplingFieldDiscretizationGauss(*this); @@ -810,7 +849,7 @@ void MEDCouplingFieldDiscretizationGauss::checkCoherencyBetween(const MEDCouplin } } -MEDCouplingFieldDouble *MEDCouplingFieldDiscretizationGauss::getWeightingField(const MEDCouplingMesh *mesh, bool isAbs) const +MEDCouplingFieldDouble *MEDCouplingFieldDiscretizationGauss::getMeasureField(const MEDCouplingMesh *mesh, bool isAbs) const { throw INTERP_KERNEL::Exception("Not implemented yet !"); } @@ -837,6 +876,11 @@ void MEDCouplingFieldDiscretizationGauss::renumberValuesOnNodes(const int *, Dat { } +void MEDCouplingFieldDiscretizationGauss::renumberValuesOnCells(const MEDCouplingMesh *mesh, const int *old2New, DataArrayDouble *arr) const +{ + throw INTERP_KERNEL::Exception("Not implemented yet !"); +} + void MEDCouplingFieldDiscretizationGauss::setGaussLocalizationOnType(const MEDCouplingMesh *m, INTERP_KERNEL::NormalizedCellType type, const std::vector& refCoo, const std::vector& gsCoo, const std::vector& wg) throw(INTERP_KERNEL::Exception) { @@ -1104,7 +1148,7 @@ void MEDCouplingFieldDiscretizationGaussNE::checkCoherencyBetween(const MEDCoupl } } -MEDCouplingFieldDouble *MEDCouplingFieldDiscretizationGaussNE::getWeightingField(const MEDCouplingMesh *mesh, bool isAbs) const +MEDCouplingFieldDouble *MEDCouplingFieldDiscretizationGaussNE::getMeasureField(const MEDCouplingMesh *mesh, bool isAbs) const { throw INTERP_KERNEL::Exception("Not implemented yet !"); } @@ -1131,6 +1175,11 @@ void MEDCouplingFieldDiscretizationGaussNE::renumberValuesOnNodes(const int *, D { } +void MEDCouplingFieldDiscretizationGaussNE::renumberValuesOnCells(const MEDCouplingMesh *mesh, const int *old2New, DataArrayDouble *arr) const +{ + throw INTERP_KERNEL::Exception("Not implemented yet !"); +} + MEDCouplingFieldDiscretizationGaussNE::MEDCouplingFieldDiscretizationGaussNE(const MEDCouplingFieldDiscretizationGaussNE& other):MEDCouplingFieldDiscretization(other) { } diff --git a/src/MEDCoupling/MEDCouplingFieldDiscretization.hxx b/src/MEDCoupling/MEDCouplingFieldDiscretization.hxx index 89d3e7c0f..316fa753d 100644 --- a/src/MEDCoupling/MEDCouplingFieldDiscretization.hxx +++ b/src/MEDCoupling/MEDCouplingFieldDiscretization.hxx @@ -46,6 +46,7 @@ namespace ParaMEDMEM static TypeOfField getTypeOfFieldFromStringRepr(const char *repr) throw(INTERP_KERNEL::Exception); virtual TypeOfField getEnum() const = 0; virtual bool isEqual(const MEDCouplingFieldDiscretization *other, double eps) const = 0; + virtual bool isEqualWithoutConsideringStr(const MEDCouplingFieldDiscretization *other, double eps) const; virtual MEDCouplingFieldDiscretization *clone() const = 0; virtual const char *getStringRepr() const = 0; virtual int getNumberOfTuples(const MEDCouplingMesh *mesh) const = 0; @@ -61,11 +62,12 @@ namespace ParaMEDMEM const int *old2NewBg, bool check) throw(INTERP_KERNEL::Exception) = 0; virtual double getIJK(const MEDCouplingMesh *mesh, const DataArrayDouble *da, int cellId, int nodeIdInCell, int compoId) const throw(INTERP_KERNEL::Exception); virtual void checkCoherencyBetween(const MEDCouplingMesh *mesh, const DataArrayDouble *da) const throw(INTERP_KERNEL::Exception) = 0; - virtual MEDCouplingFieldDouble *getWeightingField(const MEDCouplingMesh *mesh, bool isAbs) const = 0; + virtual MEDCouplingFieldDouble *getMeasureField(const MEDCouplingMesh *mesh, bool isAbs) const = 0; virtual void getValueOn(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, const double *loc, double *res) const = 0; virtual void getValueOnPos(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, int i, int j, int k, double *res) const = 0; virtual MEDCouplingMesh *buildSubMeshData(const MEDCouplingMesh *mesh, const int *start, const int *end, DataArrayInt *&di) const = 0; virtual void renumberValuesOnNodes(const int *old2New, DataArrayDouble *arr) const = 0; + virtual void renumberValuesOnCells(const MEDCouplingMesh *mesh, const int *old2New, DataArrayDouble *arr) const = 0; virtual void getSerializationIntArray(DataArrayInt *& arr) const; virtual void getTinySerializationIntInformation(std::vector& tinyInfo) const; virtual void getTinySerializationDbleInformation(std::vector& tinyInfo) const; @@ -85,6 +87,7 @@ namespace ParaMEDMEM virtual ~MEDCouplingFieldDiscretization(); protected: MEDCouplingFieldDiscretization(); + static void renumberEntitiesFromO2NArr(const int *old2NewPtr, DataArrayDouble *arr, const char *msg); protected: double _precision; static const double DFLT_PRECISION; @@ -105,10 +108,11 @@ namespace ParaMEDMEM void computeMeshRestrictionFromTupleIds(const MEDCouplingMesh *mesh, const int *partBg, const int *partEnd, DataArrayInt *&cellRest); void checkCoherencyBetween(const MEDCouplingMesh *mesh, const DataArrayDouble *da) const throw(INTERP_KERNEL::Exception); - MEDCouplingFieldDouble *getWeightingField(const MEDCouplingMesh *mesh, bool isAbs) const; + MEDCouplingFieldDouble *getMeasureField(const MEDCouplingMesh *mesh, bool isAbs) const; void getValueOn(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, const double *loc, double *res) const; void getValueOnPos(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, int i, int j, int k, double *res) const; void renumberValuesOnNodes(const int *old2New, DataArrayDouble *arr) const; + void renumberValuesOnCells(const MEDCouplingMesh *mesh, const int *old2New, DataArrayDouble *arr) const; MEDCouplingMesh *buildSubMeshData(const MEDCouplingMesh *mesh, const int *start, const int *end, DataArrayInt *&di) const; public: static const char REPR[]; @@ -130,11 +134,12 @@ namespace ParaMEDMEM DataArrayInt *&cellRest); void checkCompatibilityWithNature(NatureOfField nat) const throw(INTERP_KERNEL::Exception); void checkCoherencyBetween(const MEDCouplingMesh *mesh, const DataArrayDouble *da) const throw(INTERP_KERNEL::Exception); - MEDCouplingFieldDouble *getWeightingField(const MEDCouplingMesh *mesh, bool isAbs) const; + MEDCouplingFieldDouble *getMeasureField(const MEDCouplingMesh *mesh, bool isAbs) const; void getValueOn(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, const double *loc, double *res) const; void getValueOnPos(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, int i, int j, int k, double *res) const; MEDCouplingMesh *buildSubMeshData(const MEDCouplingMesh *mesh, const int *start, const int *end, DataArrayInt *&di) const; void renumberValuesOnNodes(const int *old2New, DataArrayDouble *arr) const; + void renumberValuesOnCells(const MEDCouplingMesh *mesh, const int *old2New, DataArrayDouble *arr) const; public: static const char REPR[]; static const TypeOfField TYPE; @@ -153,6 +158,7 @@ namespace ParaMEDMEM void updateTime(); void checkCoherencyBetween(const MEDCouplingMesh *mesh, const DataArrayDouble *da) const throw(INTERP_KERNEL::Exception); bool isEqual(const MEDCouplingFieldDiscretization *other, double eps) const; + bool isEqualWithoutConsideringStr(const MEDCouplingFieldDiscretization *other, double eps) const; void renumberCells(const int *old2NewBg, bool check) throw(INTERP_KERNEL::Exception); protected: void buildDiscrPerCellIfNecessary(const MEDCouplingMesh *m); @@ -166,6 +172,7 @@ namespace ParaMEDMEM MEDCouplingFieldDiscretizationGauss(); TypeOfField getEnum() const; bool isEqual(const MEDCouplingFieldDiscretization *other, double eps) const; + bool isEqualWithoutConsideringStr(const MEDCouplingFieldDiscretization *other, double eps) const; MEDCouplingFieldDiscretization *clone() const; const char *getStringRepr() const; int getNumberOfTuples(const MEDCouplingMesh *mesh) const; @@ -182,11 +189,12 @@ namespace ParaMEDMEM void resizeForUnserialization(const std::vector& tinyInfo, DataArrayInt *& arr); double getIJK(const MEDCouplingMesh *mesh, const DataArrayDouble *da, int cellId, int nodeIdInCell, int compoId) const throw(INTERP_KERNEL::Exception); void checkCoherencyBetween(const MEDCouplingMesh *mesh, const DataArrayDouble *da) const throw(INTERP_KERNEL::Exception); - MEDCouplingFieldDouble *getWeightingField(const MEDCouplingMesh *mesh, bool isAbs) const; + MEDCouplingFieldDouble *getMeasureField(const MEDCouplingMesh *mesh, bool isAbs) const; void getValueOn(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, const double *loc, double *res) const; void getValueOnPos(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, int i, int j, int k, double *res) const; MEDCouplingMesh *buildSubMeshData(const MEDCouplingMesh *mesh, const int *start, const int *end, DataArrayInt *&di) const; void renumberValuesOnNodes(const int *old2New, DataArrayDouble *arr) const; + void renumberValuesOnCells(const MEDCouplingMesh *mesh, const int *old2New, DataArrayDouble *arr) const; void setGaussLocalizationOnType(const MEDCouplingMesh *m, INTERP_KERNEL::NormalizedCellType type, const std::vector& refCoo, const std::vector& gsCoo, const std::vector& wg) throw(INTERP_KERNEL::Exception); void setGaussLocalizationOnCells(const MEDCouplingMesh *m, const int *begin, const int *end, const std::vector& refCoo, @@ -230,11 +238,12 @@ namespace ParaMEDMEM void checkCompatibilityWithNature(NatureOfField nat) const throw(INTERP_KERNEL::Exception); double getIJK(const MEDCouplingMesh *mesh, const DataArrayDouble *da, int cellId, int nodeIdInCell, int compoId) const throw(INTERP_KERNEL::Exception); void checkCoherencyBetween(const MEDCouplingMesh *mesh, const DataArrayDouble *da) const throw(INTERP_KERNEL::Exception); - MEDCouplingFieldDouble *getWeightingField(const MEDCouplingMesh *mesh, bool isAbs) const; + MEDCouplingFieldDouble *getMeasureField(const MEDCouplingMesh *mesh, bool isAbs) const; void getValueOn(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, const double *loc, double *res) const; void getValueOnPos(const DataArrayDouble *arr, const MEDCouplingMesh *mesh, int i, int j, int k, double *res) const; MEDCouplingMesh *buildSubMeshData(const MEDCouplingMesh *mesh, const int *start, const int *end, DataArrayInt *&di) const; void renumberValuesOnNodes(const int *old2New, DataArrayDouble *arr) const; + void renumberValuesOnCells(const MEDCouplingMesh *mesh, const int *old2New, DataArrayDouble *arr) const; protected: MEDCouplingFieldDiscretizationGaussNE(const MEDCouplingFieldDiscretizationGaussNE& other); public: diff --git a/src/MEDCoupling/MEDCouplingFieldDouble.cxx b/src/MEDCoupling/MEDCouplingFieldDouble.cxx index 10c8758f4..eecbba978 100644 --- a/src/MEDCoupling/MEDCouplingFieldDouble.cxx +++ b/src/MEDCoupling/MEDCouplingFieldDouble.cxx @@ -18,7 +18,7 @@ // #include "MEDCouplingFieldDouble.hxx" -#include "MEDCouplingPointSet.hxx" +#include "MEDCouplingUMesh.hxx" #include "MEDCouplingTimeDiscretization.hxx" #include "MEDCouplingFieldDiscretization.hxx" #include "MEDCouplingAutoRefCountObjectPtr.hxx" @@ -84,7 +84,14 @@ std::string MEDCouplingFieldDouble::simpleRepr() const ret << "FieldDouble time discretization is : " << _time_discr->getStringRepr() << "\n"; ret << "FieldDouble nature of field is : " << MEDCouplingNatureOfField::getRepr(_nature) << "\n"; if(getArray()) - ret << "FieldDouble default array has " << getArray()->getNumberOfComponents() << " components and " << getArray()->getNumberOfTuples() << " tuples.\n"; + { + int nbOfCompo=getArray()->getNumberOfComponents(); + ret << "FieldDouble default array has " << nbOfCompo << " components and " << getArray()->getNumberOfTuples() << " tuples.\n"; + ret << "FieldDouble default array has following info on components : "; + for(int i=0;igetInfoOnComponent(i) << "\" "; + ret << "\n"; + } if(_mesh) ret << "Mesh support information :\n__________________________\n" << _mesh->simpleRepr(); else @@ -134,6 +141,20 @@ bool MEDCouplingFieldDouble::isEqual(const MEDCouplingField *other, double meshP return true; } +bool MEDCouplingFieldDouble::isEqualWithoutConsideringStr(const MEDCouplingField *other, double meshPrec, double valsPrec) const +{ + const MEDCouplingFieldDouble *otherC=dynamic_cast(other); + if(!otherC) + return false; + if(_nature!=otherC->_nature) + return false; + if(!MEDCouplingField::isEqualWithoutConsideringStr(other,meshPrec,valsPrec)) + return false; + if(!_time_discr->isEqualWithoutConsideringStr(otherC->_time_discr,valsPrec)) + return false; + return true; +} + /*! * This method states if 'this' and 'other' are compatibles each other before performing any treatment. * This method is good for methods like : mergeFields. @@ -247,7 +268,8 @@ void MEDCouplingFieldDouble::renumberNodesWithoutMesh(const int *old2NewBg) thro std::vector arrays; _time_discr->getArrays(arrays); for(std::vector::const_iterator iter=arrays.begin();iter!=arrays.end();iter++) - _type->renumberValuesOnNodes(old2NewBg,*iter); + if(*iter) + _type->renumberValuesOnNodes(old2NewBg,*iter); } /*! @@ -392,6 +414,38 @@ double MEDCouplingFieldDouble::getMaxValue() const throw(INTERP_KERNEL::Exceptio return ret; } +/*! + * This method is an extension of ParaMEDMEM::MEDCouplingFieldDouble::getMaxValue method because the returned + * value is the same but this method also returns to you a tupleIds object which the caller have the responsibility + * to deal with. The main difference is that the returned tupleIds is those corresponding the first set array. + * If you have more than one array set (in LINEAR_TIME instance for example) only the first not null array will be used + * to compute tupleIds. + */ +double MEDCouplingFieldDouble::getMaxValue2(DataArrayInt*& tupleIds) const throw(INTERP_KERNEL::Exception) +{ + std::vector arrays; + _time_discr->getArrays(arrays); + double ret=-std::numeric_limits::max(); + bool isExistingArr=false; + tupleIds=0; + for(std::vector::const_iterator iter=arrays.begin();iter!=arrays.end();iter++) + { + if(*iter) + { + isExistingArr=true; + DataArrayInt *tmp; + ret=std::max(ret,(*iter)->getMaxValue2(tmp)); + if(!tupleIds) + tupleIds=tmp; + else + tmp->decrRef(); + } + } + if(!isExistingArr) + throw INTERP_KERNEL::Exception("getMaxValue2 : No arrays defined !"); + return ret; +} + /*! * This method returns the min value in 'this'. 'This' is expected to be a field with exactly \b one component. If not an exception will be thrown. * To getMinValue on vector field applyFunc is needed before. This method looks only on all arrays stored in 'this->_time_discr'. @@ -417,6 +471,38 @@ double MEDCouplingFieldDouble::getMinValue() const throw(INTERP_KERNEL::Exceptio return ret; } +/*! + * This method is an extension of ParaMEDMEM::MEDCouplingFieldDouble::getMinValue method because the returned + * value is the same but this method also returns to you a tupleIds object which the caller have the responsibility + * to deal with. The main difference is that the returned tupleIds is those corresponding the first set array. + * If you have more than one array set (in LINEAR_TIME instance for example) only the first not null array will be used + * to compute tupleIds. + */ +double MEDCouplingFieldDouble::getMinValue2(DataArrayInt*& tupleIds) const throw(INTERP_KERNEL::Exception) +{ + std::vector arrays; + _time_discr->getArrays(arrays); + double ret=-std::numeric_limits::max(); + bool isExistingArr=false; + tupleIds=0; + for(std::vector::const_iterator iter=arrays.begin();iter!=arrays.end();iter++) + { + if(*iter) + { + isExistingArr=true; + DataArrayInt *tmp; + ret=std::max(ret,(*iter)->getMinValue2(tmp)); + if(!tupleIds) + tupleIds=tmp; + else + tmp->decrRef(); + } + } + if(!isExistingArr) + throw INTERP_KERNEL::Exception("getMinValue2 : No arrays defined !"); + return ret; +} + /*! * This method returns the average value in 'this'. 'This' is expected to be a field with exactly \b one component. If not an exception will be thrown. * To getAverageValue on vector field applyFunc is needed before. This method looks only \b default array \b and \b only \b default. @@ -430,7 +516,7 @@ double MEDCouplingFieldDouble::getAverageValue() const throw(INTERP_KERNEL::Exce } /*! - * This method returns the average value in 'this' weighted by ParaMEDMEM::MEDCouplingField::buildWeightingField. + * This method returns the average value in 'this' weighted by ParaMEDMEM::MEDCouplingField::buildMeasureField. * 'This' is expected to be a field with exactly \b one component. If not an exception will be thrown. * To getAverageValue on vector field applyFunc is needed before. This method looks only \b default array \b and \b only \b default. * If default array does not exist, an exception will be thrown. @@ -439,7 +525,7 @@ double MEDCouplingFieldDouble::getWeightedAverageValue() const throw(INTERP_KERN { if(getArray()==0) throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::getWeightedAverageValue : no default array defined !"); - MEDCouplingFieldDouble *w=buildWeightingField(true); + MEDCouplingFieldDouble *w=buildMeasureField(true); double deno=w->getArray()->accumulate(0); w->getArray()->multiplyEqual(getArray()); double res=w->getArray()->accumulate(0); @@ -619,6 +705,46 @@ void MEDCouplingFieldDouble::applyLin(double a, double b, int compoId) _time_discr->applyLin(a,b,compoId); } +/*! + * This method sets 'this' to a uniform scalar field with one component. + * All tuples will have the same value 'value'. + * An exception is thrown if no underlying mesh is defined. + */ +MEDCouplingFieldDouble &MEDCouplingFieldDouble::operator=(double value) throw(INTERP_KERNEL::Exception) +{ + if(!_mesh) + throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::operator= : no mesh defined !"); + int nbOfTuple=_type->getNumberOfTuples(_mesh); + _time_discr->setUniformValue(nbOfTuple,value); + return *this; +} + +/*! + * This method is very similar to this one MEDCouplingMesh::fillFromAnalytic. + * The main difference is that the field as been started to be constructed here. + * An exception is throw if no underlying mesh is set before the call of this method. + */ +void MEDCouplingFieldDouble::fillFromAnalytic(int nbOfComp, FunctionToEvaluate func) throw(INTERP_KERNEL::Exception) +{ + if(!_mesh) + throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::fillFromAnalytic : no mesh defined !"); + MEDCouplingAutoRefCountObjectPtr loc=_type->getLocalizationOfDiscValues(_mesh); + _time_discr->fillFromAnalytic(loc,nbOfComp,func); +} + +/*! + * This method is very similar to this one MEDCouplingMesh::fillFromAnalytic. + * The main difference is that the field as been started to be constructed here. + * An exception is throw if no underlying mesh is set before the call of this method. + */ +void MEDCouplingFieldDouble::fillFromAnalytic(int nbOfComp, const char *func) throw(INTERP_KERNEL::Exception) +{ + if(!_mesh) + throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::fillFromAnalytic : no mesh defined !"); + MEDCouplingAutoRefCountObjectPtr loc=_type->getLocalizationOfDiscValues(_mesh); + _time_discr->fillFromAnalytic(loc,nbOfComp,func); +} + /*! * Applyies the function specified by pointer 'func' on each tuples on all arrays contained in _time_discr. * If '*func' returns false during one evaluation an exception will be thrown. @@ -651,13 +777,18 @@ void MEDCouplingFieldDouble::applyFunc(const char *func) /*! * Applyies the function specified by the string repr 'func' on each tuples on all arrays contained in _time_discr. * The field will contain exactly the same number of components after the call. - * Use is not warranted and can cause SIGSEGV ! + * Use is not warranted for the moment ! */ void MEDCouplingFieldDouble::applyFuncFast32(const char *func) throw(INTERP_KERNEL::Exception) { _time_discr->applyFuncFast32(func); } +/*! + * Applyies the function specified by the string repr 'func' on each tuples on all arrays contained in _time_discr. + * The field will contain exactly the same number of components after the call. + * Use is not warranted for the moment ! + */ void MEDCouplingFieldDouble::applyFuncFast64(const char *func) throw(INTERP_KERNEL::Exception) { _time_discr->applyFuncFast64(func); @@ -863,7 +994,7 @@ bool MEDCouplingFieldDouble::mergeNodes(double eps) throw(INTERP_KERNEL::Excepti { const MEDCouplingPointSet *meshC=dynamic_cast(_mesh); if(!meshC) - throw INTERP_KERNEL::Exception("Invalid mesh to apply mergeNodes on it !"); + throw INTERP_KERNEL::Exception("Invalid support mesh to apply mergeNodes on it : must be a MEDCouplingPointSet one !"); MEDCouplingAutoRefCountObjectPtr meshC2((MEDCouplingPointSet *)meshC->deepCpy()); bool ret; int ret2; @@ -873,11 +1004,62 @@ bool MEDCouplingFieldDouble::mergeNodes(double eps) throw(INTERP_KERNEL::Excepti std::vector arrays; _time_discr->getArrays(arrays); for(std::vector::const_iterator iter=arrays.begin();iter!=arrays.end();iter++) - _type->renumberValuesOnNodes(arr->getConstPointer(),*iter); + if(*iter) + _type->renumberValuesOnNodes(arr->getConstPointer(),*iter); setMesh(meshC2); return true; } +/*! + * This method applyies ParaMEDMEM::MEDCouplingPointSet::zipCoords method on 'this->_mesh' that should be set and of type ParaMEDMEM::MEDCouplingPointSet. + * If some nodes have disappeared true is returned. + */ +bool MEDCouplingFieldDouble::zipCoords() throw(INTERP_KERNEL::Exception) +{ + const MEDCouplingPointSet *meshC=dynamic_cast(_mesh); + if(!meshC) + throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::zipCoords : Invalid support mesh to apply zipCoords on it : must be a MEDCouplingPointSet one !"); + MEDCouplingAutoRefCountObjectPtr meshC2((MEDCouplingPointSet *)meshC->deepCpy()); + int oldNbOfNodes=meshC2->getNumberOfNodes(); + MEDCouplingAutoRefCountObjectPtr arr=meshC2->zipCoordsTraducer(); + if(meshC2->getNumberOfNodes()!=oldNbOfNodes) + { + std::vector arrays; + _time_discr->getArrays(arrays); + for(std::vector::const_iterator iter=arrays.begin();iter!=arrays.end();iter++) + if(*iter) + _type->renumberValuesOnNodes(arr->getConstPointer(),*iter); + setMesh(meshC2); + return true; + } + return false; +} + +/*! + * This method applyies ParaMEDMEM::MEDCouplingUMesh::zipConnectivityTraducer on 'this->_mesh' that should be set and of type ParaMEDMEM::MEDCouplingUMesh. + * The semantic of 'compType' is given in ParaMEDMEM::MEDCouplingUMesh::zipConnectivityTraducer method. + */ +bool MEDCouplingFieldDouble::zipConnectivity(int compType) throw(INTERP_KERNEL::Exception) +{ + const MEDCouplingUMesh *meshC=dynamic_cast(_mesh); + if(!meshC) + throw INTERP_KERNEL::Exception("MEDCouplingFieldDouble::zipCoords : Invalid support mesh to apply zipCoords on it : must be a MEDCouplingPointSet one !"); + MEDCouplingAutoRefCountObjectPtr meshC2((MEDCouplingUMesh *)meshC->deepCpy()); + int oldNbOfCells=meshC2->getNumberOfCells(); + MEDCouplingAutoRefCountObjectPtr arr=meshC2->zipConnectivityTraducer(compType); + if(meshC2->getNumberOfCells()!=oldNbOfCells) + { + std::vector arrays; + _time_discr->getArrays(arrays); + for(std::vector::const_iterator iter=arrays.begin();iter!=arrays.end();iter++) + if(*iter) + _type->renumberValuesOnCells(meshC,arr->getConstPointer(),*iter); + setMesh(meshC2); + return true; + } + return false; +} + MEDCouplingFieldDouble *MEDCouplingFieldDouble::doublyContractedProduct() const throw(INTERP_KERNEL::Exception) { MEDCouplingTimeDiscretization *td=_time_discr->doublyContractedProduct(); diff --git a/src/MEDCoupling/MEDCouplingFieldDouble.hxx b/src/MEDCoupling/MEDCouplingFieldDouble.hxx index 18d6d6ae8..bcdb5861d 100644 --- a/src/MEDCoupling/MEDCouplingFieldDouble.hxx +++ b/src/MEDCoupling/MEDCouplingFieldDouble.hxx @@ -36,6 +36,7 @@ namespace ParaMEDMEM std::string simpleRepr() const; std::string advancedRepr() const; bool isEqual(const MEDCouplingField *other, double meshPrec, double valsPrec) const; + bool isEqualWithoutConsideringStr(const MEDCouplingField *other, double meshPrec, double valsPrec) const; bool areCompatibleForMerge(const MEDCouplingField *other) const; bool areStrictlyCompatible(const MEDCouplingField *other) const; bool areCompatibleForMul(const MEDCouplingField *other) const; @@ -68,7 +69,9 @@ namespace ParaMEDMEM double accumulate(int compId) const; void accumulate(double *res) const; double getMaxValue() const throw(INTERP_KERNEL::Exception); + double getMaxValue2(DataArrayInt*& tupleIds) const throw(INTERP_KERNEL::Exception); double getMinValue() const throw(INTERP_KERNEL::Exception); + double getMinValue2(DataArrayInt*& tupleIds) const throw(INTERP_KERNEL::Exception); double getAverageValue() const throw(INTERP_KERNEL::Exception); double getWeightedAverageValue() const throw(INTERP_KERNEL::Exception); double normL1(int compId) const throw(INTERP_KERNEL::Exception); @@ -82,6 +85,9 @@ namespace ParaMEDMEM void getValueOn(const double *spaceLoc, double time, double *res) const throw(INTERP_KERNEL::Exception); //! \b temporary void applyLin(double a, double b, int compoId); + MEDCouplingFieldDouble &operator=(double value) throw(INTERP_KERNEL::Exception); + void fillFromAnalytic(int nbOfComp, FunctionToEvaluate func) throw(INTERP_KERNEL::Exception); + void fillFromAnalytic(int nbOfComp, const char *func) throw(INTERP_KERNEL::Exception); void applyFunc(int nbOfComp, FunctionToEvaluate func); void applyFunc(int nbOfComp, const char *func); void applyFunc(const char *func); @@ -102,6 +108,8 @@ namespace ParaMEDMEM void changeUnderlyingMesh(const MEDCouplingMesh *other, int levOfCheck, double prec) throw(INTERP_KERNEL::Exception); void substractInPlaceDM(const MEDCouplingFieldDouble *f, int levOfCheck, double prec) throw(INTERP_KERNEL::Exception); bool mergeNodes(double eps) throw(INTERP_KERNEL::Exception); + bool zipCoords() throw(INTERP_KERNEL::Exception); + bool zipConnectivity(int compType) throw(INTERP_KERNEL::Exception); MEDCouplingFieldDouble *doublyContractedProduct() const throw(INTERP_KERNEL::Exception); MEDCouplingFieldDouble *determinant() const throw(INTERP_KERNEL::Exception); MEDCouplingFieldDouble *eigenValues() const throw(INTERP_KERNEL::Exception); diff --git a/src/MEDCoupling/MEDCouplingMemArray.cxx b/src/MEDCoupling/MEDCouplingMemArray.cxx index 67923bc7e..c40c4dd92 100644 --- a/src/MEDCoupling/MEDCouplingMemArray.cxx +++ b/src/MEDCoupling/MEDCouplingMemArray.cxx @@ -62,6 +62,28 @@ void DataArray::reprWithoutNameStream(std::ostream& stream) const stream << "\n"; } +std::string DataArray::getInfoOnComponent(int i) const throw(INTERP_KERNEL::Exception) +{ + if(i<(int)_info_on_compo.size()) + return _info_on_compo[i]; + else + { + std::ostringstream oss; oss << "getInfoOnComponent : Invalid component id transmitted (" << i << ") >= " << (int) _info_on_compo.size(); + throw INTERP_KERNEL::Exception(oss.str().c_str()); + } +} + +void DataArray::setInfoOnComponent(int i, const char *info) throw(INTERP_KERNEL::Exception) +{ + if(i<(int)_info_on_compo.size()) + _info_on_compo[i]=info; + else + { + std::ostringstream oss; oss << "setInfoOnComponent : Invalid component id transmitted (" << i << ") >= " << (int) _info_on_compo.size(); + throw INTERP_KERNEL::Exception(oss.str().c_str()); + } +} + DataArrayDouble *DataArrayDouble::New() { return new DataArrayDouble; @@ -94,6 +116,13 @@ void DataArrayDouble::alloc(int nbOfTuple, int nbOfCompo) void DataArrayDouble::fillWithZero() { _mem.fillWithValue(0.); + declareAsNew(); +} + +void DataArrayDouble::fillWithValue(double val) +{ + _mem.fillWithValue(val); + declareAsNew(); } std::string DataArrayDouble::repr() const @@ -143,6 +172,11 @@ bool DataArrayDouble::isEqual(const DataArrayDouble& other, double prec) const return _mem.isEqual(other._mem,prec); } +bool DataArrayDouble::isEqualWithoutConsideringStr(const DataArrayDouble& other, double prec) const +{ + return _mem.isEqual(other._mem,prec); +} + void DataArrayDouble::reAlloc(int nbOfTuples) { _mem.reAlloc(_info_on_compo.size()*nbOfTuples); @@ -179,6 +213,23 @@ void DataArrayDouble::renumberInPlace(const int *old2New) declareAsNew(); } +/*! + * This method does \b not change the number of tuples after this call. + * Only a permutation is done. + */ +void DataArrayDouble::renumberInPlaceR(const int *new2Old) +{ + int nbTuples=getNumberOfTuples(); + int nbOfCompo=getNumberOfComponents(); + double *tmp=new double[nbTuples*nbOfCompo]; + const double *iptr=getConstPointer(); + for(int i=0;igetPointer(); for(int i=0;icopyStringInfoFrom(*this); + return ret; +} + +/*! + * This method does \b not change the number of tuples after this call. + * Only a permutation is done. + */ +DataArrayDouble *DataArrayDouble::renumberR(const int *new2Old) const +{ + int nbTuples=getNumberOfTuples(); + int nbOfCompo=getNumberOfComponents(); + DataArrayDouble *ret=DataArrayDouble::New(); + ret->alloc(nbTuples,nbOfCompo); + ret->copyStringInfoFrom(*this); + const double *iptr=getConstPointer(); + double *optr=ret->getPointer(); + for(int i=0;icopyStringInfoFrom(*this); + return ret; +} + +/*! + * Idem DataArrayDouble::renumber method except that the number of tuples is reduced. + * That is to say that it is expected that newNbOfTuplegetNumberOfTuples(). + * ['old2New','old2New'+getNumberOfTuples()) defines a range containing old to new array. For every negative value in ['old2NewBg','old2New'+getNumberOfTuples()) the corresponding tuple is + * omitted. + */ +DataArrayDouble *DataArrayDouble::renumberAndReduce(const int *old2New, int newNbOfTuple) const +{ + int nbTuples=getNumberOfTuples(); + int nbOfCompo=getNumberOfComponents(); + DataArrayDouble *ret=DataArrayDouble::New(); + ret->alloc(newNbOfTuple,nbOfCompo); + const double *iptr=getConstPointer(); + double *optr=ret->getPointer(); + for(int i=0;i=0) + std::copy(iptr+i*nbOfCompo,iptr+(i+1)*nbOfCompo,optr+w*nbOfCompo); + } + ret->copyStringInfoFrom(*this); + return ret; +} + +/*! + * This method is a generalization of DataArrayDouble::substr method because a not contigous range can be specified here. + * This method is equavalent to DataArrayDouble::renumberAndReduce except that convention in input is new2old and \b not old2new. + */ +DataArrayDouble *DataArrayDouble::selectByTupleId(const int *new2OldBg, const int *new2OldEnd) const +{ + DataArrayDouble *ret=DataArrayDouble::New(); + int nbComp=getNumberOfComponents(); + ret->alloc(std::distance(new2OldBg,new2OldEnd),nbComp); + ret->copyStringInfoFrom(*this); + double *pt=ret->getPointer(); + const double *srcPt=getConstPointer(); + int i=0; + for(const int *w=new2OldBg;w!=new2OldEnd;w++,i++) + std::copy(srcPt+(*w)*nbComp,srcPt+((*w)+1)*nbComp,pt+i*nbComp); + ret->copyStringInfoFrom(*this); return ret; } @@ -254,23 +368,6 @@ DataArrayDouble *DataArrayDouble::changeNbOfComponents(int newNbOfComp, double d return ret; } -/*! - * This method is a generalization of DataArrayDouble::substr method because a not contigous range can be specified here. - */ -DataArrayDouble *DataArrayDouble::selectByTupleId(const int *start, const int *end) const -{ - DataArrayDouble *ret=DataArrayDouble::New(); - int nbComp=getNumberOfComponents(); - ret->alloc(std::distance(start,end),nbComp); - ret->copyStringInfoFrom(*this); - double *pt=ret->getPointer(); - const double *srcPt=getConstPointer(); - int i=0; - for(const int *w=start;w!=end;w++,i++) - std::copy(srcPt+(*w)*nbComp,srcPt+((*w)+1)*nbComp,pt+i*nbComp); - return ret; -} - void DataArrayDouble::setArrayIn(DataArrayDouble *newArray, DataArrayDouble* &arrayToSet) { if(newArray!=arrayToSet) @@ -313,6 +410,15 @@ double DataArrayDouble::getMaxValue(int& tupleId) const throw(INTERP_KERNEL::Exc return *loc; } +double DataArrayDouble::getMaxValue2(DataArrayInt*& tupleIds) const throw(INTERP_KERNEL::Exception) +{ + int tmp; + tupleIds=0; + double ret=getMaxValue(tmp); + tupleIds=getIdsInRange(ret,ret); + return ret; +} + double DataArrayDouble::getMinValue(int& tupleId) const throw(INTERP_KERNEL::Exception) { if(getNumberOfComponents()!=1) @@ -326,6 +432,15 @@ double DataArrayDouble::getMinValue(int& tupleId) const throw(INTERP_KERNEL::Exc return *loc; } +double DataArrayDouble::getMinValue2(DataArrayInt*& tupleIds) const throw(INTERP_KERNEL::Exception) +{ + int tmp; + tupleIds=0; + double ret=getMinValue(tmp); + tupleIds=getIdsInRange(ret,ret); + return ret; +} + double DataArrayDouble::getAverageValue() const throw(INTERP_KERNEL::Exception) { if(getNumberOfComponents()!=1) @@ -1017,6 +1132,13 @@ void DataArrayInt::alloc(int nbOfTuple, int nbOfCompo) void DataArrayInt::fillWithZero() { _mem.fillWithValue(0); + declareAsNew(); +} + +void DataArrayInt::fillWithValue(int val) +{ + _mem.fillWithValue(val); + declareAsNew(); } std::string DataArrayInt::repr() const @@ -1068,7 +1190,7 @@ void DataArrayInt::transformWithIndArr(const int *indArr) } /*! - * This method invert array 'di' that is a conversion map from Old to New node numbering to New to Old node numbering. + * This method invert array 'di' that is a conversion map from Old to New numbering to New to Old numbering. */ DataArrayInt *DataArrayInt::invertArrayO2N2N2O(int newNbOfElem) const { @@ -1083,6 +1205,22 @@ DataArrayInt *DataArrayInt::invertArrayO2N2N2O(int newNbOfElem) const return ret; } +/*! + * This method invert array 'di' that is a conversion map from New to old numbering to Old to New numbering. + */ +DataArrayInt *DataArrayInt::invertArrayN2O2O2N(int oldNbOfElem) const +{ + DataArrayInt *ret=DataArrayInt::New(); + ret->alloc(oldNbOfElem,1); + const int *new2Old=getConstPointer(); + int *pt=ret->getPointer(); + std::fill(pt,pt+oldNbOfElem,-1); + int nbOfNewElems=getNumberOfTuples(); + for(int i=0;igetPointer(); for(int i=0;icopyStringInfoFrom(*this); + return ret; +} + +DataArrayInt *DataArrayInt::renumberR(const int *new2Old) const +{ + int nbTuples=getNumberOfTuples(); + int nbOfCompo=getNumberOfComponents(); + DataArrayInt *ret=DataArrayInt::New(); + ret->alloc(nbTuples,nbOfCompo); + ret->copyStringInfoFrom(*this); + const int *iptr=getConstPointer(); + int *optr=ret->getPointer(); + for(int i=0;icopyStringInfoFrom(*this); + return ret; +} + +/*! + * Idem DataArrayDouble::renumber method except that the number of tuples is reduced. + * That is to say that it is expected that newNbOfTuplegetNumberOfTuples(). + * ['old2New','old2New'+getNumberOfTuples()) defines a range containing old to new array. For every negative value in ['old2NewBg','old2New'getNumberOfTuples()) the corresponding tuple is + * omitted. + */ +DataArrayInt *DataArrayInt::renumberAndReduce(const int *old2New, int newNbOfTuple) const +{ + int nbTuples=getNumberOfTuples(); + int nbOfCompo=getNumberOfComponents(); + DataArrayInt *ret=DataArrayInt::New(); + ret->alloc(newNbOfTuple,nbOfCompo); + const int *iptr=getConstPointer(); + int *optr=ret->getPointer(); + for(int i=0;i=0) + std::copy(iptr+i*nbOfCompo,iptr+(i+1)*nbOfCompo,optr+w*nbOfCompo); + } + ret->copyStringInfoFrom(*this); + return ret; +} + +/*! + * This method is a generalization of DataArrayDouble::substr method because a not contigous range can be specified here. + * This method is equavalent to DataArrayInt::renumberAndReduce except that convention in input is new2old and \b not old2new. + */ +DataArrayInt *DataArrayInt::selectByTupleId(const int *new2OldBg, const int *new2OldEnd) const +{ + DataArrayInt *ret=DataArrayInt::New(); + int nbComp=getNumberOfComponents(); + ret->alloc(std::distance(new2OldBg,new2OldEnd),nbComp); + ret->copyStringInfoFrom(*this); + int *pt=ret->getPointer(); + const int *srcPt=getConstPointer(); + int i=0; + for(const int *w=new2OldBg;w!=new2OldEnd;w++,i++) + std::copy(srcPt+(*w)*nbComp,srcPt+((*w)+1)*nbComp,pt+i*nbComp); + ret->copyStringInfoFrom(*this); return ret; } @@ -1211,24 +1426,6 @@ DataArrayInt *DataArrayInt::changeNbOfComponents(int newNbOfComp, int dftValue) return ret; } - -/*! - * This method is a generalization of DataArrayDouble::substr method because a not contigous range can be specified here. - */ -DataArrayInt *DataArrayInt::selectByTupleId(const int *start, const int *end) const -{ - DataArrayInt *ret=DataArrayInt::New(); - int nbComp=getNumberOfComponents(); - ret->alloc(std::distance(start,end),nbComp); - ret->copyStringInfoFrom(*this); - int *pt=ret->getPointer(); - const int *srcPt=getConstPointer(); - int i=0; - for(const int *w=start;w!=end;w++,i++) - std::copy(srcPt+(*w)*nbComp,srcPt+((*w)+1)*nbComp,pt+i*nbComp); - return ret; -} - void DataArrayInt::reAlloc(int nbOfTuples) { _mem.reAlloc(_info_on_compo.size()*nbOfTuples); diff --git a/src/MEDCoupling/MEDCouplingMemArray.hxx b/src/MEDCoupling/MEDCouplingMemArray.hxx index d3b57c927..c866a80b3 100644 --- a/src/MEDCoupling/MEDCouplingMemArray.hxx +++ b/src/MEDCoupling/MEDCouplingMemArray.hxx @@ -88,8 +88,8 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT void reprWithoutNameStream(std::ostream& stream) const; MEDCOUPLING_EXPORT std::string getName() const { return _name; } MEDCOUPLING_EXPORT const std::vector &getInfoOnComponent() const { return _info_on_compo; } - MEDCOUPLING_EXPORT std::string getInfoOnComponent(int i) const { return _info_on_compo[i]; } - MEDCOUPLING_EXPORT void setInfoOnComponent(int i, const char *info) { _info_on_compo[i]=info; } + MEDCOUPLING_EXPORT std::string getInfoOnComponent(int i) const throw(INTERP_KERNEL::Exception); + MEDCOUPLING_EXPORT void setInfoOnComponent(int i, const char *info) throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT int getNumberOfComponents() const { return _info_on_compo.size(); } MEDCOUPLING_EXPORT int getNumberOfTuples() const { return _nb_of_tuples; } MEDCOUPLING_EXPORT int getNbOfElems() const { return _info_on_compo.size()*_nb_of_tuples; } @@ -115,6 +115,7 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT DataArrayDouble *performCpy(bool deepCpy) const; MEDCOUPLING_EXPORT void alloc(int nbOfTuple, int nbOfCompo); MEDCOUPLING_EXPORT void fillWithZero(); + MEDCOUPLING_EXPORT void fillWithValue(double val); MEDCOUPLING_EXPORT std::string repr() const; MEDCOUPLING_EXPORT std::string reprZip() const; MEDCOUPLING_EXPORT void reprStream(std::ostream& stream) const; @@ -122,14 +123,18 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT void reprWithoutNameStream(std::ostream& stream) const; MEDCOUPLING_EXPORT void reprZipWithoutNameStream(std::ostream& stream) const; MEDCOUPLING_EXPORT bool isEqual(const DataArrayDouble& other, double prec) const; + MEDCOUPLING_EXPORT bool isEqualWithoutConsideringStr(const DataArrayDouble& other, double prec) const; //!alloc or useArray should have been called before. MEDCOUPLING_EXPORT void reAlloc(int nbOfTuples); MEDCOUPLING_EXPORT DataArrayInt *convertToIntArr() const; MEDCOUPLING_EXPORT void renumberInPlace(const int *old2New); + MEDCOUPLING_EXPORT void renumberInPlaceR(const int *new2Old); MEDCOUPLING_EXPORT DataArrayDouble *renumber(const int *old2New) const; + MEDCOUPLING_EXPORT DataArrayDouble *renumberR(const int *new2Old) const; + MEDCOUPLING_EXPORT DataArrayDouble *renumberAndReduce(const int *old2New, int newNbOfTuple) const; + MEDCOUPLING_EXPORT DataArrayDouble *selectByTupleId(const int *new2OldBg, const int *new2OldEnd) const; MEDCOUPLING_EXPORT DataArrayDouble *substr(int tupleIdBg, int tupleIdEnd=-1) const throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT DataArrayDouble *changeNbOfComponents(int newNbOfComp, double dftValue) const throw(INTERP_KERNEL::Exception); - MEDCOUPLING_EXPORT DataArrayDouble *selectByTupleId(const int *start, const int *end) const; MEDCOUPLING_EXPORT void getTuple(int tupleId, double *res) const { std::copy(_mem.getConstPointerLoc(tupleId*_info_on_compo.size()),_mem.getConstPointerLoc((tupleId+1)*_info_on_compo.size()),res); } MEDCOUPLING_EXPORT double getIJ(int tupleId, int compoId) const { return _mem[tupleId*_info_on_compo.size()+compoId]; } MEDCOUPLING_EXPORT void setIJ(int tupleId, int compoId, double newVal) { _mem[tupleId*_info_on_compo.size()+compoId]=newVal; declareAsNew(); } @@ -141,6 +146,8 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT void checkNoNullValues() const throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT double getMaxValue(int& tupleId) const throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT double getMinValue(int& tupleId) const throw(INTERP_KERNEL::Exception); + MEDCOUPLING_EXPORT double getMaxValue2(DataArrayInt*& tupleIds) const throw(INTERP_KERNEL::Exception); + MEDCOUPLING_EXPORT double getMinValue2(DataArrayInt*& tupleIds) const throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT double getAverageValue() const throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT void accumulate(double *res) const; MEDCOUPLING_EXPORT double accumulate(int compId) const; @@ -190,7 +197,9 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT DataArrayInt *performCpy(bool deepCpy) const; MEDCOUPLING_EXPORT void alloc(int nbOfTuple, int nbOfCompo); MEDCOUPLING_EXPORT bool isEqual(const DataArrayInt& other) const; + MEDCOUPLING_EXPORT bool isEqualWithoutConsideringStr(const DataArrayInt& other) const; MEDCOUPLING_EXPORT void fillWithZero(); + MEDCOUPLING_EXPORT void fillWithValue(int val); MEDCOUPLING_EXPORT std::string repr() const; MEDCOUPLING_EXPORT std::string reprZip() const; MEDCOUPLING_EXPORT void reprStream(std::ostream& stream) const; @@ -199,15 +208,19 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT void reprZipWithoutNameStream(std::ostream& stream) const; MEDCOUPLING_EXPORT void transformWithIndArr(const int *indArr); MEDCOUPLING_EXPORT DataArrayInt *invertArrayO2N2N2O(int newNbOfElem) const; + MEDCOUPLING_EXPORT DataArrayInt *invertArrayN2O2O2N(int oldNbOfElem) const; //!alloc or useArray should have been called before. MEDCOUPLING_EXPORT void reAlloc(int nbOfTuples); MEDCOUPLING_EXPORT DataArrayDouble *convertToDblArr() const; MEDCOUPLING_EXPORT void renumberInPlace(const int *old2New); + MEDCOUPLING_EXPORT void renumberInPlaceR(const int *new2Old); MEDCOUPLING_EXPORT DataArrayInt *renumber(const int *old2New) const; + MEDCOUPLING_EXPORT DataArrayInt *renumberR(const int *new2Old) const; + MEDCOUPLING_EXPORT DataArrayInt *renumberAndReduce(const int *old2NewBg, int newNbOfTuple) const; + MEDCOUPLING_EXPORT DataArrayInt *selectByTupleId(const int *new2OldBg, const int *new2OldEnd) const; MEDCOUPLING_EXPORT bool isIdentity() const; MEDCOUPLING_EXPORT DataArrayInt *substr(int tupleIdBg, int tupleIdEnd=-1) const throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT DataArrayInt *changeNbOfComponents(int newNbOfComp, int dftValue) const throw(INTERP_KERNEL::Exception); - MEDCOUPLING_EXPORT DataArrayInt *selectByTupleId(const int *start, const int *end) const; MEDCOUPLING_EXPORT void getTuple(int tupleId, int *res) const { std::copy(_mem.getConstPointerLoc(tupleId*_info_on_compo.size()),_mem.getConstPointerLoc((tupleId+1)*_info_on_compo.size()),res); } MEDCOUPLING_EXPORT int getIJ(int tupleId, int compoId) const { return _mem[tupleId*_info_on_compo.size()+compoId]; } MEDCOUPLING_EXPORT void setIJ(int tupleId, int compoId, int newVal) { _mem[tupleId*_info_on_compo.size()+compoId]=newVal; } diff --git a/src/MEDCoupling/MEDCouplingMemArray.txx b/src/MEDCoupling/MEDCouplingMemArray.txx index 21c88c78c..5a1a048d5 100644 --- a/src/MEDCoupling/MEDCouplingMemArray.txx +++ b/src/MEDCoupling/MEDCouplingMemArray.txx @@ -87,6 +87,8 @@ namespace ParaMEDMEM return true; if(pt1==0 || pt2==0) return false; + if(pt1==pt2) + return true; for(int i=0;i<_nb_of_elem;i++) if(pt1[i]-pt2[i]<-prec || (pt1[i]-pt2[i])>prec) return false; diff --git a/src/MEDCoupling/MEDCouplingMesh.cxx b/src/MEDCoupling/MEDCouplingMesh.cxx index cf181274f..cd3157568 100644 --- a/src/MEDCoupling/MEDCouplingMesh.cxx +++ b/src/MEDCoupling/MEDCouplingMesh.cxx @@ -21,9 +21,9 @@ #include "MEDCouplingMemArray.hxx" #include "MEDCouplingFieldDouble.hxx" #include "MEDCouplingFieldDiscretization.hxx" +#include "MEDCouplingAutoRefCountObjectPtr.hxx" -#include "InterpKernelExprParser.hxx" - +#include #include #include @@ -55,7 +55,9 @@ bool MEDCouplingMesh::isEqual(const MEDCouplingMesh *other, double prec) const * Possible values for levOfCheck : * - 0 for strict equality. This is the strongest level. 'cellCor' and 'nodeCor' params are never informed. * - 10,11,12 for less strict equality. Two meshes are compared geometrically. In case of success 'cellCor' and 'nodeCor' are informed. Warning ! These equivalences are CPU/Mem costly. The 3 values correspond respectively to policy used for cell comparison (see MEDCouplingUMesh::zipConnectivityTraducer to have more details) + * - 20,21,22, for less strict equality. Two meshes are compared geometrically. The difference with the previous version is that nodes(coordinates) are expected to be the same between this and other. In case of success 'cellCor' is informed. Warning ! These equivalences are CPU/Mem costly. The 3 values correspond respectively to policy used for cell comparison (see MEDCouplingUMesh::zipConnectivityTraducer to have more details) * - 1 for fast 'equality'. This is a lazy level. Just number of cells and number of nodes are considered here and 3 cells (begin,middle,end) + * - 2 for deep 'equality' as 0 option except that no control is done on all strings in mesh. */ void MEDCouplingMesh::checkGeoEquivalWith(const MEDCouplingMesh *other, int levOfCheck, double prec, DataArrayInt *&cellCor, DataArrayInt *&nodeCor) const throw(INTERP_KERNEL::Exception) @@ -79,16 +81,56 @@ void MEDCouplingMesh::checkGeoEquivalWith(const MEDCouplingMesh *other, int levO checkDeepEquivalWith(other,levOfCheck-10,prec,cellCor,nodeCor); return ; } + case 20: + case 21: + case 22: + { + checkDeepEquivalOnSameNodesWith(other,levOfCheck-20,prec,cellCor); + return ; + } case 1: { checkFastEquivalWith(other,prec); return; } + case 2: + { + if(!isEqualWithoutConsideringStr(other,prec)) + throw INTERP_KERNEL::Exception("checkGeoFitWith : Meshes are not equal without considering strings !"); + return ; + } default: - throw INTERP_KERNEL::Exception("checkGeoFitWith : Invalid levOfCheck specified ! Value must be in 0,1,10,11 or 12."); + throw INTERP_KERNEL::Exception("checkGeoFitWith : Invalid levOfCheck specified ! Value must be in 0,1,2,10,11 or 12."); } } +/*! + * Given a nodeIds range ['partBg','partEnd'), this method returns the set of cell ids in ascendant order whose connectivity of + * these cells are fully included in the range. As a consequence the returned set of cell ids does \b not \b always fit the nodes in ['partBg','partEnd') + * This method returns the corresponding cells in a newly created array that the caller has the responsability. + */ +DataArrayInt *MEDCouplingMesh::getCellIdsFullyIncludedInNodeIds(const int *partBg, const int *partEnd) const +{ + std::vector crest; + std::set p(partBg,partEnd); + int nbOfCells=getNumberOfCells(); + for(int i=0;i conn; + getNodeIdsOfCell(i,conn); + bool cont=true; + for(std::vector::const_iterator iter=conn.begin();iter!=conn.end() && cont;iter++) + if(p.find(*iter)==p.end()) + cont=false; + if(cont) + crest.push_back(i); + } + DataArrayInt *ret=DataArrayInt::New(); + ret->alloc(crest.size(),1); + std::copy(crest.begin(),crest.end(),ret->getPointer()); + return ret; +} + /*! * This method checks fastly that 'this' and 'other' are equal. All common checks are done here. */ @@ -127,32 +169,10 @@ bool MEDCouplingMesh::areCompatibleForMerge(const MEDCouplingMesh *other) const */ MEDCouplingFieldDouble *MEDCouplingMesh::fillFromAnalytic(TypeOfField t, int nbOfComp, FunctionToEvaluate func) const { - MEDCouplingFieldDouble *ret=MEDCouplingFieldDouble::New(t); + MEDCouplingAutoRefCountObjectPtr ret=MEDCouplingFieldDouble::New(t,NO_TIME); ret->setMesh(this); - DataArrayDouble *loc=ret->getDiscretization()->getLocalizationOfDiscValues(this); - DataArrayDouble *array=DataArrayDouble::New(); - int nbOfTuple=loc->getNumberOfTuples(); - int nbCompIn=loc->getNumberOfComponents(); - const double *locPtr=loc->getConstPointer(); - array->alloc(nbOfTuple,nbOfComp); - double *ptToFill=array->getPointer(); - for(int i=0;i(oss,", ")); - oss << ") : Evaluation of function failed !"; - loc->decrRef(); - array->decrRef(); - ret->decrRef(); - throw INTERP_KERNEL::Exception(oss.str().c_str()); - } - ptToFill+=nbOfComp; - } - loc->decrRef(); - ret->setArray(array); - array->decrRef(); + ret->fillFromAnalytic(nbOfComp,func); + ret->incrRef(); return ret; } @@ -177,50 +197,10 @@ void MEDCouplingMesh::copyTinyStringsFrom(const MEDCouplingMesh *other) throw(IN */ MEDCouplingFieldDouble *MEDCouplingMesh::fillFromAnalytic(TypeOfField t, int nbOfComp, const char *func) const { - INTERP_KERNEL::ExprParser expr(func); - expr.parse(); - std::set vars; - expr.getTrueSetOfVars(vars); - if((int)vars.size()>getSpaceDimension()) - { - std::ostringstream oss; oss << "The mesh has a spaceDim==" << getSpaceDimension() << " and there are "; - oss << vars.size() << " variables : "; - std::copy(vars.begin(),vars.end(),std::ostream_iterator(oss," ")); - throw INTERP_KERNEL::Exception(oss.str().c_str()); - } - std::vector varsV(vars.begin(),vars.end()); - expr.prepareExprEvaluation(varsV); - // - MEDCouplingFieldDouble *ret=MEDCouplingFieldDouble::New(t); + MEDCouplingAutoRefCountObjectPtr ret=MEDCouplingFieldDouble::New(t,NO_TIME); ret->setMesh(this); - DataArrayDouble *loc=ret->getDiscretization()->getLocalizationOfDiscValues(this); - DataArrayDouble *array=DataArrayDouble::New(); - int nbOfTuple=loc->getNumberOfTuples(); - int nbCompIn=loc->getNumberOfComponents(); - const double *locPtr=loc->getConstPointer(); - array->alloc(nbOfTuple,nbOfComp); - double *ptToFill=array->getPointer(); - for(int i=0;i(oss,", ")); - oss << ") : Evaluation of function failed ! " << e.what(); - loc->decrRef(); - array->decrRef(); - ret->decrRef(); - throw INTERP_KERNEL::Exception(oss.str().c_str()); - } - ptToFill+=nbOfComp; - } - loc->decrRef(); - ret->setArray(array); - array->decrRef(); + ret->fillFromAnalytic(nbOfComp,func); + ret->incrRef(); return ret; } diff --git a/src/MEDCoupling/MEDCouplingMesh.hxx b/src/MEDCoupling/MEDCouplingMesh.hxx index 7ca13c6f3..524c23017 100644 --- a/src/MEDCoupling/MEDCouplingMesh.hxx +++ b/src/MEDCoupling/MEDCouplingMesh.hxx @@ -53,8 +53,11 @@ namespace ParaMEDMEM virtual void copyTinyStringsFrom(const MEDCouplingMesh *other) throw(INTERP_KERNEL::Exception); // comparison methods virtual bool isEqual(const MEDCouplingMesh *other, double prec) const; + virtual bool isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const = 0; virtual void checkDeepEquivalWith(const MEDCouplingMesh *other, int cellCompPol, double prec, DataArrayInt *&cellCor, DataArrayInt *&nodeCor) const throw(INTERP_KERNEL::Exception) = 0; + virtual void checkDeepEquivalOnSameNodesWith(const MEDCouplingMesh *other, int cellCompPol, double prec, + DataArrayInt *&cellCor) const throw(INTERP_KERNEL::Exception) = 0; virtual void checkFastEquivalWith(const MEDCouplingMesh *other, double prec) const throw(INTERP_KERNEL::Exception); void checkGeoEquivalWith(const MEDCouplingMesh *other, int levOfCheck, double prec, DataArrayInt *&cellCor, DataArrayInt *&nodeCor) const throw(INTERP_KERNEL::Exception); @@ -69,6 +72,7 @@ namespace ParaMEDMEM virtual int getNumberOfCellsWithType(INTERP_KERNEL::NormalizedCellType type) const = 0; virtual INTERP_KERNEL::NormalizedCellType getTypeOfCell(int cellId) const = 0; virtual void getNodeIdsOfCell(int cellId, std::vector& conn) const = 0; + virtual DataArrayInt *getCellIdsFullyIncludedInNodeIds(const int *partBg, const int *partEnd) const; virtual void getCoordinatesOfNode(int nodeId, std::vector& coo) const = 0; virtual std::string simpleRepr() const = 0; virtual std::string advancedRepr() const = 0; @@ -82,6 +86,7 @@ namespace ParaMEDMEM virtual MEDCouplingFieldDouble *buildOrthogonalField() const = 0; virtual void rotate(const double *center, const double *vector, double angle) = 0; virtual void translate(const double *vector) = 0; + virtual void scale(const double *point, double factor) = 0; virtual void renumberCells(const int *old2NewBg, bool check) throw(INTERP_KERNEL::Exception) = 0; virtual MEDCouplingMesh *mergeMyselfWith(const MEDCouplingMesh *other) const = 0; virtual MEDCouplingMesh *buildPart(const int *start, const int *end) const = 0; diff --git a/src/MEDCoupling/MEDCouplingNatureOfField.hxx b/src/MEDCoupling/MEDCouplingNatureOfField.hxx index bdd28a6db..89f9125e0 100644 --- a/src/MEDCoupling/MEDCouplingNatureOfField.hxx +++ b/src/MEDCoupling/MEDCouplingNatureOfField.hxx @@ -20,6 +20,7 @@ #ifndef __PARAMEDMEM_MEDCOUPLINGNATUREOFFIELD_HXX__ #define __PARAMEDMEM_MEDCOUPLINGNATUREOFFIELD_HXX__ +#include "MEDCoupling.hxx" #include "InterpKernelException.hxx" namespace ParaMEDMEM @@ -36,7 +37,7 @@ namespace ParaMEDMEM class MEDCouplingNatureOfField { public: - static const char *getRepr(NatureOfField nat) throw(INTERP_KERNEL::Exception); + MEDCOUPLING_EXPORT static const char *getRepr(NatureOfField nat) throw(INTERP_KERNEL::Exception); private: static const int NB_OF_POSSIBILITIES=5; static const char *REPR_OF_NATUREOFFIELD[NB_OF_POSSIBILITIES]; diff --git a/src/MEDCoupling/MEDCouplingPointSet.cxx b/src/MEDCoupling/MEDCouplingPointSet.cxx index e0dec42a8..87964cbdf 100644 --- a/src/MEDCoupling/MEDCouplingPointSet.cxx +++ b/src/MEDCoupling/MEDCouplingPointSet.cxx @@ -119,6 +119,16 @@ bool MEDCouplingPointSet::isEqual(const MEDCouplingMesh *other, double prec) con return true; } +bool MEDCouplingPointSet::isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const +{ + const MEDCouplingPointSet *otherC=dynamic_cast(other); + if(!otherC) + return false; + if(!areCoordsEqualWithoutConsideringStr(*otherC,prec)) + return false; + return true; +} + bool MEDCouplingPointSet::areCoordsEqual(const MEDCouplingPointSet& other, double prec) const { if(_coords==0 && other._coords==0) @@ -130,6 +140,17 @@ bool MEDCouplingPointSet::areCoordsEqual(const MEDCouplingPointSet& other, doubl return _coords->isEqual(*other._coords,prec); } +bool MEDCouplingPointSet::areCoordsEqualWithoutConsideringStr(const MEDCouplingPointSet& other, double prec) const +{ + if(_coords==0 && other._coords==0) + return true; + if(_coords==0 || other._coords==0) + return false; + if(_coords==other._coords) + return true; + return _coords->isEqualWithoutConsideringStr(*other._coords,prec); +} + /*! * This method is typically the base method used for implementation of mergeNodes. This method computes this permutation array using as input, * This method is const ! So this method simply computes the array, no permutation of nodes is done. @@ -143,7 +164,7 @@ DataArrayInt *MEDCouplingPointSet::buildPermArrayForMergeNode(int limitNodeId, d DataArrayInt *comm,*commI; findCommonNodes(limitNodeId,precision,comm,commI); int oldNbOfNodes=getNumberOfNodes(); - DataArrayInt *ret=buildNewNumberingFromCommNodesFrmt(comm,commI,newNbOfNodes); + DataArrayInt *ret=buildNewNumberingFromCommonNodesFormat(comm,commI,newNbOfNodes); areNodesMerged=(oldNbOfNodes!=newNbOfNodes); comm->decrRef(); commI->decrRef(); @@ -201,8 +222,8 @@ void MEDCouplingPointSet::findCommonNodes(int limitNodeId, double prec, DataArra * @param commI in param in the same format than one returned by findCommonNodes method. * @return the old to new correspondance array. */ -DataArrayInt *MEDCouplingPointSet::buildNewNumberingFromCommNodesFrmt(const DataArrayInt *comm, const DataArrayInt *commIndex, - int& newNbOfNodes) const +DataArrayInt *MEDCouplingPointSet::buildNewNumberingFromCommonNodesFormat(const DataArrayInt *comm, const DataArrayInt *commIndex, + int& newNbOfNodes) const { DataArrayInt *ret=DataArrayInt::New(); int nbNodesOld=getNumberOfNodes(); @@ -415,7 +436,7 @@ void MEDCouplingPointSet::tryToShareSameCoords(const MEDCouplingPointSet& other, throw INTERP_KERNEL::Exception("Current instance has no coords whereas other has !"); if(!other._coords) throw INTERP_KERNEL::Exception("Other instance has no coords whereas current has !"); - if(!_coords->isEqual(*other._coords,epsilon)) + if(!_coords->isEqualWithoutConsideringStr(*other._coords,epsilon)) throw INTERP_KERNEL::Exception("Coords are not the same !"); setCoords(other._coords); } @@ -672,7 +693,7 @@ MEDCouplingMesh *MEDCouplingPointSet::buildPart(const int *start, const int *end /*! * This method implements pure virtual method MEDCouplingMesh::buildPartAndReduceNodes. * This method build a part of 'this' by simply keeping cells whose ids are in ['start','end') \b and potentially reduces the nodes set - * behind returned mesh. This cause an overhead but it is more little in memory. + * behind returned mesh. This cause an overhead but it is lesser in memory. * This method returns an array too. This array allows to the caller to know the mapping between nodeids in 'this' and nodeids in * returned mesh. This is quite usefull for MEDCouplingFieldDouble on nodes for example... * The returned mesh has to be managed by the caller. diff --git a/src/MEDCoupling/MEDCouplingPointSet.hxx b/src/MEDCoupling/MEDCouplingPointSet.hxx index 53aa5ea40..87a4c04ec 100644 --- a/src/MEDCoupling/MEDCouplingPointSet.hxx +++ b/src/MEDCoupling/MEDCouplingPointSet.hxx @@ -50,12 +50,14 @@ namespace ParaMEDMEM DataArrayDouble *getCoordinatesAndOwner() const; void copyTinyStringsFrom(const MEDCouplingMesh *other) throw(INTERP_KERNEL::Exception); bool isEqual(const MEDCouplingMesh *other, double prec) const; + bool isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const; bool areCoordsEqual(const MEDCouplingPointSet& other, double prec) const; + bool areCoordsEqualWithoutConsideringStr(const MEDCouplingPointSet& other, double prec) const; virtual DataArrayInt *mergeNodes(double precision, bool& areNodesMerged, int& newNbOfNodes) = 0; DataArrayInt *buildPermArrayForMergeNode(int limitNodeId, double precision, bool& areNodesMerged, int& newNbOfNodes) const; void findCommonNodes(int limitNodeId, double prec, DataArrayInt *&comm, DataArrayInt *&commIndex) const; - DataArrayInt *buildNewNumberingFromCommNodesFrmt(const DataArrayInt *comm, const DataArrayInt *commIndex, - int& newNbOfNodes) const; + DataArrayInt *buildNewNumberingFromCommonNodesFormat(const DataArrayInt *comm, const DataArrayInt *commIndex, + int& newNbOfNodes) const; void getBoundingBox(double *bbox) const; void zipCoords(); double getCaracteristicDimension() const; diff --git a/src/MEDCoupling/MEDCouplingRemapper.cxx b/src/MEDCoupling/MEDCouplingRemapper.cxx index 3337b8b4e..bb494899b 100644 --- a/src/MEDCoupling/MEDCouplingRemapper.cxx +++ b/src/MEDCoupling/MEDCouplingRemapper.cxx @@ -378,8 +378,8 @@ void MEDCouplingRemapper::computeDenoFromScratch(NatureOfField nat, const MEDCou } case Integral: { - MEDCouplingFieldDouble *deno=srcField->getDiscretization()->getWeightingField(srcField->getMesh(),true); - MEDCouplingFieldDouble *denoR=trgField->getDiscretization()->getWeightingField(trgField->getMesh(),true); + MEDCouplingFieldDouble *deno=srcField->getDiscretization()->getMeasureField(srcField->getMesh(),true); + MEDCouplingFieldDouble *denoR=trgField->getDiscretization()->getMeasureField(trgField->getMesh(),true); const double *denoPtr=deno->getArray()->getConstPointer(); const double *denoRPtr=denoR->getArray()->getConstPointer(); if(trgField->getMesh()->getMeshDimension()==-1) @@ -410,8 +410,8 @@ void MEDCouplingRemapper::computeDenoFromScratch(NatureOfField nat, const MEDCou } case RevIntegral: { - MEDCouplingFieldDouble *deno=trgField->getDiscretization()->getWeightingField(trgField->getMesh(),true); - MEDCouplingFieldDouble *denoR=srcField->getDiscretization()->getWeightingField(srcField->getMesh(),true); + MEDCouplingFieldDouble *deno=trgField->getDiscretization()->getMeasureField(trgField->getMesh(),true); + MEDCouplingFieldDouble *denoR=srcField->getDiscretization()->getMeasureField(srcField->getMesh(),true); const double *denoPtr=deno->getArray()->getConstPointer(); const double *denoRPtr=denoR->getArray()->getConstPointer(); if(trgField->getMesh()->getMeshDimension()==-1) diff --git a/src/MEDCoupling/MEDCouplingTimeDiscretization.cxx b/src/MEDCoupling/MEDCouplingTimeDiscretization.cxx index 734f46aa1..a98a75f58 100644 --- a/src/MEDCoupling/MEDCouplingTimeDiscretization.cxx +++ b/src/MEDCoupling/MEDCouplingTimeDiscretization.cxx @@ -23,6 +23,7 @@ #include #include +#include using namespace ParaMEDMEM; @@ -139,6 +140,15 @@ bool MEDCouplingTimeDiscretization::isEqual(const MEDCouplingTimeDiscretization return _array->isEqual(*other->_array,prec); } +bool MEDCouplingTimeDiscretization::isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const +{ + if(!areStrictlyCompatible(other)) + return false; + if(_array==other->_array) + return true; + return _array->isEqualWithoutConsideringStr(*other->_array,prec); +} + MEDCouplingTimeDiscretization *MEDCouplingTimeDiscretization::buildNewTimeReprFromThis(const MEDCouplingTimeDiscretization *other, TypeOfTimeDiscretization type, bool deepCpy) const { @@ -483,6 +493,33 @@ void MEDCouplingTimeDiscretization::sortPerTuple(bool asc) throw(INTERP_KERNEL:: } } +void MEDCouplingTimeDiscretization::setUniformValue(int nbOfTuple, double value) +{ + std::vector arrays; + getArrays(arrays); + std::vector< MEDCouplingAutoRefCountObjectPtr > arrays2(arrays.size()); + for(int j=0;j<(int)arrays.size();j++) + { + if(arrays[j]) + { + arrays[j]->incrRef(); + arrays[j]->fillWithValue(value); + arrays2[j]=arrays[j]; + } + else + { + DataArrayDouble *tmp=DataArrayDouble::New(); + tmp->alloc(nbOfTuple,1); + tmp->fillWithValue(value); + arrays2[j]=tmp; + } + } + std::vector arrays3(arrays.size()); + for(int j=0;j<(int)arrays.size();j++) + arrays3[j]=arrays2[j]; + setArrays(arrays3,0); +} + void MEDCouplingTimeDiscretization::applyLin(double a, double b, int compoId) { std::vector arrays; @@ -570,6 +607,32 @@ void MEDCouplingTimeDiscretization::applyFuncFast64(const char *func) } } +void MEDCouplingTimeDiscretization::fillFromAnalytic(const DataArrayDouble *loc, int nbOfComp, FunctionToEvaluate func) throw(INTERP_KERNEL::Exception) +{ + std::vector arrays; + getArrays(arrays); + std::vector< MEDCouplingAutoRefCountObjectPtr > arrays2(arrays.size()); + for(int j=0;j<(int)arrays.size();j++) + arrays2[j]=loc->applyFunc(nbOfComp,func); + std::vector arrays3(arrays.size()); + for(int j=0;j<(int)arrays.size();j++) + arrays3[j]=arrays2[j]; + setArrays(arrays3,0); +} + +void MEDCouplingTimeDiscretization::fillFromAnalytic(const DataArrayDouble *loc, int nbOfComp, const char *func) throw(INTERP_KERNEL::Exception) +{ + std::vector arrays; + getArrays(arrays); + std::vector< MEDCouplingAutoRefCountObjectPtr > arrays2(arrays.size()); + for(int j=0;j<(int)arrays.size();j++) + arrays2[j]=loc->applyFunc(nbOfComp,func); + std::vector arrays3(arrays.size()); + for(int j=0;j<(int)arrays.size();j++) + arrays3[j]=arrays2[j]; + setArrays(arrays3,0); +} + MEDCouplingNoTimeLabel::MEDCouplingNoTimeLabel() { } @@ -617,6 +680,14 @@ bool MEDCouplingNoTimeLabel::isEqual(const MEDCouplingTimeDiscretization *other, return MEDCouplingTimeDiscretization::isEqual(other,prec); } +bool MEDCouplingNoTimeLabel::isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const +{ + const MEDCouplingNoTimeLabel *otherC=dynamic_cast(other); + if(!otherC) + return false; + return MEDCouplingTimeDiscretization::isEqualWithoutConsideringStr(other,prec); +} + MEDCouplingTimeDiscretization *MEDCouplingNoTimeLabel::aggregate(const MEDCouplingTimeDiscretization *other) const { const MEDCouplingNoTimeLabel *otherC=dynamic_cast(other); @@ -893,6 +964,20 @@ bool MEDCouplingWithTimeStep::isEqual(const MEDCouplingTimeDiscretization *other return MEDCouplingTimeDiscretization::isEqual(other,prec); } +bool MEDCouplingWithTimeStep::isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const +{ + const MEDCouplingWithTimeStep *otherC=dynamic_cast(other); + if(!otherC) + return false; + if(_iteration!=otherC->_iteration) + return false; + if(_order!=otherC->_order) + return false; + if(std::fabs(_time-otherC->_time)>_time_tolerance) + return false; + return MEDCouplingTimeDiscretization::isEqualWithoutConsideringStr(other,prec); +} + void MEDCouplingWithTimeStep::copyTinyAttrFrom(const MEDCouplingTimeDiscretization& other) { MEDCouplingTimeDiscretization::copyTinyAttrFrom(other); @@ -1240,6 +1325,26 @@ bool MEDCouplingConstOnTimeInterval::isEqual(const MEDCouplingTimeDiscretization return MEDCouplingTimeDiscretization::isEqual(other,prec); } +bool MEDCouplingConstOnTimeInterval::isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const +{ + const MEDCouplingConstOnTimeInterval *otherC=dynamic_cast(other); + if(!otherC) + return false; + if(_start_iteration!=otherC->_start_iteration) + return false; + if(_start_order!=otherC->_start_order) + return false; + if(std::fabs(_start_time-otherC->_start_time)>_time_tolerance) + return false; + if(_end_iteration!=otherC->_end_iteration) + return false; + if(_end_order!=otherC->_end_order) + return false; + if(std::fabs(_end_time-otherC->_end_time)>_time_tolerance) + return false; + return MEDCouplingTimeDiscretization::isEqualWithoutConsideringStr(other,prec); +} + void MEDCouplingConstOnTimeInterval::getValueOnTime(int eltId, double time, double *value) const throw(INTERP_KERNEL::Exception) { if(time>_start_time-_time_tolerance && time<_end_time+_time_tolerance) @@ -1523,6 +1628,29 @@ bool MEDCouplingTwoTimeSteps::isEqual(const MEDCouplingTimeDiscretization *other return MEDCouplingTimeDiscretization::isEqual(other,prec); } +bool MEDCouplingTwoTimeSteps::isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const +{ + const MEDCouplingTwoTimeSteps *otherC=dynamic_cast(other); + if(!otherC) + return false; + if(_start_iteration!=otherC->_start_iteration) + return false; + if(_end_iteration!=otherC->_end_iteration) + return false; + if(_start_order!=otherC->_start_order) + return false; + if(_end_order!=otherC->_end_order) + return false; + if(std::fabs(_start_time-otherC->_start_time)>_time_tolerance) + return false; + if(std::fabs(_end_time-otherC->_end_time)>_time_tolerance) + return false; + if(_end_array!=otherC->_end_array) + if(!_end_array->isEqualWithoutConsideringStr(*otherC->_end_array,prec)) + return false; + return MEDCouplingTimeDiscretization::isEqualWithoutConsideringStr(other,prec); +} + MEDCouplingTwoTimeSteps::MEDCouplingTwoTimeSteps():_start_time(0.),_end_time(0.),_start_iteration(-1),_end_iteration(-1),_start_order(-1),_end_order(-1),_end_array(0) { } diff --git a/src/MEDCoupling/MEDCouplingTimeDiscretization.hxx b/src/MEDCoupling/MEDCouplingTimeDiscretization.hxx index d128ec7a5..f3e80dd9b 100644 --- a/src/MEDCoupling/MEDCouplingTimeDiscretization.hxx +++ b/src/MEDCoupling/MEDCouplingTimeDiscretization.hxx @@ -47,6 +47,7 @@ namespace ParaMEDMEM virtual bool areStrictlyCompatible(const MEDCouplingTimeDiscretization *other) const; virtual bool areStrictlyCompatibleForMul(const MEDCouplingTimeDiscretization *other) const; virtual bool isEqual(const MEDCouplingTimeDiscretization *other, double prec) const; + virtual bool isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const; virtual MEDCouplingTimeDiscretization *buildNewTimeReprFromThis(const MEDCouplingTimeDiscretization *other, TypeOfTimeDiscretization type, bool deepCpy) const; virtual std::string getStringRepr() const = 0; @@ -104,13 +105,15 @@ namespace ParaMEDMEM virtual MEDCouplingTimeDiscretization *maxPerTuple() const throw(INTERP_KERNEL::Exception); virtual void changeNbOfComponents(int newNbOfComp, double dftValue) throw(INTERP_KERNEL::Exception); virtual void sortPerTuple(bool asc) throw(INTERP_KERNEL::Exception); + virtual void setUniformValue(int nbOfTuple, double value); virtual void applyLin(double a, double b, int compoId); virtual void applyFunc(int nbOfComp, FunctionToEvaluate func); virtual void applyFunc(int nbOfComp, const char *func); virtual void applyFunc(const char *func); virtual void applyFuncFast32(const char *func); virtual void applyFuncFast64(const char *func); - + virtual void fillFromAnalytic(const DataArrayDouble *loc, int nbOfComp, FunctionToEvaluate func) throw(INTERP_KERNEL::Exception); + virtual void fillFromAnalytic(const DataArrayDouble *loc, int nbOfComp, const char *func) throw(INTERP_KERNEL::Exception); // virtual ~MEDCouplingTimeDiscretization(); protected: @@ -141,6 +144,7 @@ namespace ParaMEDMEM MEDCouplingTimeDiscretization *divide(const MEDCouplingTimeDiscretization *other) const; void divideEqual(const MEDCouplingTimeDiscretization *other); bool isEqual(const MEDCouplingTimeDiscretization *other, double prec) const; + bool isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const; bool areCompatible(const MEDCouplingTimeDiscretization *other) const; bool areStrictlyCompatible(const MEDCouplingTimeDiscretization *other) const; bool areStrictlyCompatibleForMul(const MEDCouplingTimeDiscretization *other) const; @@ -187,6 +191,7 @@ namespace ParaMEDMEM MEDCouplingTimeDiscretization *divide(const MEDCouplingTimeDiscretization *other) const; void divideEqual(const MEDCouplingTimeDiscretization *other); bool isEqual(const MEDCouplingTimeDiscretization *other, double prec) const; + bool isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const; bool areCompatible(const MEDCouplingTimeDiscretization *other) const; bool areStrictlyCompatible(const MEDCouplingTimeDiscretization *other) const; bool areStrictlyCompatibleForMul(const MEDCouplingTimeDiscretization *other) const; @@ -230,6 +235,7 @@ namespace ParaMEDMEM bool areStrictlyCompatible(const MEDCouplingTimeDiscretization *other) const; bool areStrictlyCompatibleForMul(const MEDCouplingTimeDiscretization *other) const; bool isEqual(const MEDCouplingTimeDiscretization *other, double prec) const; + bool isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const; std::vector< const DataArrayDouble *> getArraysForTime(double time) const throw(INTERP_KERNEL::Exception); void getValueForTime(double time, const std::vector& vals, double *res) const; void getValueOnTime(int eltId, double time, double *value) const throw(INTERP_KERNEL::Exception); @@ -282,6 +288,7 @@ namespace ParaMEDMEM DataArrayDouble *getEndArray() const; void checkCoherency() const throw(INTERP_KERNEL::Exception); bool isEqual(const MEDCouplingTimeDiscretization *other, double prec) const; + bool isEqualWithoutConsideringStr(const MEDCouplingTimeDiscretization *other, double prec) const; void checkNoTimePresence() const throw(INTERP_KERNEL::Exception); void checkTimePresence(double time) const throw(INTERP_KERNEL::Exception); void getArrays(std::vector& arrays) const; diff --git a/src/MEDCoupling/MEDCouplingUMesh.cxx b/src/MEDCoupling/MEDCouplingUMesh.cxx index e77d8bba4..11f9d12ea 100644 --- a/src/MEDCoupling/MEDCouplingUMesh.cxx +++ b/src/MEDCoupling/MEDCouplingUMesh.cxx @@ -25,6 +25,7 @@ #include "PointLocatorAlgos.txx" #include "BBTree.txx" #include "DirectedBoundingBox.hxx" +#include "InterpKernelMeshQuality.hxx" #include "MEDCouplingAutoRefCountObjectPtr.hxx" #include @@ -80,6 +81,12 @@ MEDCouplingUMesh::MEDCouplingUMesh():_iterator(-1),_mesh_dim(-2), { } +/*! + * This method checks that this is correctly designed. For example le coordinates are set, nodal connectivity. + * When this method returns without throwing any exception, 'this' is expected to be writable, exchangeable and to be + * available for most of algorithm. When a mesh has been constructed from scratch it is a good habits to call this method to check + * that all is in order in 'this'. + */ void MEDCouplingUMesh::checkCoherency() const throw(INTERP_KERNEL::Exception) { if(_mesh_dim<-1) @@ -201,6 +208,32 @@ bool MEDCouplingUMesh::isEqual(const MEDCouplingMesh *other, double prec) const return true; } +bool MEDCouplingUMesh::isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const +{ + const MEDCouplingUMesh *otherC=dynamic_cast(other); + if(!otherC) + return false; + if(!MEDCouplingPointSet::isEqualWithoutConsideringStr(other,prec)) + return false; + if(_mesh_dim!=otherC->_mesh_dim) + return false; + if(_types!=otherC->_types) + return false; + if(_nodal_connec!=0 || otherC->_nodal_connec!=0) + if(_nodal_connec==0 || otherC->_nodal_connec==0) + return false; + if(_nodal_connec!=otherC->_nodal_connec) + if(!_nodal_connec->isEqualWithoutConsideringStr(*otherC->_nodal_connec)) + return false; + if(_nodal_connec_index!=0 || otherC->_nodal_connec_index!=0) + if(_nodal_connec_index==0 || otherC->_nodal_connec_index==0) + return false; + if(_nodal_connec_index!=otherC->_nodal_connec_index) + if(!_nodal_connec_index->isEqualWithoutConsideringStr(*otherC->_nodal_connec_index)) + return false; + return true; +} + /*! * This method looks if 'this' and 'other' are geometrically equivalent that is to say if each cell in 'other' correspond to one cell and only one * in 'this' is found regarding 'prec' parameter and 'cellCompPol' parameter. @@ -258,6 +291,47 @@ void MEDCouplingUMesh::checkDeepEquivalWith(const MEDCouplingMesh *other, int ce } } +/*! + * This method looks if 'this' and 'other' are geometrically equivalent that is to say if each cell in 'other' correspond to one cell and only one + * in 'this' is found regarding 'prec' parameter and 'cellCompPol' parameter. The difference with MEDCouplingUMesh::checkDeepEquivalWith method is that + * coordinates of 'this' and 'other' are expected to be the same. If not an exception will be thrown. + * + * In case of success cellCor are informed both. + * @param cellCompPol values are described in MEDCouplingUMesh::zipConnectivityTraducer method. + * @param cellCor output array giving the correspondance of cells from 'other' to 'this'. + */ +void MEDCouplingUMesh::checkDeepEquivalOnSameNodesWith(const MEDCouplingMesh *other, int cellCompPol, double prec, + DataArrayInt *&cellCor) const throw(INTERP_KERNEL::Exception) +{ + const MEDCouplingUMesh *otherC=dynamic_cast(other); + if(!otherC) + throw INTERP_KERNEL::Exception("checkDeepEquivalOnSameNodesWith : Two meshes are not not unstructured !"); + MEDCouplingMesh::checkFastEquivalWith(other,prec); + if(_types!=otherC->_types) + throw INTERP_KERNEL::Exception("checkDeepEquivalOnSameNodesWith : Types are not equal !"); + if(_coords!=otherC->_coords) + throw INTERP_KERNEL::Exception("checkDeepEquivalOnSameNodesWith : meshes do not share the same coordinates ! Use tryToShareSameCoordinates or call checkDeepEquivalWith !"); + std::vector ms(2); + ms[0]=const_cast(this); + ms[1]=const_cast(otherC); + MEDCouplingAutoRefCountObjectPtr m=mergeUMeshesOnSameCoords(ms); + MEDCouplingAutoRefCountObjectPtr da=m->zipConnectivityTraducer(cellCompPol); + int maxId=*std::max_element(da->getConstPointer(),da->getConstPointer()+getNumberOfCells()); + const int *pt=std::find_if(da->getConstPointer()+getNumberOfCells(),da->getConstPointer()+da->getNbOfElems(),std::bind2nd(std::greater(),maxId)); + if(pt!=da->getConstPointer()+da->getNbOfElems()) + { + throw INTERP_KERNEL::Exception("checkDeepEquivalOnSameNodesWith : some cells in other are not in this !"); + } + cellCor=DataArrayInt::New(); + cellCor->alloc(otherC->getNumberOfCells(),1); + std::copy(da->getConstPointer()+getNumberOfCells(),da->getConstPointer()+da->getNbOfElems(),cellCor->getPointer()); + if(cellCor->isIdentity()) + { + cellCor->decrRef(); + cellCor=0; + } +} + /*! * This method checks fastly that 'this' and 'other' are equal. */ @@ -498,7 +572,9 @@ void MEDCouplingUMesh::convertToPolyTypes(const std::vector& cellIdsToConve DataArrayInt *MEDCouplingUMesh::zipCoordsTraducer() { int nbOfNodes=getNumberOfNodes(); - int *traducer=new int[nbOfNodes]; + DataArrayInt *ret=DataArrayInt::New(); + ret->alloc(nbOfNodes,1); + int *traducer=ret->getPointer(); std::fill(traducer,traducer+nbOfNodes,-1); int nbOfCells=getNumberOfCells(); const int *connIndex=_nodal_connec_index->getConstPointer(); @@ -513,14 +589,7 @@ DataArrayInt *MEDCouplingUMesh::zipCoordsTraducer() for(int j=connIndex[i]+1;j=0) conn[j]=traducer[conn[j]]; - DataArrayInt *ret=DataArrayInt::New(); - ret->alloc(newNbOfNodes,1); - int *retPtr=ret->getPointer(); - for(int i=0;iselectByTupleId(retPtr,retPtr+newNbOfNodes); + DataArrayDouble *newCoords=_coords->renumberAndReduce(traducer,newNbOfNodes); setCoords(newCoords); newCoords->decrRef(); return ret; @@ -820,44 +889,58 @@ void MEDCouplingUMesh::tryToShareSameCoordsPermute(const MEDCouplingPointSet& ot } /*! - * build a sub part of 'this'. This sub part is defined by the cell ids contained in the array in [start,end). - * @param start start of array containing the cell ids to keep. + * build a sub part of 'this'. This sub part is defined by the cell ids contained in the array in [begin,end). + * @param begin begin of array containing the cell ids to keep. * @param end end of array of cell ids to keep. \b WARNING end param is \b not included ! Idem STL standard definitions. * @param keepCoords that specifies if you want or not to keep coords as this or zip it (see zipCoords) */ -MEDCouplingPointSet *MEDCouplingUMesh::buildPartOfMySelf(const int *start, const int *end, bool keepCoords) const +MEDCouplingPointSet *MEDCouplingUMesh::buildPartOfMySelf(const int *begin, const int *end, bool keepCoords) const { if(getMeshDimension()!=-1) { - MEDCouplingUMesh *ret=buildPartOfMySelfKeepCoords(start,end); + MEDCouplingUMesh *ret=buildPartOfMySelfKeepCoords(begin,end); if(!keepCoords) ret->zipCoords(); return ret; } else { - if(end-start!=1) + if(end-begin!=1) throw INTERP_KERNEL::Exception("-1D mesh has only one cell !"); - if(start[0]!=0) + if(begin[0]!=0) throw INTERP_KERNEL::Exception("-1D mesh has only one cell : 0 !"); incrRef(); return (MEDCouplingUMesh *)this; } } +DataArrayInt *MEDCouplingUMesh::getCellIdsFullyIncludedInNodeIds(const int *partBg, const int *partEnd) const +{ + std::vector cellIdsKept; + fillCellIdsToKeepFromNodeIds(partBg,partEnd,true,cellIdsKept); + DataArrayInt *ret=DataArrayInt::New(); + ret->alloc(cellIdsKept.size(),1); + std::copy(cellIdsKept.begin(),cellIdsKept.end(),ret->getPointer()); + return ret; +} + /*! - * Keeps from 'this' only cells which constituing point id are in the ids specified by ['start','end'). - * The return newly allocated mesh will share the same coordinates as 'this'. + * Keeps from 'this' only cells which constituing point id are in the ids specified by ['begin','end'). + * The resulting cell ids are stored at the end of the 'cellIdsKept' parameter. * Parameter 'fullyIn' specifies if a cell that has part of its nodes in ids array is kept or not. - * If 'fullyIn' is true only cells whose ids are \b fully contained in ['start','end') tab will be kept. + * If 'fullyIn' is true only cells whose ids are \b fully contained in ['begin','end') tab will be kept. + * + * @param begin input start of array of node ids. + * @param end input end of array of node ids. + * @param fullyIn input that specifies if all node ids must be in ['begin','end') array to consider cell to be in. + * @param cellIdsKept in/out array where all candidate cell ids are put at the end. */ -MEDCouplingPointSet *MEDCouplingUMesh::buildPartOfMySelfNode(const int *start, const int *end, bool fullyIn) const +void MEDCouplingUMesh::fillCellIdsToKeepFromNodeIds(const int *begin, const int *end, bool fullyIn, std::vector& cellIdsKept) const { - std::set fastFinder(start,end); + std::set fastFinder(begin,end); + int nbOfCells=getNumberOfCells(); const int *conn=getNodalConnectivity()->getConstPointer(); const int *connIndex=getNodalConnectivityIndex()->getConstPointer(); - int nbOfCells=getNumberOfCells(); - std::vector cellIdsKept; for(int i=0;i connOfCell(conn+connIndex[i]+1,conn+connIndex[i+1]); @@ -869,22 +952,34 @@ MEDCouplingPointSet *MEDCouplingUMesh::buildPartOfMySelfNode(const int *start, c if(((int)locMerge.size()==refLgth && fullyIn) || (locMerge.size()!=0 && !fullyIn)) cellIdsKept.push_back(i); } +} + +/*! + * Keeps from 'this' only cells which constituing point id are in the ids specified by ['begin','end'). + * The return newly allocated mesh will share the same coordinates as 'this'. + * Parameter 'fullyIn' specifies if a cell that has part of its nodes in ids array is kept or not. + * If 'fullyIn' is true only cells whose ids are \b fully contained in ['begin','end') tab will be kept. + */ +MEDCouplingPointSet *MEDCouplingUMesh::buildPartOfMySelfNode(const int *begin, const int *end, bool fullyIn) const +{ + std::vector cellIdsKept; + fillCellIdsToKeepFromNodeIds(begin,end,fullyIn,cellIdsKept); return buildPartOfMySelf(&cellIdsKept[0],&cellIdsKept[0]+cellIdsKept.size(),true); } /*! - * Contrary to MEDCouplingUMesh::buildPartOfMySelfNode method this method a mesh with a meshDimension equal to + * Contrary to MEDCouplingUMesh::buildPartOfMySelfNode method this method builds a mesh with a meshDimension equal to * this->getMeshDimension()-1. The return newly allocated mesh will share the same coordinates as 'this'. * Parameter 'fullyIn' specifies if a face that has part of its nodes in ids array is kept or not. - * If 'fullyIn' is true only faces whose ids are \b fully contained in ['start','end') tab will be kept. + * If 'fullyIn' is true only faces whose ids are \b fully contained in ['begin','end') tab will be kept. */ -MEDCouplingPointSet *MEDCouplingUMesh::buildFacePartOfMySelfNode(const int *start, const int *end, bool fullyIn) const +MEDCouplingPointSet *MEDCouplingUMesh::buildFacePartOfMySelfNode(const int *begin, const int *end, bool fullyIn) const { DataArrayInt *desc,*descIndx,*revDesc,*revDescIndx; desc=DataArrayInt::New(); descIndx=DataArrayInt::New(); revDesc=DataArrayInt::New(); revDescIndx=DataArrayInt::New(); MEDCouplingUMesh *subMesh=buildDescendingConnectivity(desc,descIndx,revDesc,revDescIndx); desc->decrRef(); descIndx->decrRef(); revDesc->decrRef(); revDescIndx->decrRef(); - MEDCouplingUMesh *ret=(MEDCouplingUMesh *)subMesh->buildPartOfMySelfNode(start,end,fullyIn); + MEDCouplingUMesh *ret=(MEDCouplingUMesh *)subMesh->buildPartOfMySelfNode(begin,end,fullyIn); subMesh->decrRef(); return ret; } @@ -1439,10 +1534,10 @@ void MEDCouplingUMesh::unserialization(const std::vector& tinyInfo, const D /*! * This is the low algorithm of buildPartOfMySelf. - * Keeps from 'this' only cells which constituing point id are in the ids specified by ['start','end'). + * Keeps from 'this' only cells which constituing point id are in the ids specified by ['begin','end'). * The return newly allocated mesh will share the same coordinates as 'this'. */ -MEDCouplingUMesh *MEDCouplingUMesh::buildPartOfMySelfKeepCoords(const int *start, const int *end) const +MEDCouplingUMesh *MEDCouplingUMesh::buildPartOfMySelfKeepCoords(const int *begin, const int *end) const { checkFullyDefined(); MEDCouplingUMesh *ret=MEDCouplingUMesh::New(); @@ -1459,18 +1554,18 @@ MEDCouplingUMesh *MEDCouplingUMesh::buildPartOfMySelfKeepCoords(const int *start ret->setName(getName()); ret->_mesh_dim=_mesh_dim; ret->setCoords(_coords); - int nbOfElemsRet=end-start; + int nbOfElemsRet=end-begin; int *connIndexRet=new int[nbOfElemsRet+1]; connIndexRet[0]=0; const int *conn=_nodal_connec->getConstPointer(); const int *connIndex=_nodal_connec_index->getConstPointer(); int newNbring=0; - for(const int *work=start;work!=end;work++,newNbring++) + for(const int *work=begin;work!=end;work++,newNbring++) connIndexRet[newNbring+1]=connIndexRet[newNbring]+connIndex[*work+1]-connIndex[*work]; int *connRet=new int[connIndexRet[nbOfElemsRet]]; int *connRetWork=connRet; std::set types; - for(const int *work=start;work!=end;work++) + for(const int *work=begin;work!=end;work++) { types.insert((INTERP_KERNEL::NormalizedCellType)conn[connIndex[*work]]); connRetWork=std::copy(conn+connIndex[*work],conn+connIndex[*work+1],connRetWork); @@ -1607,15 +1702,15 @@ MEDCouplingFieldDouble *MEDCouplingUMesh::buildOrthogonalField() const } /*! - * This methods returns a vector newly created field on cells that represents the director vector of each 1D cell of this. + * This methods returns a vector newly created field on cells that represents the direction vector of each 1D cell of this. * This method is only callable on mesh with meshdim == 1 containing only SEG2. */ -MEDCouplingFieldDouble *MEDCouplingUMesh::buildLinearField() const +MEDCouplingFieldDouble *MEDCouplingUMesh::buildDirectionVectorField() const { if(getMeshDimension()!=1) - throw INTERP_KERNEL::Exception("Expected a umesh with meshDim == 1 for buildLinearField !"); + throw INTERP_KERNEL::Exception("Expected a umesh with meshDim == 1 for buildDirectionVectorField !"); if(_types.size()!=1 || *(_types.begin())!=INTERP_KERNEL::NORM_SEG2) - throw INTERP_KERNEL::Exception("Expected a umesh with only NORM_SEG2 type of elements for buildLinearField !"); + throw INTERP_KERNEL::Exception("Expected a umesh with only NORM_SEG2 type of elements for buildDirectionVectorField !"); MEDCouplingFieldDouble *ret=MEDCouplingFieldDouble::New(ON_CELLS,NO_TIME); DataArrayDouble *array=DataArrayDouble::New(); int nbOfCells=getNumberOfCells(); @@ -1653,7 +1748,7 @@ void MEDCouplingUMesh::project1D(const double *pt, const double *v, double eps, throw INTERP_KERNEL::Exception("Expected a umesh with only NORM_SEG2 type of elements for project1D !"); if(getSpaceDimension()!=3) throw INTERP_KERNEL::Exception("Expected a umesh with spaceDim==3 for project1D !"); - MEDCouplingFieldDouble *f=buildLinearField(); + MEDCouplingFieldDouble *f=buildDirectionVectorField(); const double *fPtr=f->getArray()->getConstPointer(); double tmp[3]; for(int i=0;i& cells) const { @@ -2174,10 +2271,10 @@ void MEDCouplingUMesh::orientCorrectlyPolyhedrons() throw(INTERP_KERNEL::Excepti * @param vec output of size at least 3 used to store the normal vector (with norm equal to Area ) of searched plane. * @param pos output of size at least 3 used to store a point owned of searched plane. */ -void MEDCouplingUMesh::getFastMiddlePlaneOfThis(double *vec, double *pos) const throw(INTERP_KERNEL::Exception) +void MEDCouplingUMesh::getFastAveragePlaneOfThis(double *vec, double *pos) const throw(INTERP_KERNEL::Exception) { if(getMeshDimension()!=2 || getSpaceDimension()!=3) - throw INTERP_KERNEL::Exception("Invalid mesh to apply getFastMiddlePlaneOfThis on it : must be meshDim==2 and spaceDim==3 !"); + throw INTERP_KERNEL::Exception("Invalid mesh to apply getFastAveragePlaneOfThis on it : must be meshDim==2 and spaceDim==3 !"); const int *conn=_nodal_connec->getConstPointer(); const int *connI=_nodal_connec_index->getConstPointer(); const double *coordsPtr=_coords->getConstPointer(); @@ -2185,6 +2282,222 @@ void MEDCouplingUMesh::getFastMiddlePlaneOfThis(double *vec, double *pos) const std::copy(coordsPtr+3*conn[1],coordsPtr+3*conn[1]+3,pos); } +/*! + * The returned newly created field has to be managed by the caller. + * This method returns a field on cell with no time lying on 'this'. The meshdimension and spacedimension of this are expected to be both in [2,3]. If not an exception will be thrown. + * This method for the moment only deals with NORM_TRI3, NORM_QUAD4 and NORM_TETRA4 geometric types. + * If a cell has an another type an exception will be thrown. + */ +MEDCouplingFieldDouble *MEDCouplingUMesh::getEdgeRatioField() const throw(INTERP_KERNEL::Exception) +{ + checkCoherency(); + int spaceDim=getSpaceDimension(); + int meshDim=getMeshDimension(); + if(spaceDim!=2 && spaceDim!=3) + throw INTERP_KERNEL::Exception("MEDCouplingUMesh::getEdgeRatioField : SpaceDimension must be equal to 2 or 3 !"); + if(meshDim!=2 && meshDim!=3) + throw INTERP_KERNEL::Exception("MEDCouplingUMesh::getEdgeRatioField : MeshDimension must be equal to 2 or 3 !"); + MEDCouplingAutoRefCountObjectPtr ret=MEDCouplingFieldDouble::New(ON_CELLS,NO_TIME); + ret->setMesh(this); + int nbOfCells=getNumberOfCells(); + DataArrayDouble *arr=DataArrayDouble::New(); + arr->alloc(nbOfCells,1); + double *pt=arr->getPointer(); + ret->setArray(arr);//In case of throw to avoid mem leaks arr will be used after decrRef. + arr->decrRef(); + const int *conn=_nodal_connec->getConstPointer(); + const int *connI=_nodal_connec_index->getConstPointer(); + const double *coo=_coords->getConstPointer(); + double tmp[12]; + for(int i=0;isetName("EdgeRatio"); + ret->incrRef(); + return ret; +} + +/*! + * The returned newly created field has to be managed by the caller. + * This method returns a field on cell with no time lying on 'this'. The meshdimension and spacedimension of this are expected to be both in [2,3]. If not an exception will be thrown. + * This method for the moment only deals with NORM_TRI3, NORM_QUAD4 and NORM_TETRA4 geometric types. + * If a cell has an another type an exception will be thrown. + */ +MEDCouplingFieldDouble *MEDCouplingUMesh::getAspectRatioField() const throw(INTERP_KERNEL::Exception) +{ + checkCoherency(); + int spaceDim=getSpaceDimension(); + int meshDim=getMeshDimension(); + if(spaceDim!=2 && spaceDim!=3) + throw INTERP_KERNEL::Exception("MEDCouplingUMesh::getAspectRatioField : SpaceDimension must be equal to 2 or 3 !"); + if(meshDim!=2 && meshDim!=3) + throw INTERP_KERNEL::Exception("MEDCouplingUMesh::getAspectRatioField : MeshDimension must be equal to 2 or 3 !"); + MEDCouplingAutoRefCountObjectPtr ret=MEDCouplingFieldDouble::New(ON_CELLS,NO_TIME); + ret->setMesh(this); + int nbOfCells=getNumberOfCells(); + DataArrayDouble *arr=DataArrayDouble::New(); + arr->alloc(nbOfCells,1); + double *pt=arr->getPointer(); + ret->setArray(arr);//In case of throw to avoid mem leaks arr will be used after decrRef. + arr->decrRef(); + const int *conn=_nodal_connec->getConstPointer(); + const int *connI=_nodal_connec_index->getConstPointer(); + const double *coo=_coords->getConstPointer(); + double tmp[12]; + for(int i=0;isetName("AspectRatio"); + ret->incrRef(); + return ret; +} + +/*! + * The returned newly created field has to be managed by the caller. + * This method returns a field on cell with no time lying on 'this'. The meshdimension must be equal to 2 and the spacedimension must be equal to 3. If not an exception will be thrown. + * This method for the moment only deals with NORM_QUAD4 geometric type. + * If a cell has an another type an exception will be thrown. + */ +MEDCouplingFieldDouble *MEDCouplingUMesh::getWarpField() const throw(INTERP_KERNEL::Exception) +{ + checkCoherency(); + int spaceDim=getSpaceDimension(); + int meshDim=getMeshDimension(); + if(spaceDim!=3) + throw INTERP_KERNEL::Exception("MEDCouplingUMesh::getWarpField : SpaceDimension must be equal to 3 !"); + if(meshDim!=2) + throw INTERP_KERNEL::Exception("MEDCouplingUMesh::getWarpField : MeshDimension must be equal to 2 !"); + MEDCouplingAutoRefCountObjectPtr ret=MEDCouplingFieldDouble::New(ON_CELLS,NO_TIME); + ret->setMesh(this); + int nbOfCells=getNumberOfCells(); + DataArrayDouble *arr=DataArrayDouble::New(); + arr->alloc(nbOfCells,1); + double *pt=arr->getPointer(); + ret->setArray(arr);//In case of throw to avoid mem leaks arr will be used after decrRef. + arr->decrRef(); + const int *conn=_nodal_connec->getConstPointer(); + const int *connI=_nodal_connec_index->getConstPointer(); + const double *coo=_coords->getConstPointer(); + double tmp[12]; + for(int i=0;isetName("Warp"); + ret->incrRef(); + return ret; +} + +/*! + * The returned newly created field has to be managed by the caller. + * This method returns a field on cell with no time lying on 'this'. The meshdimension must be equal to 2 and the spacedimension must be equal to 3. If not an exception will be thrown. + * This method for the moment only deals with NORM_QUAD4 geometric type. + * If a cell has an another type an exception will be thrown. + */ +MEDCouplingFieldDouble *MEDCouplingUMesh::getSkewField() const throw(INTERP_KERNEL::Exception) +{ + checkCoherency(); + int spaceDim=getSpaceDimension(); + int meshDim=getMeshDimension(); + if(spaceDim!=3) + throw INTERP_KERNEL::Exception("MEDCouplingUMesh::getSkewField : SpaceDimension must be equal to 3 !"); + if(meshDim!=2) + throw INTERP_KERNEL::Exception("MEDCouplingUMesh::getSkewField : MeshDimension must be equal to 2 !"); + MEDCouplingAutoRefCountObjectPtr ret=MEDCouplingFieldDouble::New(ON_CELLS,NO_TIME); + ret->setMesh(this); + int nbOfCells=getNumberOfCells(); + DataArrayDouble *arr=DataArrayDouble::New(); + arr->alloc(nbOfCells,1); + double *pt=arr->getPointer(); + ret->setArray(arr);//In case of throw to avoid mem leaks arr will be used after decrRef. + arr->decrRef(); + const int *conn=_nodal_connec->getConstPointer(); + const int *connI=_nodal_connec_index->getConstPointer(); + const double *coo=_coords->getConstPointer(); + double tmp[12]; + for(int i=0;isetName("Skew"); + ret->incrRef(); + return ret; +} + /*! * This method aggregate the bbox of each cell and put it into bbox parameter. * @param bbox out parameter of size 2*spacedim*nbOfcells. @@ -2283,7 +2596,7 @@ bool MEDCouplingUMesh::checkConsecutiveCellTypesAndOrder(const INTERP_KERNEL::No * The mesh after this call will pass the test of MEDCouplingUMesh::checkConsecutiveCellTypesAndOrder with the same inputs. * The returned array minimizes the permutations that is to say the order of cells inside same geometric type remains the same. */ -DataArrayInt *MEDCouplingUMesh::getRenumArrForConsctvCellTypesSpe(const INTERP_KERNEL::NormalizedCellType *orderBg, const INTERP_KERNEL::NormalizedCellType *orderEnd) const +DataArrayInt *MEDCouplingUMesh::getRenumArrForConsecutiveCellTypesSpec(const INTERP_KERNEL::NormalizedCellType *orderBg, const INTERP_KERNEL::NormalizedCellType *orderEnd) const { checkFullyDefined(); int nbOfCells=getNumberOfCells(); @@ -2371,13 +2684,13 @@ std::vector MEDCouplingUMesh::splitByType() const for(const int *i=connI;i!=connI+nbOfCells;) { INTERP_KERNEL::NormalizedCellType curType=(INTERP_KERNEL::NormalizedCellType)conn[*i]; - int startCellId=std::distance(connI,i); + int beginCellId=std::distance(connI,i); i=std::find_if(i+1,connI+nbOfCells,ParaMEDMEMImpl::ConnReader(conn,(int)curType)); int endCellId=std::distance(connI,i); - int sz=endCellId-startCellId; + int sz=endCellId-beginCellId; int *cells=new int[sz]; for(int j=0;j& conn) const; + MEDCOUPLING_EXPORT DataArrayInt *getCellIdsFullyIncludedInNodeIds(const int *partBg, const int *partEnd) const; MEDCOUPLING_EXPORT void getCoordinatesOfNode(int nodeId, std::vector& coo) const; MEDCOUPLING_EXPORT std::string simpleRepr() const; MEDCOUPLING_EXPORT std::string advancedRepr() const; @@ -81,9 +85,9 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT MEDCouplingUMesh *buildDescendingConnectivity(DataArrayInt *desc, DataArrayInt *descIndx, DataArrayInt *revDesc, DataArrayInt *revDescIndx) const; MEDCOUPLING_EXPORT DataArrayInt *mergeNodes(double precision, bool& areNodesMerged, int& newNbOfNodes); MEDCOUPLING_EXPORT void tryToShareSameCoordsPermute(const MEDCouplingPointSet& other, double epsilon) throw(INTERP_KERNEL::Exception); - MEDCOUPLING_EXPORT MEDCouplingPointSet *buildPartOfMySelf(const int *start, const int *end, bool keepCoords) const; - MEDCOUPLING_EXPORT MEDCouplingPointSet *buildPartOfMySelfNode(const int *start, const int *end, bool fullyIn) const; - MEDCOUPLING_EXPORT MEDCouplingPointSet *buildFacePartOfMySelfNode(const int *start, const int *end, bool fullyIn) const; + MEDCOUPLING_EXPORT MEDCouplingPointSet *buildPartOfMySelf(const int *begin, const int *end, bool keepCoords) const; + MEDCOUPLING_EXPORT MEDCouplingPointSet *buildPartOfMySelfNode(const int *begin, const int *end, bool fullyIn) const; + MEDCOUPLING_EXPORT MEDCouplingPointSet *buildFacePartOfMySelfNode(const int *begin, const int *end, bool fullyIn) const; MEDCOUPLING_EXPORT void findBoundaryNodes(std::vector& nodes) const; MEDCOUPLING_EXPORT MEDCouplingPointSet *buildBoundaryMesh(bool keepCoords) const; MEDCOUPLING_EXPORT void renumberNodes(const int *newNodeNumbers, int newNbOfNodes); @@ -93,7 +97,7 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT MEDCouplingFieldDouble *getMeasureField(bool isAbs) const; MEDCOUPLING_EXPORT MEDCouplingFieldDouble *getMeasureFieldOnNode(bool isAbs) const; MEDCOUPLING_EXPORT MEDCouplingFieldDouble *buildOrthogonalField() const; - MEDCOUPLING_EXPORT MEDCouplingFieldDouble *buildLinearField() const; + MEDCOUPLING_EXPORT MEDCouplingFieldDouble *buildDirectionVectorField() const; MEDCOUPLING_EXPORT void project1D(const double *pt, const double *v, double eps, double *res) const; MEDCOUPLING_EXPORT int getCellContainingPoint(const double *pos, double eps) const; MEDCOUPLING_EXPORT void getCellsContainingPoint(const double *pos, double eps, std::vector& elts) const; @@ -108,11 +112,16 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT void orientCorrectly2DCells(const double *vec, bool polyOnly) throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT void arePolyhedronsNotCorrectlyOriented(std::vector& cells) const throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT void orientCorrectlyPolyhedrons() throw(INTERP_KERNEL::Exception); - MEDCOUPLING_EXPORT void getFastMiddlePlaneOfThis(double *vec, double *pos) const throw(INTERP_KERNEL::Exception); + MEDCOUPLING_EXPORT void getFastAveragePlaneOfThis(double *vec, double *pos) const throw(INTERP_KERNEL::Exception); + //Mesh quality + MEDCOUPLING_EXPORT MEDCouplingFieldDouble *getEdgeRatioField() const throw(INTERP_KERNEL::Exception); + MEDCOUPLING_EXPORT MEDCouplingFieldDouble *getAspectRatioField() const throw(INTERP_KERNEL::Exception); + MEDCOUPLING_EXPORT MEDCouplingFieldDouble *getWarpField() const throw(INTERP_KERNEL::Exception); + MEDCOUPLING_EXPORT MEDCouplingFieldDouble *getSkewField() const throw(INTERP_KERNEL::Exception); //utilities for MED File RW MEDCOUPLING_EXPORT bool checkConsecutiveCellTypes() const; MEDCOUPLING_EXPORT bool checkConsecutiveCellTypesAndOrder(const INTERP_KERNEL::NormalizedCellType *orderBg, const INTERP_KERNEL::NormalizedCellType *orderEnd) const; - MEDCOUPLING_EXPORT DataArrayInt *getRenumArrForConsctvCellTypesSpe(const INTERP_KERNEL::NormalizedCellType *orderBg, const INTERP_KERNEL::NormalizedCellType *orderEnd) const; + MEDCOUPLING_EXPORT DataArrayInt *getRenumArrForConsecutiveCellTypesSpec(const INTERP_KERNEL::NormalizedCellType *orderBg, const INTERP_KERNEL::NormalizedCellType *orderEnd) const; MEDCOUPLING_EXPORT DataArrayInt *rearrange2ConsecutiveCellTypes(); MEDCOUPLING_EXPORT std::vector splitByType() const; MEDCOUPLING_EXPORT DataArrayInt *convertCellArrayPerGeoType(const DataArrayInt *da) const throw(INTERP_KERNEL::Exception); @@ -134,15 +143,17 @@ namespace ParaMEDMEM void reprConnectivityOfThisLL(std::ostringstream& stream) const; //tools void renumberNodesInConn(const int *newNodeNumbers); + void fillCellIdsToKeepFromNodeIds(const int *begin, const int *end, bool fullyIn, std::vector& cellIdsKept) const; MEDCouplingUMesh *buildExtrudedMeshFromThisLowLev(int nbOfNodesOf1Lev, bool isQuad) const; DataArrayDouble *fillExtCoordsUsingTranslation(const MEDCouplingUMesh *mesh1D, bool isQuad) const; template void findCommonCellsBase(int compType, std::vector& res, std::vector& resI) const; bool areCellsEqualInPool(const std::vector& candidates, int compType, std::vector& result) const; - MEDCouplingUMesh *buildPartOfMySelfKeepCoords(const int *start, const int *end) const; + MEDCouplingUMesh *buildPartOfMySelfKeepCoords(const int *begin, const int *end) const; template void getCellsContainingPointsAlg(const double *coords, const double *pos, int nbOfPoints, double eps, std::vector& elts, std::vector& eltsIndex) const; + static void fillInCompact3DMode(int spaceDim, int nbOfNodesInCell, const int *conn, const double *coo, double *zipFrmt) throw(INTERP_KERNEL::Exception); static void appendExtrudedCell(const int *connBg, const int *connEnd, int nbOfNodesPerLev, bool isQuad, std::vector& ret); private: //! this iterator stores current position in _nodal_connec array. diff --git a/src/MEDCoupling/MEDCouplingUMeshDesc.cxx b/src/MEDCoupling/MEDCouplingUMeshDesc.cxx index 5fb8072db..f45cd5eba 100644 --- a/src/MEDCoupling/MEDCouplingUMeshDesc.cxx +++ b/src/MEDCoupling/MEDCouplingUMeshDesc.cxx @@ -82,6 +82,12 @@ void MEDCouplingUMeshDesc::checkDeepEquivalWith(const MEDCouplingMesh *other, in throw INTERP_KERNEL::Exception("MEDCouplingUMeshDesc::checkDeepEquivalWith : not implemented yet !"); } +void MEDCouplingUMeshDesc::checkDeepEquivalOnSameNodesWith(const MEDCouplingMesh *other, int cellCompPol, double prec, + DataArrayInt *&cellCor) const throw(INTERP_KERNEL::Exception) +{ + throw INTERP_KERNEL::Exception("MEDCouplingUMeshDesc::checkDeepEquivalOnSameNodesWith : not implemented yet !"); +} + void MEDCouplingUMeshDesc::setMeshDimension(unsigned meshDim) { _mesh_dim=meshDim; diff --git a/src/MEDCoupling/MEDCouplingUMeshDesc.hxx b/src/MEDCoupling/MEDCouplingUMeshDesc.hxx index 7c1648e47..7c965a31c 100644 --- a/src/MEDCoupling/MEDCouplingUMeshDesc.hxx +++ b/src/MEDCoupling/MEDCouplingUMeshDesc.hxx @@ -37,6 +37,8 @@ namespace ParaMEDMEM MEDCOUPLING_EXPORT void checkCoherency() const throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT void checkDeepEquivalWith(const MEDCouplingMesh *other, int cellCompPol, double prec, DataArrayInt *&cellCor, DataArrayInt *&nodeCor) const throw(INTERP_KERNEL::Exception); + MEDCOUPLING_EXPORT void checkDeepEquivalOnSameNodesWith(const MEDCouplingMesh *other, int cellCompPol, double prec, + DataArrayInt *&cellCor) const throw(INTERP_KERNEL::Exception); MEDCOUPLING_EXPORT void setMeshDimension(unsigned meshDim); MEDCOUPLING_EXPORT int getNumberOfCells() const; MEDCOUPLING_EXPORT int getNumberOfFaces() const; diff --git a/src/MEDCoupling/Test/MEDCouplingBasicsTest.hxx b/src/MEDCoupling/Test/MEDCouplingBasicsTest.hxx index 71651417b..0e8cf3e7f 100644 --- a/src/MEDCoupling/Test/MEDCouplingBasicsTest.hxx +++ b/src/MEDCoupling/Test/MEDCouplingBasicsTest.hxx @@ -122,6 +122,25 @@ namespace ParaMEDMEM CPPUNIT_TEST( testMaxPerTuple1 ); CPPUNIT_TEST( testChangeNbOfComponents ); CPPUNIT_TEST( testSortPerTuple1 ); + CPPUNIT_TEST( testIsEqualWithoutConsideringStr1 ); + CPPUNIT_TEST( testGetNodeIdsOfCell1 ); + CPPUNIT_TEST( testGetEdgeRatioField1 ); + CPPUNIT_TEST( testFillFromAnalytic3 ); + CPPUNIT_TEST( testFieldDoubleOpEqual1 ); + CPPUNIT_TEST( testAreaBary3D2 ); + CPPUNIT_TEST( testGetMeasureFieldCMesh1 ); + CPPUNIT_TEST( testFieldDoubleZipCoords1 ); + CPPUNIT_TEST( testFieldDoubleZipConnectivity1 ); + CPPUNIT_TEST( testDaDoubleRenumber1 ); + CPPUNIT_TEST( testDaDoubleRenumberAndReduce1 ); + CPPUNIT_TEST( testDaDoubleRenumberInPlace1 ); + CPPUNIT_TEST( testDaDoubleSelectByTupleId1 ); + CPPUNIT_TEST( testDaDoubleRenumberR1 ); + CPPUNIT_TEST( testDaDoubleRenumberInPlaceR1 ); + CPPUNIT_TEST( testDaDoubleGetMinMaxValues1 ); + CPPUNIT_TEST( testFieldDoubleGetMinMaxValues2 ); + CPPUNIT_TEST( testBuildUnstructuredCMesh1 ); + CPPUNIT_TEST( testDataArrayIntInvertO2NNO21 ); //MEDCouplingBasicsTestInterp.cxx CPPUNIT_TEST( test2DInterpP0P0_1 ); CPPUNIT_TEST( test2DInterpP0P0PL_1 ); @@ -272,6 +291,25 @@ namespace ParaMEDMEM void testMaxPerTuple1(); void testChangeNbOfComponents(); void testSortPerTuple1(); + void testIsEqualWithoutConsideringStr1(); + void testGetNodeIdsOfCell1(); + void testGetEdgeRatioField1(); + void testFillFromAnalytic3(); + void testFieldDoubleOpEqual1(); + void testAreaBary3D2(); + void testGetMeasureFieldCMesh1(); + void testFieldDoubleZipCoords1(); + void testFieldDoubleZipConnectivity1(); + void testDaDoubleRenumber1(); + void testDaDoubleRenumberAndReduce1(); + void testDaDoubleRenumberInPlace1(); + void testDaDoubleSelectByTupleId1(); + void testDaDoubleRenumberR1(); + void testDaDoubleRenumberInPlaceR1(); + void testDaDoubleGetMinMaxValues1(); + void testFieldDoubleGetMinMaxValues2(); + void testBuildUnstructuredCMesh1(); + void testDataArrayIntInvertO2NNO21(); //MEDCouplingBasicsTestInterp.cxx void test2DInterpP0P0_1(); void test2DInterpP0P0PL_1(); diff --git a/src/MEDCoupling/Test/MEDCouplingBasicsTest1.cxx b/src/MEDCoupling/Test/MEDCouplingBasicsTest1.cxx index fb96af12d..ffa8b6a75 100644 --- a/src/MEDCoupling/Test/MEDCouplingBasicsTest1.cxx +++ b/src/MEDCoupling/Test/MEDCouplingBasicsTest1.cxx @@ -691,8 +691,8 @@ void MEDCouplingBasicsTest::testZipCoords() MEDCouplingUMesh *subMesh=dynamic_cast(subMeshPtSet); CPPUNIT_ASSERT(subMesh); DataArrayInt *traducer=subMesh->zipCoordsTraducer(); - const int expectedTraducer[7]={0,1,3,4,5,7,8}; - CPPUNIT_ASSERT(std::equal(expectedTraducer,expectedTraducer+7,traducer->getPointer())); + const int expectedTraducer[9]={0,1,-1,2,3,4,-1,5,6}; + CPPUNIT_ASSERT(std::equal(expectedTraducer,expectedTraducer+9,traducer->getPointer())); traducer->decrRef(); CPPUNIT_ASSERT_EQUAL(INTERP_KERNEL::NORM_QUAD4,*subMesh->getAllTypes().begin()); CPPUNIT_ASSERT_EQUAL(2,subMesh->getNumberOfCells()); @@ -1163,7 +1163,7 @@ void MEDCouplingBasicsTest::testFindCommonNodes() CPPUNIT_ASSERT_EQUAL(1,commI->getNumberOfTuples()); CPPUNIT_ASSERT_EQUAL(0,comm->getNumberOfTuples()); int newNbOfNodes; - DataArrayInt *o2n=targetMesh->buildNewNumberingFromCommNodesFrmt(comm,commI,newNbOfNodes); + DataArrayInt *o2n=targetMesh->buildNewNumberingFromCommonNodesFormat(comm,commI,newNbOfNodes); CPPUNIT_ASSERT_EQUAL(27,newNbOfNodes); CPPUNIT_ASSERT_EQUAL(27,o2n->getNumberOfTuples()); const int o2nExp1[27]= @@ -1186,7 +1186,7 @@ void MEDCouplingBasicsTest::testFindCommonNodes() const int commIExpected[3]={0,4,6}; CPPUNIT_ASSERT(std::equal(commExpected,commExpected+6,comm->getConstPointer())); CPPUNIT_ASSERT(std::equal(commIExpected,commIExpected+3,commI->getConstPointer())); - o2n=targetMesh->buildNewNumberingFromCommNodesFrmt(comm,commI,newNbOfNodes); + o2n=targetMesh->buildNewNumberingFromCommonNodesFormat(comm,commI,newNbOfNodes); CPPUNIT_ASSERT_EQUAL(31,o2n->getNumberOfTuples()); CPPUNIT_ASSERT_EQUAL(27,newNbOfNodes); const int o2nExp2[31]= @@ -1921,13 +1921,13 @@ void MEDCouplingBasicsTest::testCheckConsecutiveCellTypes() CPPUNIT_ASSERT(!targetMesh->checkConsecutiveCellTypes()); CPPUNIT_ASSERT(!targetMesh->checkConsecutiveCellTypesAndOrder(order1,order1+2)); CPPUNIT_ASSERT(!targetMesh->checkConsecutiveCellTypesAndOrder(order2,order2+2)); - DataArrayInt *da=targetMesh->getRenumArrForConsctvCellTypesSpe(order1,order1+2); + DataArrayInt *da=targetMesh->getRenumArrForConsecutiveCellTypesSpec(order1,order1+2); CPPUNIT_ASSERT_EQUAL(5,da->getNumberOfTuples()); CPPUNIT_ASSERT_EQUAL(1,da->getNumberOfComponents()); const int expected1[5]={2,0,1,3,4}; CPPUNIT_ASSERT(std::equal(expected1,expected1+5,da->getConstPointer())); da->decrRef(); - da=targetMesh->getRenumArrForConsctvCellTypesSpe(order2,order2+2); + da=targetMesh->getRenumArrForConsecutiveCellTypesSpec(order2,order2+2); CPPUNIT_ASSERT_EQUAL(5,da->getNumberOfTuples()); CPPUNIT_ASSERT_EQUAL(1,da->getNumberOfComponents()); const int expected2[5]={0,3,4,1,2}; diff --git a/src/MEDCoupling/Test/MEDCouplingBasicsTest2.cxx b/src/MEDCoupling/Test/MEDCouplingBasicsTest2.cxx index af5ec9aa4..9636efbaa 100644 --- a/src/MEDCoupling/Test/MEDCouplingBasicsTest2.cxx +++ b/src/MEDCoupling/Test/MEDCouplingBasicsTest2.cxx @@ -386,11 +386,11 @@ void MEDCouplingBasicsTest::testNormL12Integ1D() CPPUNIT_ASSERT_DOUBLES_EQUAL(expected7[0],f1->normL2(0),1e-9); CPPUNIT_ASSERT_DOUBLES_EQUAL(expected7[1],f1->normL2(1),1e-9); CPPUNIT_ASSERT_DOUBLES_EQUAL(expected7[2],f1->normL2(2),1e-9); - //buildWeightingField - MEDCouplingFieldDouble *f4=f1->buildWeightingField(false); + //buildMeasureField + MEDCouplingFieldDouble *f4=f1->buildMeasureField(false); CPPUNIT_ASSERT_DOUBLES_EQUAL(-0.2,f4->accumulate(0),1e-12); f4->decrRef(); - f4=f1->buildWeightingField(true); + f4=f1->buildMeasureField(true); CPPUNIT_ASSERT_DOUBLES_EQUAL(1.62,f4->accumulate(0),1e-12); f4->decrRef(); // @@ -1885,3 +1885,961 @@ void MEDCouplingBasicsTest::testSortPerTuple1() mesh1->decrRef(); f1->decrRef(); } + +void MEDCouplingBasicsTest::testIsEqualWithoutConsideringStr1() +{ + MEDCouplingUMesh *mesh1=build2DTargetMesh_1(); + MEDCouplingUMesh *mesh2=build2DTargetMesh_1(); + DataArrayInt *da1,*da2; + // + CPPUNIT_ASSERT(mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2->setName("rr"); + CPPUNIT_ASSERT(!mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh1->checkDeepEquivalWith(mesh2,2,1e-12,da1,da2); + CPPUNIT_ASSERT_THROW(mesh1->checkGeoEquivalWith(mesh2,0,1e-12,da1,da2),INTERP_KERNEL::Exception); + mesh2->setName(""); + CPPUNIT_ASSERT(mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2->getCoords()->setInfoOnComponent(0,"tty"); + CPPUNIT_ASSERT(!mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2->getCoords()->setInfoOnComponent(0,""); + CPPUNIT_ASSERT(mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2->getCoords()->setInfoOnComponent(1,"tty"); + CPPUNIT_ASSERT(!mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2->getCoords()->setInfoOnComponent(1,""); + CPPUNIT_ASSERT(mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + double tmp=mesh2->getCoords()->getIJ(0,3); + mesh2->getCoords()->setIJ(0,3,9999.); + CPPUNIT_ASSERT(!mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(!mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2->getCoords()->setIJ(0,3,tmp); + CPPUNIT_ASSERT(mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + int tmp2=mesh2->getNodalConnectivity()->getIJ(0,4); + mesh2->getNodalConnectivity()->setIJ(0,4,0); + CPPUNIT_ASSERT(!mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(!mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2->getNodalConnectivity()->setIJ(0,4,tmp2); + CPPUNIT_ASSERT(mesh1->isEqual(mesh2,1e-12)); + CPPUNIT_ASSERT(mesh1->isEqualWithoutConsideringStr(mesh2,1e-12)); + // + MEDCouplingFieldDouble *f1=mesh1->getMeasureField(true); + MEDCouplingFieldDouble *f2=mesh2->getMeasureField(true); + CPPUNIT_ASSERT(f1->isEqual(f2,1e-12,1e-12)); + CPPUNIT_ASSERT(f1->isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + f2->setName("ftest"); + CPPUNIT_ASSERT(!f1->isEqual(f2,1e-12,1e-12)); + CPPUNIT_ASSERT(f1->isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + f1->setName("ftest"); + CPPUNIT_ASSERT(f1->isEqual(f2,1e-12,1e-12)); + CPPUNIT_ASSERT(f1->isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + // + f2->getArray()->setInfoOnComponent(0,"eee"); + CPPUNIT_ASSERT(!f1->isEqual(f2,1e-12,1e-12)); + CPPUNIT_ASSERT(f1->isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + f2->getArray()->setInfoOnComponent(0,""); + CPPUNIT_ASSERT(f1->isEqual(f2,1e-12,1e-12)); + CPPUNIT_ASSERT(f1->isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + // + f2->getArray()->setIJ(1,0,0.123); + CPPUNIT_ASSERT(!f1->isEqual(f2,1e-12,1e-12)); + CPPUNIT_ASSERT(!f1->isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + f2->getArray()->setIJ(1,0,0.125); + CPPUNIT_ASSERT(f1->isEqual(f2,1e-12,1e-12)); + CPPUNIT_ASSERT(f1->isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + // + f1->decrRef(); + f2->decrRef(); + // + mesh1->decrRef(); + mesh2->decrRef(); +} + +void MEDCouplingBasicsTest::testGetNodeIdsOfCell1() +{ + MEDCouplingUMesh *mesh1=build2DTargetMesh_1(); + std::vector nodeIds; + mesh1->getNodeIdsOfCell(1,nodeIds); + CPPUNIT_ASSERT_EQUAL(3,(int)nodeIds.size()); + CPPUNIT_ASSERT_EQUAL(1,nodeIds[0]); + CPPUNIT_ASSERT_EQUAL(4,nodeIds[1]); + CPPUNIT_ASSERT_EQUAL(2,nodeIds[2]); + std::vector coords; + mesh1->getCoordinatesOfNode(4,coords); + CPPUNIT_ASSERT_EQUAL(2,(int)coords.size()); + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.2,coords[0],1e-13); + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.2,coords[1],1e-13); + mesh1->decrRef(); +} + +void MEDCouplingBasicsTest::testGetEdgeRatioField1() +{ + MEDCouplingUMesh *m1=build2DTargetMesh_1(); + MEDCouplingFieldDouble *f1=m1->getEdgeRatioField(); + CPPUNIT_ASSERT_EQUAL(m1->getNumberOfCells(),f1->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(5,f1->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,f1->getNumberOfComponents()); + const double expected1[5]={1.,1.4142135623730951, 1.4142135623730951,1.,1.}; + for(int i=0;i<5;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],f1->getIJ(i,0),1e-14); + f1->decrRef(); + m1->decrRef(); + // + m1=build3DSurfTargetMesh_1(); + f1=m1->getEdgeRatioField(); + CPPUNIT_ASSERT_EQUAL(m1->getNumberOfCells(),f1->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(5,f1->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,f1->getNumberOfComponents()); + const double expected2[5]={1.4142135623730951, 1.7320508075688772, 1.7320508075688772, 1.4142135623730951, 1.4142135623730951}; + for(int i=0;i<5;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected2[i],f1->getIJ(i,0),1e-14); + f1->decrRef(); + m1->decrRef(); +} + +void MEDCouplingBasicsTest::testFillFromAnalytic3() +{ + MEDCouplingUMesh *m=build2DTargetMesh_1(); + MEDCouplingFieldDouble *f1=MEDCouplingFieldDouble::New(ON_CELLS,ONE_TIME); + CPPUNIT_ASSERT_THROW(f1->fillFromAnalytic(1,"y+x"),INTERP_KERNEL::Exception); + f1->setMesh(m); + f1->setName("myField"); + f1->fillFromAnalytic(1,"y+x"); + f1->checkCoherency(); + CPPUNIT_ASSERT(std::string(f1->getName())=="myField"); + CPPUNIT_ASSERT(f1->getTypeOfField()==ON_CELLS); + CPPUNIT_ASSERT(f1->getTimeDiscretization()==ONE_TIME); + CPPUNIT_ASSERT_EQUAL(1,f1->getNumberOfComponents()); + CPPUNIT_ASSERT_EQUAL(5,f1->getNumberOfTuples()); + double values1[5]={-0.1,0.23333333333333336,0.56666666666666665,0.4,0.9}; + const double *tmp=f1->getArray()->getConstPointer(); + std::transform(tmp,tmp+5,values1,values1,std::minus()); + std::transform(values1,values1+5,values1,std::ptr_fun(fabs)); + double max=*std::max_element(values1,values1+5); + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.,max,1.e-12); + f1->decrRef(); + // + f1=MEDCouplingFieldDouble::New(ON_NODES,CONST_ON_TIME_INTERVAL); + f1->setMesh(m); + f1->setEndTime(1.2,3,4); + f1->fillFromAnalytic(1,"y+2*x"); + f1->checkCoherency(); + CPPUNIT_ASSERT(f1->getTypeOfField()==ON_NODES); + CPPUNIT_ASSERT(f1->getTimeDiscretization()==CONST_ON_TIME_INTERVAL); + CPPUNIT_ASSERT_EQUAL(1,f1->getNumberOfComponents()); + CPPUNIT_ASSERT_EQUAL(9,f1->getNumberOfTuples()); + double values2[9]={-0.9,0.1,1.1,-0.4,0.6,1.6,0.1,1.1,2.1}; + tmp=f1->getArray()->getConstPointer(); + std::transform(tmp,tmp+9,values2,values2,std::minus()); + std::transform(values2,values2+9,values2,std::ptr_fun(fabs)); + max=*std::max_element(values2,values2+9); + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.,max,1.e-12); + f1->decrRef(); + f1=MEDCouplingFieldDouble::New(ON_NODES,LINEAR_TIME); + f1->setMesh(m); + f1->setEndTime(1.2,3,4); + f1->fillFromAnalytic(1,"2.*x+y"); + f1->checkCoherency(); + CPPUNIT_ASSERT(f1->getTypeOfField()==ON_NODES); + CPPUNIT_ASSERT(f1->getTimeDiscretization()==LINEAR_TIME); + CPPUNIT_ASSERT_EQUAL(1,f1->getNumberOfComponents()); + CPPUNIT_ASSERT_EQUAL(9,f1->getNumberOfTuples()); + tmp=f1->getArray()->getConstPointer(); + double values2Bis[9]={-0.9,0.1,1.1,-0.4,0.6,1.6,0.1,1.1,2.1}; + double values2BisBis[9]; + std::transform(tmp,tmp+9,values2Bis,values2BisBis,std::minus()); + std::transform(values2,values2+9,values2BisBis,std::ptr_fun(fabs)); + max=*std::max_element(values2BisBis,values2BisBis+9); + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.,max,1.e-12); + tmp=f1->getEndArray()->getConstPointer(); + std::transform(tmp,tmp+9,values2Bis,values2BisBis,std::minus()); + std::transform(values2,values2+9,values2BisBis,std::ptr_fun(fabs)); + max=*std::max_element(values2BisBis,values2BisBis+9); + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.,max,1.e-12); + f1->decrRef(); + // + f1=MEDCouplingFieldDouble::New(ON_NODES,NO_TIME); + f1->setMesh(m); + f1->fillFromAnalytic(2,"(x+y)*IVec+2*(x+y)*JVec"); + f1->checkCoherency(); + CPPUNIT_ASSERT(f1->getTypeOfField()==ON_NODES); + CPPUNIT_ASSERT(f1->getTimeDiscretization()==NO_TIME); + CPPUNIT_ASSERT_EQUAL(2,f1->getNumberOfComponents()); + CPPUNIT_ASSERT_EQUAL(9,f1->getNumberOfTuples()); + double values3[18]={-0.6,-1.2,-0.1,-0.2,0.4,0.8,-0.1,-0.2,0.4,0.8,0.9,1.8,0.4,0.8,0.9,1.8,1.4,2.8}; + tmp=f1->getArray()->getConstPointer(); + std::transform(tmp,tmp+18,values3,values3,std::minus()); + std::transform(values3,values3+18,values3,std::ptr_fun(fabs)); + max=*std::max_element(values3,values3+18); + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.,max,1.e-12); + double values4[2]; + f1->accumulate(values4); + CPPUNIT_ASSERT_DOUBLES_EQUAL(3.6,values4[0],1.e-12); + CPPUNIT_ASSERT_DOUBLES_EQUAL(7.2,values4[1],1.e-12); + f1->integral(true,values4); + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.5,values4[0],1.e-12); + CPPUNIT_ASSERT_DOUBLES_EQUAL(1.,values4[1],1.e-12); + f1->decrRef(); + // + f1=MEDCouplingFieldDouble::New(ON_NODES,NO_TIME); + f1->setMesh(m); + CPPUNIT_ASSERT_THROW(f1->fillFromAnalytic(1,"1./(x-0.2)"),INTERP_KERNEL::Exception); + // + m->decrRef(); + f1->decrRef(); +} + +void MEDCouplingBasicsTest::testFieldDoubleOpEqual1() +{ + MEDCouplingUMesh *m=build2DTargetMesh_1(); + MEDCouplingFieldDouble *f1=MEDCouplingFieldDouble::New(ON_CELLS,ONE_TIME); + CPPUNIT_ASSERT_THROW((*f1)=0.07,INTERP_KERNEL::Exception); + f1->setMesh(m); + (*f1)=0.07; + f1->checkCoherency(); + CPPUNIT_ASSERT_EQUAL(1,f1->getNumberOfComponents()); + CPPUNIT_ASSERT_EQUAL(5,f1->getNumberOfTuples()); + for(int i=0;i<5;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.07,f1->getIJ(i,0),1e-16); + (*f1)=0.09; + f1->checkCoherency(); + CPPUNIT_ASSERT_EQUAL(1,f1->getNumberOfComponents()); + CPPUNIT_ASSERT_EQUAL(5,f1->getNumberOfTuples()); + for(int i=0;i<5;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.09,f1->getIJ(i,0),1e-16); + f1->decrRef(); + // + f1=MEDCouplingFieldDouble::New(ON_NODES,LINEAR_TIME); + f1->setEndTime(4.5,2,3); + f1->setMesh(m); + (*f1)=0.08; + f1->checkCoherency(); + CPPUNIT_ASSERT_EQUAL(1,f1->getNumberOfComponents()); + CPPUNIT_ASSERT_EQUAL(9,f1->getNumberOfTuples()); + for(int i=0;i<9;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.08,f1->getIJ(i,0),1e-16); + CPPUNIT_ASSERT_EQUAL(1,f1->getEndArray()->getNumberOfComponents()); + CPPUNIT_ASSERT_EQUAL(9,f1->getEndArray()->getNumberOfTuples()); + for(int i=0;i<9;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(0.08,f1->getEndArray()->getIJ(i,0),1e-16); + f1->decrRef(); + // + m->decrRef(); +} + +void MEDCouplingBasicsTest::testAreaBary3D2() +{ + const double coordsForHexa8[24]={ + -75.45749305371, 180.95495078401, 39.515472018008, + -9.755591679144, 23.394927935279, 5.108794294848, + 14.337630157832, 61.705351002702, 160.42422501908, + -27.273893776752, 167.567731083961, 192.830034145464, + // + 99.857193154796,264.499264735586,-8.287335493412, + 144.939882761126,156.38626563134,-31.896173894226, + 161.34096835726,182.4654895809,73.832387065572, + 132.680430393685,255.37973247196,96.15235602819 + }; + const double volHexa8=3258520.29637466; + const double baryHexa8[3]={43.925705821778, 155.31893955289, 65.874418109644}; + + const double coordsForPenta6[18]={ + -68.199829618726,178.938498373416,62.608505919588, + 8.461744647847,76.653979804423,165.00018874933, + -27.273893776752,167.567731083961,192.830034145464, + // + 106.586501038965,262.629609408327,13.124533008813, + 155.465082847275,197.414118382622,78.408350795821, + 132.680430393685,255.37973247196,96.15235602819 + }; + const double volPenta6=944849.868507338; + const double baryPenta6[3]={39.631002313543,182.692711783428,106.98540473964}; + + const double coordsForPyra5[15]={ + 132.680430393685,255.37973247196,96.15235602819, + -27.273893776752,167.567731083961,192.830034145464, + 8.461744647847,76.653979804423,165.00018874933, + 155.465082847275,197.414118382622,78.408350795821, + // + -68.199829618726,178.938498373416,62.608505919588 + }; + const double volPyra5=756943.92980254; + const double baryPyra5[3]={29.204294116618,172.540129749156,118.01035951483}; + MEDCouplingUMesh *mesh=MEDCouplingUMesh::New("Bary3D2",3); + DataArrayDouble *coo=DataArrayDouble::New(); + coo->alloc(19,3); + double *tmp=std::copy(coordsForHexa8,coordsForHexa8+24,coo->getPointer()); + tmp=std::copy(coordsForPenta6,coordsForPenta6+18,tmp); + std::copy(coordsForPyra5,coordsForPyra5+15,tmp); + mesh->setCoords(coo); + coo->decrRef(); + // + int tmpConn[8]={0,1,2,3,4,5,6,7}; + mesh->allocateCells(3); + mesh->insertNextCell(INTERP_KERNEL::NORM_HEXA8,8,tmpConn); + std::transform(tmpConn,tmpConn+8,tmpConn,std::bind2nd(std::plus(),8)); + mesh->insertNextCell(INTERP_KERNEL::NORM_PENTA6,6,tmpConn); + std::transform(tmpConn,tmpConn+8,tmpConn,std::bind2nd(std::plus(),6)); + mesh->insertNextCell(INTERP_KERNEL::NORM_PYRA5,5,tmpConn); + mesh->finishInsertingCells(); + mesh->checkCoherency(); + bool isMerged; + int newNebOfNodes; + DataArrayInt *da=mesh->mergeNodes(1e-7,isMerged,newNebOfNodes); + da->decrRef(); + CPPUNIT_ASSERT_EQUAL(12,newNebOfNodes); + MEDCouplingFieldDouble *vols=mesh->getMeasureField(true); + CPPUNIT_ASSERT_EQUAL(3,vols->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,vols->getNumberOfComponents()); + CPPUNIT_ASSERT_DOUBLES_EQUAL(volHexa8,vols->getIJ(0,0),1e-6); + CPPUNIT_ASSERT_DOUBLES_EQUAL(volPenta6,vols->getIJ(1,0),1e-7); + CPPUNIT_ASSERT_DOUBLES_EQUAL(volPyra5,vols->getIJ(2,0),1e-7); + vols->decrRef(); + DataArrayDouble *bary=mesh->getBarycenterAndOwner(); + CPPUNIT_ASSERT_EQUAL(3,bary->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(3,bary->getNumberOfComponents()); + CPPUNIT_ASSERT_DOUBLES_EQUAL(baryHexa8[0],bary->getIJ(0,0),1e-11); + CPPUNIT_ASSERT_DOUBLES_EQUAL(baryHexa8[1],bary->getIJ(0,1),1e-11); + CPPUNIT_ASSERT_DOUBLES_EQUAL(baryHexa8[2],bary->getIJ(0,2),1e-11); + CPPUNIT_ASSERT_DOUBLES_EQUAL(baryPenta6[0],bary->getIJ(1,0),1e-11); + CPPUNIT_ASSERT_DOUBLES_EQUAL(baryPenta6[1],bary->getIJ(1,1),1e-11); + CPPUNIT_ASSERT_DOUBLES_EQUAL(baryPenta6[2],bary->getIJ(1,2),1e-11); + CPPUNIT_ASSERT_DOUBLES_EQUAL(baryPyra5[0],bary->getIJ(2,0),1e-11); + CPPUNIT_ASSERT_DOUBLES_EQUAL(baryPyra5[1],bary->getIJ(2,1),1e-11); + CPPUNIT_ASSERT_DOUBLES_EQUAL(baryPyra5[2],bary->getIJ(2,2),1e-11); + bary->decrRef(); + // + mesh->decrRef(); +} + +void MEDCouplingBasicsTest::testGetMeasureFieldCMesh1() +{ + MEDCouplingCMesh *m=MEDCouplingCMesh::New(); + DataArrayDouble *da=DataArrayDouble::New(); + const double discX[4]={2.3,3.4,5.8,10.2}; + const double discY[3]={12.3,23.4,45.8}; + const double discZ[5]={-0.7,1.2,1.25,2.13,2.67}; + da->alloc(4,1); + std::copy(discX,discX+4,da->getPointer()); + m->setCoordsAt(0,da); + da->decrRef(); + m->checkCoherency(); + CPPUNIT_ASSERT_EQUAL(4,m->getNumberOfNodes()); + CPPUNIT_ASSERT_EQUAL(3,m->getNumberOfCells()); + CPPUNIT_ASSERT_EQUAL(1,m->getSpaceDimension()); + MEDCouplingFieldDouble *f=m->getMeasureField(true); + CPPUNIT_ASSERT_EQUAL(3,f->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,f->getNumberOfComponents()); + const double expected1[3]={1.1,2.4,4.4}; + for(int i=0;i<3;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],f->getIJ(i,0),1e-12); + f->decrRef(); + DataArrayDouble *coords=m->getCoordinatesAndOwner(); + CPPUNIT_ASSERT_EQUAL(4,coords->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,coords->getNumberOfComponents()); + for(int i=0;i<4;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(discX[i],coords->getIJ(i,0),1e-12); + coords->decrRef(); + coords=m->getBarycenterAndOwner(); + CPPUNIT_ASSERT_EQUAL(3,coords->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,coords->getNumberOfComponents()); + const double expected1_3[3]={2.85,4.6,8.}; + for(int i=0;i<3;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1_3[i],coords->getIJ(i,0),1e-12); + coords->decrRef(); + // + da=DataArrayDouble::New(); + da->alloc(3,1); + std::copy(discY,discY+3,da->getPointer()); + m->setCoordsAt(1,da); + da->decrRef(); + m->checkCoherency(); + CPPUNIT_ASSERT_EQUAL(12,m->getNumberOfNodes()); + CPPUNIT_ASSERT_EQUAL(6,m->getNumberOfCells()); + CPPUNIT_ASSERT_EQUAL(2,m->getSpaceDimension()); + f=m->getMeasureField(true); + CPPUNIT_ASSERT_EQUAL(6,f->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,f->getNumberOfComponents()); + const double expected2[6]={12.21,26.64,48.84,24.64,53.76,98.56}; + for(int i=0;i<6;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected2[i],f->getIJ(i,0),1e-12); + f->decrRef(); + coords=m->getCoordinatesAndOwner(); + CPPUNIT_ASSERT_EQUAL(12,coords->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,coords->getNumberOfComponents()); + const double expected2_2[24]={2.3,12.3,3.4,12.3,5.8,12.3,10.2,12.3, 2.3,23.4,3.4,23.4,5.8,23.4,10.2,23.4, 2.3,45.8,3.4,45.8,5.8,45.8,10.2,45.8}; + for(int i=0;i<24;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected2_2[i],coords->getIJ(0,i),1e-12); + coords->decrRef(); + coords=m->getBarycenterAndOwner(); + CPPUNIT_ASSERT_EQUAL(6,coords->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,coords->getNumberOfComponents()); + const double expected2_3[12]={2.85,17.85,4.6,17.85,8.,17.85, 2.85,34.6,4.6,34.6,8.,34.6}; + for(int i=0;i<12;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected2_3[i],coords->getIJ(0,i),1e-12); + coords->decrRef(); + // + da=DataArrayDouble::New(); + da->alloc(5,1); + std::copy(discZ,discZ+5,da->getPointer()); + m->setCoordsAt(2,da); + da->decrRef(); + m->checkCoherency(); + CPPUNIT_ASSERT_EQUAL(60,m->getNumberOfNodes()); + CPPUNIT_ASSERT_EQUAL(24,m->getNumberOfCells()); + CPPUNIT_ASSERT_EQUAL(3,m->getSpaceDimension()); + f=m->getMeasureField(true); + CPPUNIT_ASSERT_EQUAL(24,f->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,f->getNumberOfComponents()); + const double expected3[24]={23.199, 50.616, 92.796, 46.816, 102.144, 187.264, 0.6105, 1.332, 2.442, 1.232, 2.688, 4.928, 10.7448, 23.4432, 42.9792, 21.6832, 47.3088, 86.7328, 6.5934, 14.3856, 26.3736, 13.3056, 29.0304, 53.2224}; + for(int i=0;i<24;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected3[i],f->getIJ(i,0),1e-12); + f->decrRef(); + coords=m->getCoordinatesAndOwner(); + CPPUNIT_ASSERT_EQUAL(60,coords->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(3,coords->getNumberOfComponents()); + const double expected3_2[180]={ + 2.3,12.3,-0.7, 3.4,12.3,-0.7, 5.8,12.3,-0.7, 10.2,12.3,-0.7, 2.3,23.4,-0.7, 3.4,23.4,-0.7, 5.8,23.4,-0.7, 10.2,23.4,-0.7, 2.3,45.8,-0.7, 3.4,45.8,-0.7, 5.8,45.8,-0.7, 10.2,45.8,-0.7, + 2.3,12.3,1.2, 3.4,12.3,1.2, 5.8,12.3,1.2, 10.2,12.3,1.2, 2.3,23.4,1.2, 3.4,23.4,1.2, 5.8,23.4,1.2, 10.2,23.4,1.2, 2.3,45.8,1.2, 3.4,45.8,1.2, 5.8,45.8,1.2, 10.2,45.8,1.2, + 2.3,12.3,1.25, 3.4,12.3,1.25, 5.8,12.3,1.25, 10.2,12.3,1.25, 2.3,23.4,1.25, 3.4,23.4,1.25, 5.8,23.4,1.25, 10.2,23.4,1.25, 2.3,45.8,1.25, 3.4,45.8,1.25, 5.8,45.8,1.25, 10.2,45.8,1.25, + 2.3,12.3,2.13, 3.4,12.3,2.13, 5.8,12.3,2.13, 10.2,12.3,2.13, 2.3,23.4,2.13, 3.4,23.4,2.13, 5.8,23.4,2.13, 10.2,23.4,2.13, 2.3,45.8,2.13, 3.4,45.8,2.13, 5.8,45.8,2.13, 10.2,45.8,2.13, + 2.3,12.3,2.67, 3.4,12.3,2.67, 5.8,12.3,2.67, 10.2,12.3,2.67, 2.3,23.4,2.67, 3.4,23.4,2.67, 5.8,23.4,2.67, 10.2,23.4,2.67, 2.3,45.8,2.67, 3.4,45.8,2.67, 5.8,45.8,2.67, 10.2,45.8,2.67 + }; + for(int i=0;i<180;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected3_2[i],coords->getIJ(0,i),1e-12); + coords->decrRef(); + coords=m->getBarycenterAndOwner(); + CPPUNIT_ASSERT_EQUAL(24,coords->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(3,coords->getNumberOfComponents()); + const double expected3_3[72]={ + 2.85,17.85,0.25,4.6,17.85,0.25,8.,17.85,0.25, 2.85,34.6,0.25,4.6,34.6,0.25,8.,34.6,0.25, + 2.85,17.85,1.225,4.6,17.85,1.225,8.,17.85,1.225, 2.85,34.6,1.225,4.6,34.6,1.225,8.,34.6,1.225, + 2.85,17.85,1.69,4.6,17.85,1.69,8.,17.85,1.69, 2.85,34.6,1.69,4.6,34.6,1.69,8.,34.6,1.69, + 2.85,17.85,2.4,4.6,17.85,2.4,8.,17.85,2.4, 2.85,34.6,2.4,4.6,34.6,2.4,8.,34.6,2.4 + }; + for(int i=0;i<72;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected3_3[i],coords->getIJ(0,i),1e-12); + coords->decrRef(); + // + m->decrRef(); +} + +void MEDCouplingBasicsTest::testFieldDoubleZipCoords1() +{ + MEDCouplingUMesh *m=build2DTargetMeshMergeNode_1(); + MEDCouplingFieldDouble *f=m->fillFromAnalytic(ON_NODES,2,"x*2."); + f->getArray()->setInfoOnComponent(0,"titi"); + f->getArray()->setInfoOnComponent(1,"tutu"); + f->checkCoherency(); + CPPUNIT_ASSERT_EQUAL(18,f->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,f->getNumberOfComponents()); + const double expected1[36]={-0.6, -0.6, 0.4, 0.4, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 1.4, 1.4, -0.6, -0.6, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 1.4, 1.4, 0.4, 0.4}; + for(int i=0;i<36;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],f->getIJ(0,i),1e-12); + CPPUNIT_ASSERT(f->zipCoords()); + f->checkCoherency(); + const double expected2[30]={-0.6, -0.6, 1.4, 1.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 1.4, 1.4, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 1.4, 1.4, 0.4, 0.4}; + for(int i=0;i<30;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected2[i],f->getIJ(0,i),1e-12); + CPPUNIT_ASSERT(!f->zipCoords()); + f->checkCoherency(); + for(int i=0;i<30;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected2[i],f->getIJ(0,i),1e-12); + CPPUNIT_ASSERT(std::string(f->getArray()->getInfoOnComponent(0))=="titi"); + CPPUNIT_ASSERT(std::string(f->getArray()->getInfoOnComponent(1))=="tutu"); + f->decrRef(); + m->decrRef(); +} + +void MEDCouplingBasicsTest::testFieldDoubleZipConnectivity1() +{ + MEDCouplingUMesh *m1=build2DTargetMesh_1(); + MEDCouplingUMesh *m2=build2DTargetMesh_1(); + const int cells1[3]={2,3,4}; + MEDCouplingPointSet *m3_1=m2->buildPartOfMySelf(cells1,cells1+3,true); + MEDCouplingUMesh *m3=dynamic_cast(m3_1); + CPPUNIT_ASSERT(m3); + m2->decrRef(); + MEDCouplingUMesh *m4=build2DSourceMesh_1(); + MEDCouplingUMesh *m5=MEDCouplingUMesh::mergeUMeshes(m1,m3); + m1->decrRef(); + m3->decrRef(); + MEDCouplingUMesh *m6=MEDCouplingUMesh::mergeUMeshes(m5,m4); + m4->decrRef(); + m5->decrRef(); + // + CPPUNIT_ASSERT_EQUAL(10,m6->getNumberOfCells()); + CPPUNIT_ASSERT_EQUAL(22,m6->getNumberOfNodes()); + bool areNodesMerged; + int newNbOfNodes; + DataArrayInt *arr=m6->mergeNodes(1e-13,areNodesMerged,newNbOfNodes); + CPPUNIT_ASSERT_EQUAL(9,m6->getNumberOfNodes()); + arr->decrRef(); + MEDCouplingFieldDouble *f=m6->fillFromAnalytic(ON_CELLS,2,"x"); + MEDCouplingFieldDouble *f2=m6->fillFromAnalytic(ON_NODES,2,"x"); + CPPUNIT_ASSERT_EQUAL(10,f->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,f->getNumberOfComponents()); + const double expected1[20]={-0.05, -0.05, 0.3666666666666667, 0.3666666666666667, 0.53333333333333321, 0.53333333333333321, + -0.05, -0.05, 0.45, 0.45, 0.53333333333333321, 0.53333333333333321, -0.05, -0.05, 0.45, 0.45, + 0.36666666666666659, 0.36666666666666659, 0.033333333333333326, 0.033333333333333326}; + for(int i=0;i<20;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],f->getIJ(0,i),1e-12); + f->getArray()->setInfoOnComponent(0,"titi"); + f->getArray()->setInfoOnComponent(1,"tutu"); + f->checkCoherency(); + CPPUNIT_ASSERT(f->zipConnectivity(0)); + const double expected2[14]={-0.05, -0.05, 0.3666666666666667, 0.3666666666666667, 0.53333333333333321, 0.53333333333333321, + -0.05, -0.05, 0.45, 0.45, 0.36666666666666659, 0.36666666666666659, 0.033333333333333326, 0.033333333333333326}; + CPPUNIT_ASSERT_EQUAL(7,f->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,f->getNumberOfComponents()); + for(int i=0;i<14;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected2[i],f->getIJ(0,i),1e-12); + CPPUNIT_ASSERT(std::string(f->getArray()->getInfoOnComponent(0))=="titi"); + CPPUNIT_ASSERT(std::string(f->getArray()->getInfoOnComponent(1))=="tutu"); + CPPUNIT_ASSERT(!f->zipConnectivity(0)); + f->decrRef(); + // + const double expected3[18]={-0.3, -0.3, 0.2, 0.2, 0.7, 0.7, -0.3, -0.3, 0.2, 0.2, 0.7, 0.7, + -0.3, -0.3, 0.2, 0.2, 0.7, 0.7}; + CPPUNIT_ASSERT_EQUAL(9,f2->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,f2->getNumberOfComponents()); + for(int i=0;i<18;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected3[i],f2->getIJ(0,i),1e-12); + CPPUNIT_ASSERT(f2->zipConnectivity(0)); + CPPUNIT_ASSERT_EQUAL(9,f2->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,f2->getNumberOfComponents()); + for(int i=0;i<18;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected3[i],f2->getIJ(0,i),1e-12); + f2->decrRef(); + // + m6->decrRef(); +} + +void MEDCouplingBasicsTest::testDaDoubleRenumber1() +{ + DataArrayDouble *a=DataArrayDouble::New(); + a->alloc(7,2); + a->setInfoOnComponent(0,"toto"); + a->setInfoOnComponent(1,"tata"); + const double arr1[14]={1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1}; + std::copy(arr1,arr1+14,a->getPointer()); + // + const int arr2[7]={3,1,0,6,5,4,2}; + DataArrayDouble *b=a->renumber(arr2); + CPPUNIT_ASSERT_EQUAL(7,b->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,b->getNumberOfComponents()); + CPPUNIT_ASSERT(std::string(b->getInfoOnComponent(0))=="toto"); + CPPUNIT_ASSERT(std::string(b->getInfoOnComponent(1))=="tata"); + const double expected1[14]={3.1, 13.1, 2.1, 12.1, 7.1, 17.1, 1.1, 11.1, 6.1, 16.1, 5.1, 15.1, 4.1, 14.1}; + for(int i=0;i<14;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],b->getIJ(0,i),1e-14); + b->decrRef(); + a->decrRef(); + // + DataArrayInt *c=DataArrayInt::New(); + c->alloc(7,2); + c->setInfoOnComponent(0,"toto"); + c->setInfoOnComponent(1,"tata"); + const int arr3[14]={1,11,2,12,3,13,4,14,5,15,6,16,7,17}; + std::copy(arr3,arr3+14,c->getPointer()); + DataArrayInt *d=c->renumber(arr2); + CPPUNIT_ASSERT_EQUAL(7,d->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,d->getNumberOfComponents()); + CPPUNIT_ASSERT(std::string(d->getInfoOnComponent(0))=="toto"); + CPPUNIT_ASSERT(std::string(d->getInfoOnComponent(1))=="tata"); + const int expected2[14]={3, 13, 2, 12, 7, 17, 1, 11, 6, 16, 5, 15, 4, 14}; + for(int i=0;i<14;i++) + CPPUNIT_ASSERT_EQUAL(expected2[i],d->getIJ(0,i)); + c->decrRef(); + d->decrRef(); +} + +void MEDCouplingBasicsTest::testDaDoubleRenumberAndReduce1() +{ + DataArrayDouble *a=DataArrayDouble::New(); + a->alloc(7,2); + a->setInfoOnComponent(0,"toto"); + a->setInfoOnComponent(1,"tata"); + const double arr1[14]={1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1}; + std::copy(arr1,arr1+14,a->getPointer()); + // + const int arr2[7]={2,-1,1,-1,0,4,3}; + DataArrayDouble *b=a->renumberAndReduce(arr2,5); + CPPUNIT_ASSERT_EQUAL(5,b->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,b->getNumberOfComponents()); + CPPUNIT_ASSERT(std::string(b->getInfoOnComponent(0))=="toto"); + CPPUNIT_ASSERT(std::string(b->getInfoOnComponent(1))=="tata"); + const double expected1[10]={5.1,15.1,3.1,13.1,1.1,11.1,7.1,17.1,6.1,16.1}; + for(int i=0;i<10;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],b->getIJ(0,i),1e-14); + b->decrRef(); + a->decrRef(); + // + DataArrayInt *c=DataArrayInt::New(); + c->alloc(7,2); + c->setInfoOnComponent(0,"toto"); + c->setInfoOnComponent(1,"tata"); + const int arr3[14]={1,11,2,12,3,13,4,14,5,15,6,16,7,17}; + std::copy(arr3,arr3+14,c->getPointer()); + DataArrayInt *d=c->renumberAndReduce(arr2,5); + CPPUNIT_ASSERT_EQUAL(5,d->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,d->getNumberOfComponents()); + CPPUNIT_ASSERT(std::string(d->getInfoOnComponent(0))=="toto"); + CPPUNIT_ASSERT(std::string(d->getInfoOnComponent(1))=="tata"); + const int expected2[10]={5,15,3,13,1,11,7,17,6,16}; + for(int i=0;i<10;i++) + CPPUNIT_ASSERT_EQUAL(expected2[i],d->getIJ(0,i)); + c->decrRef(); + d->decrRef(); +} + +void MEDCouplingBasicsTest::testDaDoubleRenumberInPlace1() +{ + DataArrayDouble *a=DataArrayDouble::New(); + a->alloc(7,2); + const double arr1[14]={1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1}; + std::copy(arr1,arr1+14,a->getPointer()); + // + const int arr2[7]={3,1,0,6,5,4,2}; + a->renumberInPlace(arr2); + CPPUNIT_ASSERT_EQUAL(7,a->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,a->getNumberOfComponents()); + const double expected1[14]={3.1, 13.1, 2.1, 12.1, 7.1, 17.1, 1.1, 11.1, 6.1, 16.1, 5.1, 15.1, 4.1, 14.1}; + for(int i=0;i<14;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],a->getIJ(0,i),1e-14); + a->decrRef(); + // + DataArrayInt *c=DataArrayInt::New(); + c->alloc(7,2); + const int arr3[14]={1,11,2,12,3,13,4,14,5,15,6,16,7,17}; + std::copy(arr3,arr3+14,c->getPointer()); + c->renumberInPlace(arr2); + CPPUNIT_ASSERT_EQUAL(7,c->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,c->getNumberOfComponents()); + const int expected2[14]={3, 13, 2, 12, 7, 17, 1, 11, 6, 16, 5, 15, 4, 14}; + for(int i=0;i<14;i++) + CPPUNIT_ASSERT_EQUAL(expected2[i],c->getIJ(0,i)); + c->decrRef(); +} + +void MEDCouplingBasicsTest::testDaDoubleRenumberR1() +{ + DataArrayDouble *a=DataArrayDouble::New(); + a->alloc(7,2); + a->setInfoOnComponent(0,"toto"); + a->setInfoOnComponent(1,"tata"); + const double arr1[14]={1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1}; + std::copy(arr1,arr1+14,a->getPointer()); + // + const int arr2[7]={3,1,0,6,5,4,2}; + DataArrayDouble *b=a->renumberR(arr2); + CPPUNIT_ASSERT_EQUAL(7,b->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,b->getNumberOfComponents()); + CPPUNIT_ASSERT(std::string(b->getInfoOnComponent(0))=="toto"); + CPPUNIT_ASSERT(std::string(b->getInfoOnComponent(1))=="tata"); + const double expected1[14]={4.1, 14.1, 2.1, 12.1, 1.1, 11.1, 7.1, 17.1, 6.1, 16.1, 5.1, 15.1, 3.1, 13.1}; + for(int i=0;i<14;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],b->getIJ(0,i),1e-14); + b->decrRef(); + a->decrRef(); + // + DataArrayInt *c=DataArrayInt::New(); + c->alloc(7,2); + c->setInfoOnComponent(0,"toto"); + c->setInfoOnComponent(1,"tata"); + const int arr3[14]={1,11,2,12,3,13,4,14,5,15,6,16,7,17}; + std::copy(arr3,arr3+14,c->getPointer()); + DataArrayInt *d=c->renumberR(arr2); + CPPUNIT_ASSERT_EQUAL(7,d->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,d->getNumberOfComponents()); + CPPUNIT_ASSERT(std::string(d->getInfoOnComponent(0))=="toto"); + CPPUNIT_ASSERT(std::string(d->getInfoOnComponent(1))=="tata"); + const int expected2[14]={4, 14, 2, 12, 1, 11, 7, 17, 6, 16, 5, 15, 3, 13}; + for(int i=0;i<14;i++) + CPPUNIT_ASSERT_EQUAL(expected2[i],d->getIJ(0,i)); + c->decrRef(); + d->decrRef(); +} + +void MEDCouplingBasicsTest::testDaDoubleRenumberInPlaceR1() +{ + DataArrayDouble *a=DataArrayDouble::New(); + a->alloc(7,2); + const double arr1[14]={1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1}; + std::copy(arr1,arr1+14,a->getPointer()); + // + const int arr2[7]={3,1,0,6,5,4,2}; + a->renumberInPlaceR(arr2); + CPPUNIT_ASSERT_EQUAL(7,a->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,a->getNumberOfComponents()); + const double expected1[14]={4.1, 14.1, 2.1, 12.1, 1.1, 11.1, 7.1, 17.1, 6.1, 16.1, 5.1, 15.1, 3.1, 13.1}; + for(int i=0;i<14;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],a->getIJ(0,i),1e-14); + a->decrRef(); + // + DataArrayInt *c=DataArrayInt::New(); + c->alloc(7,2); + const int arr3[14]={1,11,2,12,3,13,4,14,5,15,6,16,7,17}; + std::copy(arr3,arr3+14,c->getPointer()); + c->renumberInPlaceR(arr2); + CPPUNIT_ASSERT_EQUAL(7,c->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,c->getNumberOfComponents()); + const int expected2[14]={4, 14, 2, 12, 1, 11, 7, 17, 6, 16, 5, 15, 3, 13}; + for(int i=0;i<14;i++) + CPPUNIT_ASSERT_EQUAL(expected2[i],c->getIJ(0,i)); + c->decrRef(); +} + +void MEDCouplingBasicsTest::testDaDoubleSelectByTupleId1() +{ + DataArrayDouble *a=DataArrayDouble::New(); + a->alloc(7,2); + a->setInfoOnComponent(0,"toto"); + a->setInfoOnComponent(1,"tata"); + const double arr1[14]={1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1}; + std::copy(arr1,arr1+14,a->getPointer()); + // + const int arr2[7]={4,2,0,6,5}; + DataArrayDouble *b=a->selectByTupleId(arr2,arr2+5); + CPPUNIT_ASSERT_EQUAL(5,b->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,b->getNumberOfComponents()); + CPPUNIT_ASSERT(std::string(b->getInfoOnComponent(0))=="toto"); + CPPUNIT_ASSERT(std::string(b->getInfoOnComponent(1))=="tata"); + const double expected1[10]={5.1,15.1,3.1,13.1,1.1,11.1,7.1,17.1,6.1,16.1}; + for(int i=0;i<10;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(expected1[i],b->getIJ(0,i),1e-14); + b->decrRef(); + a->decrRef(); + // + DataArrayInt *c=DataArrayInt::New(); + c->alloc(7,2); + c->setInfoOnComponent(0,"toto"); + c->setInfoOnComponent(1,"tata"); + const int arr3[14]={1,11,2,12,3,13,4,14,5,15,6,16,7,17}; + std::copy(arr3,arr3+14,c->getPointer()); + DataArrayInt *d=c->selectByTupleId(arr2,arr2+5); + CPPUNIT_ASSERT_EQUAL(5,d->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(2,d->getNumberOfComponents()); + CPPUNIT_ASSERT(std::string(d->getInfoOnComponent(0))=="toto"); + CPPUNIT_ASSERT(std::string(d->getInfoOnComponent(1))=="tata"); + const int expected2[10]={5,15,3,13,1,11,7,17,6,16}; + for(int i=0;i<10;i++) + CPPUNIT_ASSERT_EQUAL(expected2[i],d->getIJ(0,i)); + c->decrRef(); + d->decrRef(); +} + +void MEDCouplingBasicsTest::testDaDoubleGetMinMaxValues1() +{ + DataArrayDouble *a=DataArrayDouble::New(); + a->alloc(9,1); + const double arr1[9]={2.34,4.56,-6.77,4.55,4.56,2.24,2.34,1.02,4.56}; + std::copy(arr1,arr1+9,a->getPointer()); + int where; + double m=a->getMaxValue(where); + CPPUNIT_ASSERT_EQUAL(1,where); + CPPUNIT_ASSERT_DOUBLES_EQUAL(4.56,m,1e-12); + DataArrayInt *ws; + m=a->getMaxValue2(ws); + CPPUNIT_ASSERT_DOUBLES_EQUAL(4.56,m,1e-12); + CPPUNIT_ASSERT_EQUAL(3,ws->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,ws->getNumberOfComponents()); + const int expected1[3]={1,4,8}; + for(int i=0;i<3;i++) + CPPUNIT_ASSERT_EQUAL(expected1[i],ws->getIJ(i,0)); + ws->decrRef(); + a->decrRef(); + a=DataArrayDouble::New(); + const double arr2[9]={-2.34,-4.56,6.77,-4.55,-4.56,-2.24,-2.34,-1.02,-4.56}; + a->alloc(9,1); + std::copy(arr2,arr2+9,a->getPointer()); + where=-2; + m=a->getMinValue(where); + CPPUNIT_ASSERT_EQUAL(1,where); + CPPUNIT_ASSERT_DOUBLES_EQUAL(-4.56,m,1e-12); + m=a->getMinValue2(ws); + CPPUNIT_ASSERT_DOUBLES_EQUAL(-4.56,m,1e-12); + CPPUNIT_ASSERT_EQUAL(3,ws->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,ws->getNumberOfComponents()); + for(int i=0;i<3;i++) + CPPUNIT_ASSERT_EQUAL(expected1[i],ws->getIJ(i,0)); + ws->decrRef(); + a->decrRef(); +} + +void MEDCouplingBasicsTest::testFieldDoubleGetMinMaxValues2() +{ + MEDCouplingUMesh *m1=0; + MEDCouplingUMesh *m2=build3DExtrudedUMesh_1(m1); + m1->decrRef(); + CPPUNIT_ASSERT_EQUAL(18,m2->getNumberOfCells()); + const double arr1[18]={8.71,4.53,-12.41,8.71,-8.71,8.7099,4.55,8.71,5.55,6.77,-1e-200,4.55,8.7099,0.,1.23,0.,2.22,8.71}; + MEDCouplingFieldDouble *f=MEDCouplingFieldDouble::New(ON_CELLS,NO_TIME); + DataArrayDouble *a=DataArrayDouble::New(); + a->alloc(18,1); + std::copy(arr1,arr1+18,a->getPointer()); + f->setArray(a); + a->decrRef(); + f->setMesh(m2); + // + f->checkCoherency(); + double m=f->getMaxValue(); + CPPUNIT_ASSERT_DOUBLES_EQUAL(8.71,m,1e-12); + DataArrayInt *ws; + m=f->getMaxValue2(ws); + CPPUNIT_ASSERT_DOUBLES_EQUAL(8.71,m,1e-12); + CPPUNIT_ASSERT_EQUAL(4,ws->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,ws->getNumberOfComponents()); + const int expected1[4]={0,3,7,17}; + for(int i=0;i<4;i++) + CPPUNIT_ASSERT_EQUAL(expected1[i],ws->getIJ(i,0)); + ws->decrRef(); + // + const double arr2[18]={-8.71,-4.53,12.41,-8.71,8.71,-8.7099,-4.55,-8.71,-5.55,-6.77,1e-200,-4.55,-8.7099,0.,-1.23,0.,-2.22,-8.71}; + std::copy(arr2,arr2+18,a->getPointer()); + f->checkCoherency(); + m=f->getMinValue(); + CPPUNIT_ASSERT_DOUBLES_EQUAL(-8.71,m,1e-12); + m=f->getMinValue2(ws); + CPPUNIT_ASSERT_DOUBLES_EQUAL(-8.71,m,1e-12); + CPPUNIT_ASSERT_EQUAL(4,ws->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,ws->getNumberOfComponents()); + for(int i=0;i<4;i++) + CPPUNIT_ASSERT_EQUAL(expected1[i],ws->getIJ(i,0)); + ws->decrRef(); + // + f->decrRef(); + m2->decrRef(); +} + +void MEDCouplingBasicsTest::testBuildUnstructuredCMesh1() +{ + MEDCouplingCMesh *m=MEDCouplingCMesh::New(); + DataArrayDouble *da=DataArrayDouble::New(); + const double discX[4]={2.3,3.4,5.8,10.2}; + const double discY[3]={12.3,23.4,45.8}; + const double discZ[5]={-0.7,1.2,1.25,2.13,2.67}; + da->alloc(4,1); + std::copy(discX,discX+4,da->getPointer()); + m->setCoordsAt(0,da); + da->decrRef(); + m->checkCoherency(); + double pos=2.4; + CPPUNIT_ASSERT_EQUAL(0,m->getCellContainingPoint(&pos,1e-12)); + pos=3.7; + CPPUNIT_ASSERT_EQUAL(1,m->getCellContainingPoint(&pos,1e-12)); + pos=5.9; + CPPUNIT_ASSERT_EQUAL(2,m->getCellContainingPoint(&pos,1e-12)); + pos=10.3; + CPPUNIT_ASSERT_EQUAL(-1,m->getCellContainingPoint(&pos,1e-12)); + pos=1.3; + CPPUNIT_ASSERT_EQUAL(-1,m->getCellContainingPoint(&pos,1e-12)); + // + MEDCouplingUMesh *m2=m->buildUnstructured(); + m2->checkCoherency(); + MEDCouplingFieldDouble *f1=m->getMeasureField(false); + MEDCouplingFieldDouble *f2=m2->getMeasureField(false); + CPPUNIT_ASSERT_EQUAL(f1->getNumberOfTuples(),3); + CPPUNIT_ASSERT_EQUAL(f2->getNumberOfTuples(),3); + CPPUNIT_ASSERT_EQUAL(1,m2->getMeshDimension()); + CPPUNIT_ASSERT_EQUAL(1,m2->getSpaceDimension()); + for(int i=0;i<3;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(f1->getIJ(i,0),f2->getIJ(i,0),1e-10); + da=DataArrayDouble::New(); + da->alloc(3,1); + std::copy(discY,discY+3,da->getPointer()); + m->setCoordsAt(1,da); + da->decrRef(); + m2->decrRef(); + f1->decrRef(); + f2->decrRef(); + // + m2=m->buildUnstructured(); + m2->checkCoherency(); + f1=m->getMeasureField(false); + f2=m2->getMeasureField(false); + CPPUNIT_ASSERT_EQUAL(f1->getNumberOfTuples(),6); + CPPUNIT_ASSERT_EQUAL(f2->getNumberOfTuples(),6); + CPPUNIT_ASSERT_EQUAL(2,m2->getMeshDimension()); + CPPUNIT_ASSERT_EQUAL(2,m2->getSpaceDimension()); + for(int i=0;i<6;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(f1->getIJ(i,0),f2->getIJ(i,0),1e-10); + f1->decrRef(); + f2->decrRef(); + m2->decrRef(); + // + da=DataArrayDouble::New(); + da->alloc(5,1); + std::copy(discZ,discZ+5,da->getPointer()); + m->setCoordsAt(2,da); + da->decrRef(); + m2=m->buildUnstructured(); + m2->checkCoherency(); + f1=m->getMeasureField(false); + f2=m2->getMeasureField(false); + CPPUNIT_ASSERT_EQUAL(f1->getNumberOfTuples(),24); + CPPUNIT_ASSERT_EQUAL(f2->getNumberOfTuples(),24); + CPPUNIT_ASSERT_EQUAL(3,m2->getMeshDimension()); + CPPUNIT_ASSERT_EQUAL(3,m2->getSpaceDimension()); + for(int i=0;i<24;i++) + CPPUNIT_ASSERT_DOUBLES_EQUAL(f1->getIJ(i,0),f2->getIJ(i,0),1e-10); + f1->decrRef(); + f2->decrRef(); + // + double pos1[3]={5.,30.,2.}; + CPPUNIT_ASSERT_EQUAL(16,m->getCellContainingPoint(pos1,1e-12)); + // + const double pt[3]={2.4,12.7,-3.4}; + m->scale(pt,3.7); + MEDCouplingUMesh *m3=m->buildUnstructured(); + m2->scale(pt,3.7); + CPPUNIT_ASSERT(m3->isEqual(m2,1e-12)); + m2->decrRef(); + m3->decrRef(); + // + m->decrRef(); +} + +void MEDCouplingBasicsTest::testDataArrayIntInvertO2NNO21() +{ + const int arr1[6]={2,0,4,1,5,3}; + DataArrayInt *da=DataArrayInt::New(); + da->alloc(6,1); + std::copy(arr1,arr1+6,da->getPointer()); + DataArrayInt *da2=da->invertArrayO2N2N2O(6); + CPPUNIT_ASSERT_EQUAL(6,da2->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,da2->getNumberOfComponents()); + const int expected1[6]={1,3,0,5,2,4}; + for(int i=0;i<6;i++) + CPPUNIT_ASSERT_EQUAL(expected1[i],da2->getIJ(i,0)); + DataArrayInt *da3=da2->invertArrayN2O2O2N(6); + for(int i=0;i<6;i++) + CPPUNIT_ASSERT_EQUAL(arr1[i],da3->getIJ(i,0)); + da3->decrRef(); + da2->decrRef(); + da->decrRef(); + // + const int arr2[10]={3,-1,5,4,-1,0,-1,1,2,-1}; + da=DataArrayInt::New(); + da->alloc(10,1); + std::copy(arr2,arr2+10,da->getPointer()); + da2=da->invertArrayO2N2N2O(6); + CPPUNIT_ASSERT_EQUAL(6,da2->getNumberOfTuples()); + CPPUNIT_ASSERT_EQUAL(1,da2->getNumberOfComponents()); + const int expected2[10]={5,7,8,0,3,2}; + for(int i=0;i<6;i++) + CPPUNIT_ASSERT_EQUAL(expected2[i],da2->getIJ(i,0)); + da3=da2->invertArrayN2O2O2N(10); + for(int i=0;i<10;i++) + CPPUNIT_ASSERT_EQUAL(arr2[i],da3->getIJ(i,0)); + da3->decrRef(); + da2->decrRef(); + da->decrRef(); +} + diff --git a/src/MEDCoupling_Swig/MEDCouplingBasicsTest.py b/src/MEDCoupling_Swig/MEDCouplingBasicsTest.py index 6b058c1ac..d53183363 100644 --- a/src/MEDCoupling_Swig/MEDCouplingBasicsTest.py +++ b/src/MEDCoupling_Swig/MEDCouplingBasicsTest.py @@ -42,15 +42,15 @@ class MEDCouplingBasicsTest(unittest.TestCase): arr1.setValues(arr1Ref,7,2); self.assertEqual(7,arr1.getNumberOfTuples()); self.assertEqual(2,arr1.getNumberOfComponents()); - self.assertEqual(arr1Ref,arr1.getValues()); + self.assertEqual(arr1Ref,list(arr1.getValues())); arr2=arr1.substr(3); self.assertEqual(4,arr2.getNumberOfTuples()); self.assertEqual(2,arr2.getNumberOfComponents()); - self.assertEqual(arr1Ref[6:],arr2.getValues()); + self.assertEqual(arr1Ref[6:],list(arr2.getValues())); arr3=arr1.substr(2,5); self.assertEqual(3,arr3.getNumberOfTuples()); self.assertEqual(2,arr3.getNumberOfComponents()); - self.assertEqual(arr1Ref[4:10],arr3.getValues()); + self.assertEqual(arr1Ref[4:10],list(arr3.getValues())); # arr4=DataArrayDouble.New(); arr4Ref=[0.8,10.8,1.9,11.9,2.1,12.1,3.2,13.2,4.3,14.3,5.4,15.4,6.5,16.5] @@ -200,8 +200,8 @@ class MEDCouplingBasicsTest(unittest.TestCase): revNodalIndexExpected=[0,1,3,5,7,12,14,15,17,18]; self.assertEqual(revNodal.getNbOfElems(),18) self.assertEqual(revNodalIndx.getNbOfElems(),10) - self.assertEqual(revNodal.getValues(),revNodalExpected) - self.assertEqual(revNodalIndx.getValues(),revNodalIndexExpected) + self.assertEqual(list(revNodal.getValues()),revNodalExpected) + self.assertEqual(list(revNodalIndx.getValues()),revNodalIndexExpected) pass def testConvertToPolyTypes(self): mesh=MEDCouplingDataForTest.build2DTargetMesh_1(); @@ -211,7 +211,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(5,mesh.getNumberOfCells()); self.assertEqual(23,mesh.getNodalConnectivity().getNumberOfTuples()); expected1=[4, 0, 3, 4, 1, 5, 1, 4, 2, 3, 4, 5, 2, 5, 6, 7, 4, 3, 4, 7, 8, 5, 4] - self.assertEqual(expected1,mesh.getNodalConnectivity().getValues()); + self.assertEqual(expected1,list(mesh.getNodalConnectivity().getValues())); # mesh=MEDCouplingDataForTest.build3DTargetMesh_1(); mesh.convertToPolyTypes(elts); @@ -238,19 +238,19 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(18,desc.getNbOfElems()); self.assertEqual(18,desc.getNumberOfTuples()); self.assertEqual(18,revDesc.getNbOfElems()); self.assertEqual(18,revDesc.getNumberOfTuples()); expected1=[0,1,2,3, 2,4,5, 6,7,4, 8,9,1,10, 11,12,6,9]; - self.assertEqual(expected1,desc.getValues()); + self.assertEqual(expected1,list(desc.getValues())); expected2=[0,4,7,10,14,18]; - self.assertEqual(expected2,descIndx.getValues()); + self.assertEqual(expected2,list(descIndx.getValues())); expected3=[0,1,3,5,6,8,9,11,12,13,15,16,17,18]; - self.assertEqual(expected3,revDescIndx.getValues()); + self.assertEqual(expected3,list(revDescIndx.getValues())); expected4=[0, 0,3, 0,1, 0, 1,2, 1, 2,4, 2, 3, 3,4, 3, 4, 4]; - self.assertEqual(expected4,revDesc.getValues()); + self.assertEqual(expected4,list(revDesc.getValues())); conn=mesh2.getNodalConnectivity(); connIndex=mesh2.getNodalConnectivityIndex(); expected5=[0,3,6,9,12,15,18,21,24,27,30,33,36,39]; - self.assertEqual(expected5,connIndex.getValues()); + self.assertEqual(expected5,list(connIndex.getValues())); expected6=[1, 0, 3, 1, 3, 4, 1, 4, 1, 1, 1, 0, 1, 4, 2, 1, 2, 1, 1, 4, 5, 1, 5, 2, 1, 6, 7, 1, 7, 4, 1, 3, 6, 1, 7, 8, 1, 8, 5]; - self.assertEqual(expected6,conn.getValues()); + self.assertEqual(expected6,list(conn.getValues())); # eltsV=[1,3]; mesh.convertToPolyTypes(eltsV); @@ -269,14 +269,14 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(6,descIndx.getNbOfElems()); self.assertEqual(6,descIndx.getNumberOfTuples()); self.assertEqual(18,desc.getNbOfElems()); self.assertEqual(18,desc.getNumberOfTuples()); self.assertEqual(18,revDesc.getNbOfElems()); self.assertEqual(18,revDesc.getNumberOfTuples()); - self.assertEqual(expected1,desc.getValues()); - self.assertEqual(expected2,descIndx.getValues()); - self.assertEqual(expected3,revDescIndx.getValues()); - self.assertEqual(expected4,revDesc.getValues()); + self.assertEqual(expected1,list(desc.getValues())); + self.assertEqual(expected2,list(descIndx.getValues())); + self.assertEqual(expected3,list(revDescIndx.getValues())); + self.assertEqual(expected4,list(revDesc.getValues())); conn=mesh2.getNodalConnectivity(); connIndex=mesh2.getNodalConnectivityIndex(); - self.assertEqual(expected5,connIndex.getValues()); - self.assertEqual(expected6,conn.getValues()); + self.assertEqual(expected5,list(connIndex.getValues())); + self.assertEqual(expected6,list(conn.getValues())); pass def testDescConn3D(self): mesh=MEDCouplingDataForTest.build3DTargetMesh_1(); @@ -307,12 +307,12 @@ class MEDCouplingBasicsTest(unittest.TestCase): 17, 16, 7, 4, 18, 21, 22, 19, 4, 9, 18, 19, 10, 4, 10, 19, 22, 13, 4, 13, 22, 21, 12, 4, 12, 21, 18, 9, 4, 19, 22, 23, 20, 4, 10, 19, 20, 11, 4, 11, 20, 23, 14, 4, 14, 23, 22, 13, 4, 21, 24, 25, 22, 4, 13, 22, 25, 16, 4, 16, 25, 24, 15, 4, 15, 24, 21, 12, 4, 22, 25, 26, 23, 4, 14, 23, 26, 17, 4, 17, 26, 25, 16] - self.assertEqual(expected1,descIndx.getValues()); - self.assertEqual(expected2,desc.getValues()); - self.assertEqual(expected3,revDescIndx.getValues()); - self.assertEqual(expected4,revDesc.getValues()); - self.assertEqual(expected5,mesh2.getNodalConnectivityIndex().getValues()); - self.assertEqual(expected6,mesh2.getNodalConnectivity().getValues()); + self.assertEqual(expected1,list(descIndx.getValues())); + self.assertEqual(expected2,list(desc.getValues())); + self.assertEqual(expected3,list(revDescIndx.getValues())); + self.assertEqual(expected4,list(revDesc.getValues())); + self.assertEqual(expected5,list(mesh2.getNodalConnectivityIndex().getValues())); + self.assertEqual(expected6,list(mesh2.getNodalConnectivity().getValues())); # eltsV=[1,3] mesh.convertToPolyTypes(eltsV); @@ -329,18 +329,18 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(9,descIndx.getNbOfElems()); self.assertEqual(9,descIndx.getNumberOfTuples()); self.assertEqual(48,desc.getNbOfElems()); self.assertEqual(48,desc.getNumberOfTuples()); self.assertEqual(48,revDesc.getNbOfElems()); self.assertEqual(48,revDesc.getNumberOfTuples()); - self.assertEqual(expected1,descIndx.getValues()); - self.assertEqual(expected2,desc.getValues()); - self.assertEqual(expected3,revDescIndx.getValues()); - self.assertEqual(expected4,revDesc.getValues()); - self.assertEqual(expected5,mesh2.getNodalConnectivityIndex().getValues()); - self.assertEqual(expected7,mesh2.getNodalConnectivity().getValues()); + self.assertEqual(expected1,list(descIndx.getValues())); + self.assertEqual(expected2,list(desc.getValues())); + self.assertEqual(expected3,list(revDescIndx.getValues())); + self.assertEqual(expected4,list(revDesc.getValues())); + self.assertEqual(expected5,list(mesh2.getNodalConnectivityIndex().getValues())); + self.assertEqual(expected7,list(mesh2.getNodalConnectivity().getValues())); pass def testFindBoundaryNodes(self): mesh=MEDCouplingDataForTest.build3DTargetMesh_1(); boundaryNodes=mesh.findBoundaryNodes(); expected1=[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26]; - self.assertEqual(expected1,boundaryNodes); + self.assertEqual(expected1,list(boundaryNodes)); pass def testBoundaryMesh(self): mesh=MEDCouplingDataForTest.build3DTargetMesh_1(); @@ -368,8 +368,8 @@ class MEDCouplingBasicsTest(unittest.TestCase): subConnIndex=[0,5,10]; self.assertEqual(10,subMesh.getNodalConnectivity().getNbOfElems()); self.assertEqual(3,subMesh.getNodalConnectivityIndex().getNbOfElems()); - self.assertEqual(subConn[0:10],subMesh.getNodalConnectivity().getValues()); - self.assertEqual(subConnIndex[0:3],subMesh.getNodalConnectivityIndex().getValues()); + self.assertEqual(subConn[0:10],list(subMesh.getNodalConnectivity().getValues())); + self.assertEqual(subConnIndex[0:3],list(subMesh.getNodalConnectivityIndex().getValues())); # subMesh=mesh.buildPartOfMySelf(tab2[0:3],True); self.assertTrue(isinstance(subMesh,MEDCouplingUMesh)); @@ -383,8 +383,8 @@ class MEDCouplingBasicsTest(unittest.TestCase): subConnIndex2=[0,5,9,14] self.assertEqual(14,subMesh.getNodalConnectivity().getNbOfElems()); self.assertEqual(4,subMesh.getNodalConnectivityIndex().getNbOfElems()); - self.assertEqual(subConn2[0:14],subMesh.getNodalConnectivity().getValues()); - self.assertEqual(subConnIndex2[0:4],subMesh.getNodalConnectivityIndex().getValues()); + self.assertEqual(subConn2[0:14],list(subMesh.getNodalConnectivity().getValues())); + self.assertEqual(subConnIndex2[0:4],list(subMesh.getNodalConnectivityIndex().getValues())); subMesh=subMesh.buildPartOfMySelf(range(3),True); self.assertEqual("PartOf_Toto",subMesh.getName()); pass @@ -400,8 +400,8 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(2,subMesh.getNodalConnectivityIndex().getNbOfElems()); subConn=[4,7,8,5,4] subConnIndex=[0,5] - self.assertEqual(subConn[0:5],subMesh.getNodalConnectivity().getValues()); - self.assertEqual(subConnIndex[0:2],subMesh.getNodalConnectivityIndex().getValues()); + self.assertEqual(subConn[0:5],list(subMesh.getNodalConnectivity().getValues())); + self.assertEqual(subConnIndex[0:2],list(subMesh.getNodalConnectivityIndex().getValues())); # subMesh=mesh.buildPartOfMySelfNode(tab1[0:2],False); self.assertTrue(isinstance(subMesh,MEDCouplingUMesh)) @@ -413,8 +413,8 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(4,subMesh.getNodalConnectivityIndex().getNbOfElems()); subConn2=[3,4,5,2,4,6,7,4,3,4,7,8,5,4] subConnIndex2=[0,4,9,14] - self.assertEqual(subConn2[0:14],subMesh.getNodalConnectivity().getValues()); - self.assertEqual(subConnIndex2[0:4],subMesh.getNodalConnectivityIndex().getValues()); + self.assertEqual(subConn2[0:14],list(subMesh.getNodalConnectivity().getValues())); + self.assertEqual(subConnIndex2[0:4],list(subMesh.getNodalConnectivityIndex().getValues())); #testing the case where length of tab2 is greater than max number of node per cell. tab2=[0,3,2,1,4,5,6] subMesh=mesh.buildPartOfMySelfNode(tab2[0:7],True); @@ -439,15 +439,15 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(9,mesh.getNumberOfNodes()); self.assertEqual(5,mesh.getNumberOfCells()); self.assertEqual(mesh.getCoords().getValues()[0:2*9],oldCoords.getValues()); - self.assertEqual(oldConn,mesh.getNodalConnectivity().getValues()); - self.assertEqual(oldConnIndex,mesh.getNodalConnectivityIndex().getValues()); + self.assertEqual(list(oldConn),list(mesh.getNodalConnectivity().getValues())); + self.assertEqual(list(oldConnIndex),list(mesh.getNodalConnectivityIndex().getValues())); # tab1=[0,4] subMesh=mesh.buildPartOfMySelf(tab1,True); self.assertTrue(isinstance(subMesh,MEDCouplingUMesh)) traducer=subMesh.zipCoordsTraducer(); - expectedTraducer=[0,1,3,4,5,7,8] - self.assertEqual(expectedTraducer,traducer.getValues()); + expectedTraducer=[0, 1, -1, 2, 3, 4, -1, 5, 6] + self.assertEqual(expectedTraducer,list(traducer.getValues())); self.assertEqual(NORM_QUAD4,subMesh.getAllTypes()[0]); self.assertEqual(2,subMesh.getNumberOfCells()); subConn=[4,0,2,3,1,4,5,6,4,3] @@ -455,8 +455,8 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(7,subMesh.getNumberOfNodes()); self.assertEqual(10,subMesh.getNodalConnectivity().getNbOfElems()); self.assertEqual(3,subMesh.getNodalConnectivityIndex().getNbOfElems()); - self.assertEqual(subConn,subMesh.getNodalConnectivity().getValues()); - self.assertEqual(subConnIndex,subMesh.getNodalConnectivityIndex().getValues()); + self.assertEqual(subConn,list(subMesh.getNodalConnectivity().getValues())); + self.assertEqual(subConnIndex,list(subMesh.getNodalConnectivityIndex().getValues())); # subMesh=mesh.buildPartOfMySelf(tab1,False); self.assertTrue(isinstance(subMesh,MEDCouplingUMesh)) @@ -465,8 +465,8 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(7,subMesh.getNumberOfNodes()); self.assertEqual(10,subMesh.getNodalConnectivity().getNbOfElems()); self.assertEqual(3,subMesh.getNodalConnectivityIndex().getNbOfElems()); - self.assertEqual(subConn,subMesh.getNodalConnectivity().getValues()); - self.assertEqual(subConnIndex,subMesh.getNodalConnectivityIndex().getValues()); + self.assertEqual(subConn,list(subMesh.getNodalConnectivity().getValues())); + self.assertEqual(subConnIndex,list(subMesh.getNodalConnectivityIndex().getValues())); pass def testZipConnectivity(self): m1=MEDCouplingDataForTest.build2DTargetMesh_1(); @@ -510,18 +510,18 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertTrue(mesh2.isEqual(mesh1,1e-12)); # pt2=mesh1.getNodalConnectivity().getValues(); - mesh1.getNodalConnectivity().setIJ(5,0,pt2[5]+1); + mesh1.getNodalConnectivity().setIJ(5,0,int(pt2[5])+1); self.assertTrue(not mesh1.isEqual(mesh2,1e-12)); self.assertTrue(not mesh2.isEqual(mesh1,1e-12)); - mesh1.getNodalConnectivity().setIJ(5,0,pt2[5]); + mesh1.getNodalConnectivity().setIJ(5,0,int(pt2[5])); self.assertTrue(mesh1.isEqual(mesh2,1e-12)); self.assertTrue(mesh2.isEqual(mesh1,1e-12)); # pt2=mesh1.getNodalConnectivityIndex().getValues(); - mesh1.getNodalConnectivityIndex().setIJ(1,0,pt2[1]+1); + mesh1.getNodalConnectivityIndex().setIJ(1,0,int(pt2[1]+1)); self.assertTrue(not mesh1.isEqual(mesh2,1e-12)); self.assertTrue(not mesh2.isEqual(mesh1,1e-12)); - mesh1.getNodalConnectivityIndex().setIJ(1,0,pt2[1]); + mesh1.getNodalConnectivityIndex().setIJ(1,0,int(pt2[1])); self.assertTrue(mesh1.isEqual(mesh2,1e-12)); self.assertTrue(mesh2.isEqual(mesh1,1e-12)); # @@ -654,7 +654,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(1,di.getNumberOfComponents()); toCheck=di.getValues(); expected=[1,2,4,5,7,8] - self.assertEqual(expected,toCheck); + self.assertEqual(expected,list(toCheck)); pass def testExtrudedMesh1(self): mesh3D,mesh2D=MEDCouplingDataForTest.build3DExtrudedUMesh_1(); @@ -665,7 +665,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): ids3DExpected=[5,4,3,2,1,0, 11,10,9,8,7,6, 17,16,15,14,13,12] self.assertEqual(18,ids3D.getNumberOfTuples()); self.assertEqual(1,ids3D.getNumberOfComponents()); - self.assertEqual(ids3DExpected,ids3D.getValues()); + self.assertEqual(ids3DExpected,list(ids3D.getValues())); mesh1D=ext.getMesh1D(); self.assertEqual(4,mesh1D.getNumberOfNodes()); self.assertEqual(3,mesh1D.getNumberOfCells()); @@ -680,7 +680,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(9,conn1D.getNumberOfTuples()); self.assertEqual(1,conn1D.getNumberOfComponents()); conn1DExpected=[1,0,1,1,1,2,1,2,3] - self.assertEqual(conn1DExpected,conn1D.getValues()); + self.assertEqual(conn1DExpected,list(conn1D.getValues())); pass def testExtrudedMesh3(self): @@ -698,7 +698,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(5,m4.getMesh2D().getNumberOfCells()); self.assertEqual(3,m4.getMesh1D().getNumberOfCells()); m3DIds=m4.getMesh3DIds().getValues(); - self.assertEqual(range(15),m3DIds); + self.assertEqual(range(15),list(m3DIds)); #some random in cells to check that extrusion alg find it correctly expected1=[1,3,2,0,6,5,7,10,11,8,12,9,14,13,4] m3.renumberCells(expected1,False); @@ -707,7 +707,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(5,m4.getMesh2D().getNumberOfCells()); self.assertEqual(3,m4.getMesh1D().getNumberOfCells()); m3DIds=m4.getMesh3DIds().getValues(); - self.assertEqual(expected1,m3DIds); + self.assertEqual(expected1,list(m3DIds)); #play with polygons and polyedrons cells=[2,3] m1.convertToPolyTypes(cells); @@ -723,7 +723,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(5,m4.getMesh2D().getNumberOfCells()); self.assertEqual(3,m4.getMesh1D().getNumberOfCells()); m3DIds=m4.getMesh3DIds().getValues(); - self.assertEqual(expected1,m3DIds); + self.assertEqual(expected1,list(m3DIds)); pass def testExtrudedMesh4(self): @@ -771,11 +771,11 @@ class MEDCouplingBasicsTest(unittest.TestCase): comm,commI=targetMesh.findCommonNodes(-1,1e-10); self.assertEqual(1,commI.getNumberOfTuples()); self.assertEqual(0,comm.getNumberOfTuples()); - o2n,newNbOfNodes=targetMesh.buildNewNumberingFromCommNodesFrmt(comm,commI); + o2n,newNbOfNodes=targetMesh.buildNewNumberingFromCommonNodesFormat(comm,commI); self.assertEqual(27,newNbOfNodes); self.assertEqual(27,o2n.getNumberOfTuples()); o2nExp1=range(27) - self.assertEqual(o2nExp1,o2n.getValues()); + self.assertEqual(o2nExp1,list(o2n.getValues())); # targetMesh=MEDCouplingDataForTest.build3DTargetMeshMergeNode_1(); self.assertEqual(31,targetMesh.getNumberOfNodes()); @@ -784,14 +784,14 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(6,comm.getNumberOfTuples()); commExpected=[1,27,28,29,23,30] commIExpected=[0,4,6] - self.assertEqual(commExpected,comm.getValues()); - self.assertEqual(commIExpected,commI.getValues()); - o2n,newNbOfNodes=targetMesh.buildNewNumberingFromCommNodesFrmt(comm,commI); + self.assertEqual(commExpected,list(comm.getValues())); + self.assertEqual(commIExpected,list(commI.getValues())); + o2n,newNbOfNodes=targetMesh.buildNewNumberingFromCommonNodesFormat(comm,commI); self.assertEqual(31,o2n.getNumberOfTuples()); self.assertEqual(27,newNbOfNodes); o2nExp2=[0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20, 21,22,23,24,25,26,1,1,1,23] - self.assertEqual(o2nExp2,o2n.getValues()); + self.assertEqual(o2nExp2,list(o2n.getValues())); # targetMesh=MEDCouplingDataForTest.build3DTargetMesh_1(); time=targetMesh.getTimeOfThis(); @@ -811,7 +811,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): 18,9,10,13,12,18,19,22,21, 18,10,11,14,13,19,20,23,22, 18,12,13,16,15,21,22,25,24, 18,13,14,17,16,22,23,26,25] self.assertEqual(72,targetMesh.getNodalConnectivity().getNumberOfTuples()); - self.assertEqual(connExp,targetMesh.getNodalConnectivity().getValues()); + self.assertEqual(connExp,list(targetMesh.getNodalConnectivity().getValues())); self.assertEqual(27,targetMesh.getCoords().getNumberOfTuples()); coordsExp=[ 0., 0., 0., 50., 0., 0. , 200., 0., 0. , 0., 50., 0., 50., 50., 0. , 200., 50., 0., 0., 200., 0., 50., 200., 0. , 200., 200., 0. , @@ -831,7 +831,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(9,targetMesh.getNumberOfNodes()); connExp2=[4,0,4,3,1, 3,1,3,2, 3,3,5,2, 4,4,6,7,3, 4,7,8,5,3] self.assertEqual(23,targetMesh.getNodalConnectivity().getNumberOfTuples()); - self.assertEqual(connExp2,targetMesh.getNodalConnectivity().getValues()); + self.assertEqual(connExp2,list(targetMesh.getNodalConnectivity().getValues())); coordsExp2=[-0.3,-0.3, 0.2,-0.3, 0.7,-0.3, 0.2,0.2, -0.3,0.2, 0.7,0.2, -0.3,0.7, 0.2,0.7, 0.7,0.7] self.assertEqual(9,targetMesh.getCoords().getNumberOfTuples()); self.assertEqual(coordsExp2,targetMesh.getCoords().getValues()); @@ -978,9 +978,11 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertTrue(abs(tmp[i]-values3[i])<1.e-12) pass values4=f1.accumulate(); + self.assertEqual(2,len(values4)) self.assertTrue(abs(3.6-values4[0])<1.e-12); self.assertTrue(abs(7.2-values4[1])<1.e-12); values4=f1.integral(True); + self.assertEqual(2,len(values4)) self.assertTrue(abs(0.5-values4[0])<1.e-12); self.assertTrue(abs(1.-values4[1])<1.e-12); # @@ -1364,16 +1366,16 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertTrue(not targetMesh.checkConsecutiveCellTypes()); self.assertTrue(not targetMesh.checkConsecutiveCellTypesAndOrder(order1)); self.assertTrue(not targetMesh.checkConsecutiveCellTypesAndOrder(order2)); - da=targetMesh.getRenumArrForConsctvCellTypesSpe(order1); + da=targetMesh.getRenumArrForConsecutiveCellTypesSpec(order1); self.assertEqual(5,da.getNumberOfTuples()); self.assertEqual(1,da.getNumberOfComponents()); expected1=[2,0,1,3,4] - self.assertTrue(expected1==da.getValues()); - da=targetMesh.getRenumArrForConsctvCellTypesSpe(order2); + self.assertTrue(expected1==list(da.getValues())); + da=targetMesh.getRenumArrForConsecutiveCellTypesSpec(order2); self.assertEqual(5,da.getNumberOfTuples()); self.assertEqual(1,da.getNumberOfComponents()); expected2=[0,3,4,1,2] - self.assertTrue(expected2==da.getValues()); + self.assertTrue(expected2==list(da.getValues())); renumber1=[4,0,1,2,3] targetMesh.renumberCells(renumber1,False); self.assertTrue(targetMesh.checkConsecutiveCellTypes()); @@ -1395,11 +1397,11 @@ class MEDCouplingBasicsTest(unittest.TestCase): arr1=m2_1.rearrange2ConsecutiveCellTypes(); self.assertEqual(5,arr1.getNumberOfTuples()); self.assertEqual(1,arr1.getNumberOfComponents()); - self.assertEqual(expected2,arr1.getValues()); + self.assertEqual(expected2,list(arr1.getValues())); m2_2=MEDCouplingDataForTest.build2DTargetMesh_1(); self.assertEqual(5,arr1.getNumberOfTuples()); self.assertEqual(1,arr1.getNumberOfComponents()); - self.assertEqual(expected2,arr1.getValues()); + self.assertEqual(expected2,list(arr1.getValues())); self.assertTrue(not m2_2.isEqual(m2_1,1e-12)); m2_2.renumberCells(expected2,False); self.assertTrue(m2_2.isEqual(m2_1,1e-12)); @@ -1438,7 +1440,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): nbOfVals=expectedVals1[i]; self.assertEqual(nbOfVals,arr.getNumberOfTuples()); vals=arr.getValues(); - self.assertEqual(expectedVals2[i],vals); + self.assertEqual(expectedVals2[i],list(vals)); pass arr2,fidsOfGroups=DataArrayInt.makePartition(corr,m7.getNumberOfCells()); fidExp=[5,1,3,4] @@ -1446,10 +1448,10 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(3,len(fidsOfGroups)); self.assertEqual(1,arr2.getNumberOfComponents()); self.assertEqual(4,arr2.getNumberOfTuples()); - self.assertEqual(fidExp,arr2.getValues()); + self.assertEqual(fidExp,list(arr2.getValues())); for i in xrange(3): nbOfVals=expectedVals1[i]; - self.assertEqual(fidsOfGroups[i],fidsGrp[i]); + self.assertEqual(list(fidsOfGroups[i]),fidsGrp[i]); pass pass @@ -1469,7 +1471,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): [5,6,4,7]] i=0; for it in corr: - self.assertEqual(exp2[i],it.getValues()); + self.assertEqual(exp2[i],list(it.getValues())); i+=1 pass pass @@ -1512,8 +1514,8 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(7,len(t2)); expectedValues1=[0,4,3,0,1,2] expectedValues2=[0,1,2,3,4,5,6] - self.assertEqual(t1,expectedValues1); - self.assertEqual(t2,expectedValues2); + self.assertEqual(list(t1),expectedValues1); + self.assertEqual(list(t2),expectedValues2); #2D with no help of bounding box. center=[0.2,0.2] MEDCouplingPointSet.rotate2DAlg(center,0.78539816339744830962,6,pos); @@ -1523,8 +1525,8 @@ class MEDCouplingBasicsTest(unittest.TestCase): t1,t2=targetMesh.getCellsContainingPoints(pos,6,1e-12); self.assertEqual(6,len(t1)); self.assertEqual(7,len(t2)); - self.assertEqual(t1,expectedValues1); - self.assertEqual(t2,expectedValues2); + self.assertEqual(list(t1),expectedValues1); + self.assertEqual(list(t2),expectedValues2); #2D outside pos1bis=[-0.3303300858899107,-0.11819805153394641] self.assertEqual(-1,targetMesh.getCellContainingPoint(pos1bis,1e-12)); @@ -1535,13 +1537,13 @@ class MEDCouplingBasicsTest(unittest.TestCase): t1=targetMesh.getCellsContainingPoint(pos2,1e-12) self.assertEqual(2,len(t1)); expectedValues3=[0,1] - self.assertEqual(t1,expectedValues3); + self.assertEqual(list(t1),expectedValues3); pos3=[0.2,0.2] t1=None t1=targetMesh.getCellsContainingPoint(pos3,1e-12); self.assertEqual(5,len(t1)); expectedValues4=[0,1,2,3,4] - self.assertEqual(t1,expectedValues4); + self.assertEqual(list(t1),expectedValues4); self.assertEqual(0,targetMesh.getCellContainingPoint(pos3,1e-12)); #3D targetMesh=MEDCouplingDataForTest.build3DTargetMesh_1(); @@ -1552,13 +1554,13 @@ class MEDCouplingBasicsTest(unittest.TestCase): t1=targetMesh.getCellsContainingPoint(pos5,1e-12); self.assertEqual(8,len(t1)); expectedValues5=[0,1,2,3,4,5,6,7] - self.assertEqual(t1,expectedValues5); + self.assertEqual(list(t1),expectedValues5); pos6=[0., 50., 0.] t1=None t1=targetMesh.getCellsContainingPoint(pos6,1e-12); self.assertEqual(2,len(t1)); expectedValues6=[0,2] - self.assertEqual(t1,expectedValues6); + self.assertEqual(list(t1),expectedValues6); #3D outside pos7=[-1.0,-1.0,0.] self.assertEqual(-1,targetMesh.getCellContainingPoint(pos7,1e-12)); @@ -1685,7 +1687,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertEqual(8,me.getNumberOfCells()); expected=[0,1,2,3,4,5,6,7] val=da.getValues(); - self.assertEqual(expected,val); + self.assertEqual(expected,list(val)); pass def testRenumberCells(self): @@ -1787,7 +1789,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): f.setGaussLocalizationOnCells(ids4,_refCoo2,_gsCoo2,_wg2); self.assertEqual(3,f.getNbOfGaussLocalization()); tmpIds=f.getCellIdsHavingGaussLocalization(0); - self.assertEqual(ids2,tmpIds); + self.assertEqual(ids2,list(tmpIds)); self.assertRaises(Exception,f.checkCoherency);#<- it's always not ok because undelying array not with the good size. array2=f.getArray().substr(0,10); f.setArray(array2); @@ -1996,7 +1998,9 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertTrue(abs(expected2[i]-ptr[i])<1e-12); pass #integral + self.assertTrue(4,f1.getNumberOfTuples()) res=f1.integral(False); + self.assertTrue(3,len(res)) expected3=[0.9866,-0.3615,0.4217] for i in xrange(3): self.assertTrue(abs(expected3[i]-res[i])<1e-12); @@ -2011,6 +2015,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): pass #normL1 res=f1.normL1(); + self.assertTrue(3,len(res)) expected5=[11.3068,27.3621,43.7881] for i in xrange(3): self.assertTrue(abs(expected5[i]-res[i])<1e-12); @@ -2020,6 +2025,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertTrue(abs(expected5[2]-f1.normL1(2))<1e-12); #normL2 res=f1.normL2(); + self.assertTrue(3,len(res)) expected7=[9.0252562290496776, 21.545259176904789, 34.433193070059595] for i in xrange(3): self.assertTrue(abs(expected7[i]-res[i])<1e-9); @@ -2027,10 +2033,10 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertTrue(abs(expected7[0]-f1.normL2(0))<1e-9); self.assertTrue(abs(expected7[1]-f1.normL2(1))<1e-9); self.assertTrue(abs(expected7[2]-f1.normL2(2))<1e-9); - #buildWeightingField - f4=f1.buildWeightingField(False); + #buildMeasureField + f4=f1.buildMeasureField(False); self.assertTrue(abs(-0.2-f4.accumulate(0))<1e-12); - f4=f1.buildWeightingField(True); + f4=f1.buildMeasureField(True); self.assertTrue(abs(1.62-f4.accumulate(0))<1e-12); # Testing with 2D Curve m1=MEDCouplingDataForTest.build2DCurveTargetMesh_3(); @@ -2399,7 +2405,7 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertTrue(cellCor); self.assertEqual(10,cellCor.getNumberOfTuples()); self.assertEqual(1,cellCor.getNumberOfComponents()); - self.assertEqual(renum,cellCor.getValues()) + self.assertEqual(renum,list(cellCor.getValues())) self.assertTrue(nodeCor==None); cellCor=0; self.assertTrue(nodeCor==None); @@ -2420,11 +2426,11 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertTrue(cellCor); self.assertEqual(10,cellCor.getNumberOfTuples()); self.assertEqual(1,cellCor.getNumberOfComponents()); - self.assertEqual(renum,cellCor.getValues()) + self.assertEqual(renum,list(cellCor.getValues())) self.assertTrue(nodeCor); self.assertEqual(11,nodeCor.getNumberOfTuples()); self.assertEqual(1,nodeCor.getNumberOfComponents()); - self.assertEqual(renum2,nodeCor.getValues()) + self.assertEqual(renum2,list(nodeCor.getValues())) cellCor=0; nodeCor=0; #5th test : modification of the last cell to check fastCheck detection. @@ -2444,11 +2450,11 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertTrue(cellCor!=None); self.assertEqual(10,cellCor.getNumberOfTuples()); self.assertEqual(1,cellCor.getNumberOfComponents()); - self.assertEqual(renum3,cellCor.getValues()) + self.assertEqual(renum3,list(cellCor.getValues())) self.assertTrue(nodeCor!=None); self.assertEqual(11,nodeCor.getNumberOfTuples()); self.assertEqual(1,nodeCor.getNumberOfComponents()); - self.assertEqual(renum2,nodeCor.getValues()); + self.assertEqual(renum2,list(nodeCor.getValues())); pass def testCheckGeoEquivalWith2(self): @@ -2775,11 +2781,11 @@ class MEDCouplingBasicsTest(unittest.TestCase): da=f1.getIdsInRange(2.9,7.1); self.failUnlessEqual(5,da.getNbOfElems()); expected1=[2,3,5,7,9] - self.failUnlessEqual(expected1,da.getValues()); + self.failUnlessEqual(expected1,list(da.getValues())); da=f1.getIdsInRange(8.,12.); self.failUnlessEqual(4,da.getNbOfElems()); expected2=[1,4,6,8] - self.failUnlessEqual(expected2,da.getValues()); + self.failUnlessEqual(expected2,list(da.getValues())); # pass @@ -2812,9 +2818,9 @@ class MEDCouplingBasicsTest(unittest.TestCase): self.assertAlmostEqual(expected2[i],m2C.getCoords().getIJ(0,i),12); pass expected3=[3,2,3,1,3,0,2,1,4,4,5,3,2] - self.failUnlessEqual(expected3,m2C.getNodalConnectivity().getValues()); + self.failUnlessEqual(expected3,list(m2C.getNodalConnectivity().getValues())); expected4=[0,4,8,13] - self.failUnlessEqual(expected4,m2C.getNodalConnectivityIndex().getValues()); + self.failUnlessEqual(expected4,list(m2C.getNodalConnectivityIndex().getValues())); # Test with field on nodes. f1=MEDCouplingFieldDouble.New(ON_NODES,ONE_TIME); f1.setTime(2.3,5,6); @@ -2840,9 +2846,9 @@ class MEDCouplingBasicsTest(unittest.TestCase): for i in xrange(8):#8 is not an error self.assertAlmostEqual(expected2[i],m2C.getCoords().getIJ(0,i),12); pass - self.failUnlessEqual(expected3[:4],m2C.getNodalConnectivity().getValues()[4:]); - self.failUnlessEqual(expected3[4:8],m2C.getNodalConnectivity().getValues()[:4]); - self.failUnlessEqual(expected4[:3],m2C.getNodalConnectivityIndex().getValues()); + self.failUnlessEqual(expected3[:4],list(m2C.getNodalConnectivity().getValues())[4:]); + self.failUnlessEqual(expected3[4:8],list(m2C.getNodalConnectivity().getValues())[:4]); + self.failUnlessEqual(expected4[:3],list(m2C.getNodalConnectivityIndex().getValues())); #idem previous because nodes of cell#4 are not fully present in part3 part3=[1,4,2,5,7] arrr=DataArrayInt.New(); @@ -2862,9 +2868,9 @@ class MEDCouplingBasicsTest(unittest.TestCase): for i in xrange(8):#8 is not an error self.assertAlmostEqual(expected2[i],m2C.getCoords().getIJ(0,i),12); pass - self.failUnlessEqual(expected3[:4],m2C.getNodalConnectivity().getValues()[4:8]); - self.failUnlessEqual(expected3[4:8],m2C.getNodalConnectivity().getValues()[:4]); - self.failUnlessEqual(expected4[:3],m2C.getNodalConnectivityIndex().getValues()); + self.failUnlessEqual(expected3[:4],list(m2C.getNodalConnectivity().getValues())[4:8]); + self.failUnlessEqual(expected3[4:8],list(m2C.getNodalConnectivity().getValues())[:4]); + self.failUnlessEqual(expected4[:3],list(m2C.getNodalConnectivityIndex().getValues())); # part4=[1,4,2,5,7,8] f2=f1.buildSubPart(part4); @@ -2883,10 +2889,1238 @@ class MEDCouplingBasicsTest(unittest.TestCase): for i in xrange(12): self.assertAlmostEqual(expected2[i],m2C.getCoords().getIJ(0,i),12); pass - self.failUnlessEqual(expected3[0:4],m2C.getNodalConnectivity().getValues()[4:8]); - self.failUnlessEqual(expected3[4:8],m2C.getNodalConnectivity().getValues()[0:4]); - self.failUnlessEqual(expected3[8:13],m2C.getNodalConnectivity().getValues()[8:13]); - self.failUnlessEqual(expected4,m2C.getNodalConnectivityIndex().getValues()); + self.failUnlessEqual(expected3[0:4],list(m2C.getNodalConnectivity().getValues())[4:8]); + self.failUnlessEqual(expected3[4:8],list(m2C.getNodalConnectivity().getValues())[0:4]); + self.failUnlessEqual(expected3[8:13],list(m2C.getNodalConnectivity().getValues())[8:13]); + self.failUnlessEqual(expected4,list(m2C.getNodalConnectivityIndex().getValues())); + pass + + def testDoublyContractedProduct1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5] + array.setValues(arr1,mesh1.getNumberOfCells(),6); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.doublyContractedProduct(); + f2.checkCoherency(); + self.assertEqual(1,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(3906.56,f2.getIJ(i,0),9); + pass + # + pass + + def testDeterminant1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,CONST_ON_TIME_INTERVAL); + f1.setTime(2.3,5,6); + f1.setEndTime(3.8,7,3); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5] + array.setValues(arr1,mesh1.getNumberOfCells(),4); + f1.setArray(array); + #4 components + f1.checkCoherency(); + f2=f1.determinant(); + f2.checkCoherency(); + self.assertEqual(CONST_ON_TIME_INTERVAL,f2.getTimeDiscretization()); + self.assertEqual(1,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfValues()); + for i in xrange(5): + self.assertAlmostEqual(-2.42,f2.getIJ(i,0),13); + pass + #6 components multi arrays with end array not defined + f1=MEDCouplingFieldDouble.New(ON_NODES,LINEAR_TIME); + f1.setTime(2.3,5,6); + f1.setEndTime(3.8,7,3); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr2=[1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, + 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7] + array.setValues(arr2,mesh1.getNumberOfNodes(),6); + f1.setArray(array); + self.assertRaises(Exception,f1.checkCoherency);#no end array specified ! + # + f2=f1.determinant(); + self.assertEqual(LINEAR_TIME,f2.getTimeDiscretization()); + self.assertEqual(1,f2.getArray().getNumberOfComponents()); + self.assertEqual(9,f2.getNumberOfTuples()); + for i in xrange(9): + self.assertAlmostEqual(137.335,f2.getIJ(i,0),10); + pass + #6 components multi arrays with end array defined + array=DataArrayDouble.New(); + arr3=[7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, + 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5] + array.setValues(arr3,mesh1.getNumberOfNodes(),6); + f1.setEndArray(array); + f1.checkCoherency(); + f2=f1.determinant(); + f2.checkCoherency(); + self.assertEqual(LINEAR_TIME,f2.getTimeDiscretization()); + self.assertEqual(1,f2.getNumberOfComponents()); + self.assertEqual(9,f2.getNumberOfTuples()); + time2,it,order=f2.getTime() + self.assertAlmostEqual(2.3,time2,12); + self.assertEqual(5,it); + self.assertEqual(6,order); + time2,it,order=f2.getEndTime() + self.assertAlmostEqual(3.8,time2,12); + self.assertEqual(7,it); + self.assertEqual(3,order); + for i in xrange(9): + self.assertAlmostEqual(137.335,f2.getIJ(i,0),10); + self.assertAlmostEqual(1289.685,f2.getEndArray().getIJ(i,0),9); + pass + #9 components + f1=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME); + f1.setTime(7.8,10,2); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr4=[1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1] + array.setValues(arr4,mesh1.getNumberOfCells(),9); + f1.setArray(array); + # + f1.checkCoherency(); + f2=f1.determinant(); + f2.checkCoherency(); + self.assertEqual(ONE_TIME,f2.getTimeDiscretization()); + self.assertEqual(1,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + time2,it,order=f2.getTime() + self.assertAlmostEqual(7.8,time2,12); + self.assertEqual(10,it); + self.assertEqual(2,order); + for i in xrange(5): + self.assertAlmostEqual(3.267,f2.getIJ(i,0),13); + pass + pass + + def testEigenValues1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7] + array.setValues(arr1,mesh1.getNumberOfCells(),6); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.eigenValues(); + f2.checkCoherency(); + self.assertEqual(3,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + expected1=[13.638813677891717,-4.502313844635971,-2.2364998332557486] + for i in xrange(5): + self.assertAlmostEqual(expected1[0],f2.getIJ(i,0),13); + self.assertAlmostEqual(expected1[1],f2.getIJ(i,1),13); + self.assertAlmostEqual(expected1[2],f2.getIJ(i,2),13); + pass + pass + + def testEigenVectors1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7] + array.setValues(arr1,mesh1.getNumberOfCells(),6); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.eigenVectors(); + f2.checkCoherency(); + self.assertEqual(9,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + expected1=[0.5424262364180696, 0.5351201064614425, 0.6476266283176001,#eigenvect 0 + 0.7381111277307373, 0.06458838384003074, -0.6715804522117897,#eigenvect 1 + -0.4012053603397987, 0.8423032781211455, -0.3599436712889738#eigenvect 2 + ] + for i in xrange(5): + self.assertAlmostEqual(expected1[0],f2.getIJ(i,0),13); + self.assertAlmostEqual(expected1[1],f2.getIJ(i,1),13); + self.assertAlmostEqual(expected1[2],f2.getIJ(i,2),13); + self.assertAlmostEqual(expected1[3],f2.getIJ(i,3),13); + self.assertAlmostEqual(expected1[4],f2.getIJ(i,4),13); + self.assertAlmostEqual(expected1[5],f2.getIJ(i,5),13); + self.assertAlmostEqual(expected1[6],f2.getIJ(i,6),13); + self.assertAlmostEqual(expected1[7],f2.getIJ(i,7),13); + self.assertAlmostEqual(expected1[8],f2.getIJ(i,8),13); + pass + # + pass + + def testInverse1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1] + array.setValues(arr1,mesh1.getNumberOfCells(),9); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.inverse(); + f2.checkCoherency(); + self.assertEqual(9,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + expected1=[-2.6538108356290113, 2.855831037649208, -1.1111111111111067, 3.461891643709813, -4.775022956841121, 2.2222222222222143, -1.1111111111111054, 2.222222222222214, -1.1111111111111072] + for i in xrange(5): + self.assertAlmostEqual(expected1[0],f2.getIJ(i,0),13); + self.assertAlmostEqual(expected1[1],f2.getIJ(i,1),13); + self.assertAlmostEqual(expected1[2],f2.getIJ(i,2),13); + self.assertAlmostEqual(expected1[3],f2.getIJ(i,3),13); + self.assertAlmostEqual(expected1[4],f2.getIJ(i,4),13); + self.assertAlmostEqual(expected1[5],f2.getIJ(i,5),13); + self.assertAlmostEqual(expected1[6],f2.getIJ(i,6),13); + self.assertAlmostEqual(expected1[7],f2.getIJ(i,7),13); + self.assertAlmostEqual(expected1[8],f2.getIJ(i,8),13); + pass + # + array=DataArrayDouble.New(); + arr3=[7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5] + array.setValues(arr3,mesh1.getNumberOfCells(),6); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.inverse(); + f2.checkCoherency(); + self.assertEqual(6,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + expected3=[-0.3617705098531818, -0.8678630828458127, -0.026843764174972983, 0.5539957431465833, 0.13133439560823013, -0.05301294502145887] + for i in xrange(5): + self.assertAlmostEqual(expected3[0],f2.getIJ(i,0),13); + self.assertAlmostEqual(expected3[1],f2.getIJ(i,1),13); + self.assertAlmostEqual(expected3[2],f2.getIJ(i,2),13); + self.assertAlmostEqual(expected3[3],f2.getIJ(i,3),13); + self.assertAlmostEqual(expected3[4],f2.getIJ(i,4),13); + self.assertAlmostEqual(expected3[5],f2.getIJ(i,5),13); + pass + # + array=DataArrayDouble.New(); + arr2=[1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5] + array.setValues(arr2,mesh1.getNumberOfCells(),4); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.inverse(); + f2.checkCoherency(); + self.assertEqual(4,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + expected2=[-1.8595041322314059, 0.9504132231404963, 1.404958677685951, -0.49586776859504156] + for i in xrange(5): + self.assertAlmostEqual(expected2[0],f2.getIJ(i,0),13); + self.assertAlmostEqual(expected2[1],f2.getIJ(i,1),13); + self.assertAlmostEqual(expected2[2],f2.getIJ(i,2),13); + self.assertAlmostEqual(expected2[3],f2.getIJ(i,3),13); + pass + # + pass + + def testTrace1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1, 1.2,2.3,3.4,4.5,5.6,6.7,7.8,8.9,9.1] + array.setValues(arr1,mesh1.getNumberOfCells(),9); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.trace(); + f2.checkCoherency(); + self.assertEqual(1,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(15.9,f2.getIJ(i,0),13); + pass + # + array=DataArrayDouble.New(); + arr3=[7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5, 7.8,8.9,9.1,10.2,23.4,34.5] + array.setValues(arr3,mesh1.getNumberOfCells(),6); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.trace(); + f2.checkCoherency(); + self.assertEqual(1,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(25.8,f2.getIJ(i,0),13); + pass + # + array=DataArrayDouble.New(); + arr2=[1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5, 1.2,2.3,3.4,4.5] + array.setValues(arr2,mesh1.getNumberOfCells(),4); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.trace(); + f2.checkCoherency(); + self.assertEqual(1,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(5.7,f2.getIJ(i,0),13); + pass + # + pass + + def testDeviator1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7, 1.2,2.3,3.4,4.5,5.6,6.7] + array.setValues(arr1,mesh1.getNumberOfCells(),6); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.deviator(); + f2.checkCoherency(); + self.assertEqual(6,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + expected1=[-1.1,0.,1.1,4.5,5.6,6.7] + for i in xrange(5): + self.assertAlmostEqual(expected1[0],f2.getIJ(i,0),13); + self.assertAlmostEqual(expected1[1],f2.getIJ(i,1),13); + self.assertAlmostEqual(expected1[2],f2.getIJ(i,2),13); + self.assertAlmostEqual(expected1[3],f2.getIJ(i,3),13); + self.assertAlmostEqual(expected1[4],f2.getIJ(i,4),13); + self.assertAlmostEqual(expected1[5],f2.getIJ(i,5),13); + pass + # + pass + + def testMagnitude1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5,5.6, 1.2,2.3,3.4,4.5,5.6, 1.2,2.3,3.4,4.5,5.6, 1.2,2.3,3.4,4.5,5.6, 1.2,2.3,3.4,4.5,5.6] + array.setValues(arr1,mesh1.getNumberOfCells(),5); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.magnitude(); + f2.checkCoherency(); + self.assertEqual(1,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(8.3606219864313918,f2.getIJ(i,0),13); + pass + # + pass + + def testMaxPerTuple1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5,5.6, 1.2,3.4,4.5,5.6,2.3, 3.4,4.5,5.6,1.2,2.3, 5.6,1.2,2.3,3.4,4.5, 4.5,5.6,1.2,2.3,3.4] + array.setValues(arr1,mesh1.getNumberOfCells(),5); + f1.setArray(array); + f1.checkCoherency(); + # + f2=f1.maxPerTuple(); + f2.checkCoherency(); + self.assertEqual(1,f2.getNumberOfComponents()); + self.assertEqual(5,f2.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(5.6,f2.getIJ(i,0),13); + pass + # + pass + + def testChangeNbOfComponents(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5,5.6, 1.2,3.4,4.5,5.6,2.3, 3.4,4.5,5.6,1.2,2.3, 5.6,1.2,2.3,3.4,4.5, 4.5,5.6,1.2,2.3,3.4] + array.setValues(arr1,mesh1.getNumberOfCells(),5); + f1.setArray(array); + f1.checkCoherency(); + # + f1.changeNbOfComponents(3,7.77); + f1.checkCoherency(); + self.assertEqual(3,f1.getNumberOfComponents()); + self.assertEqual(5,f1.getNumberOfTuples()); + expected1=[1.2,2.3,3.4, 1.2,3.4,4.5, 3.4,4.5,5.6, 5.6,1.2,2.3, 4.5,5.6,1.2] + for i in xrange(15): + self.assertAlmostEqual(expected1[i],f1.getIJ(0,i),13); + pass + f1.changeNbOfComponents(4,7.77); + f1.checkCoherency(); + self.assertEqual(4,f1.getNumberOfComponents()); + self.assertEqual(5,f1.getNumberOfTuples()); + expected2=[1.2,2.3,3.4,7.77, 1.2,3.4,4.5,7.77, 3.4,4.5,5.6,7.77, 5.6,1.2,2.3,7.77, 4.5,5.6,1.2,7.77] + for i in xrange(20): + self.assertAlmostEqual(expected2[i],f1.getIJ(0,i),13); + pass + # + pass + + def testSortPerTuple1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + f1.setMesh(mesh1); + array=DataArrayDouble.New(); + arr1=[1.2,2.3,3.4,4.5,5.6, 1.2,3.4,4.5,5.6,2.3, 3.4,4.5,5.6,1.2,2.3, 5.6,1.2,2.3,3.4,4.5, 4.5,5.6,1.2,2.3,3.4] + array.setValues(arr1,mesh1.getNumberOfCells(),5); + f1.setArray(array); + f1.checkCoherency(); + # + f1.sortPerTuple(True); + f1.checkCoherency(); + self.assertEqual(5,f1.getNumberOfComponents()); + self.assertEqual(5,f1.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(arr1[0],f1.getIJ(i,0),13); + self.assertAlmostEqual(arr1[1],f1.getIJ(i,1),13); + self.assertAlmostEqual(arr1[2],f1.getIJ(i,2),13); + self.assertAlmostEqual(arr1[3],f1.getIJ(i,3),13); + self.assertAlmostEqual(arr1[4],f1.getIJ(i,4),13); + pass + # + f1.sortPerTuple(False); + f1.checkCoherency(); + self.assertEqual(5,f1.getNumberOfComponents()); + self.assertEqual(5,f1.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(arr1[4],f1.getIJ(i,0),13); + self.assertAlmostEqual(arr1[3],f1.getIJ(i,1),13); + self.assertAlmostEqual(arr1[2],f1.getIJ(i,2),13); + self.assertAlmostEqual(arr1[1],f1.getIJ(i,3),13); + self.assertAlmostEqual(arr1[0],f1.getIJ(i,4),13); + pass + # + pass + + def testIsEqualWithoutConsideringStr1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + mesh2=MEDCouplingDataForTest.build2DTargetMesh_1(); + # + self.assertTrue(mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2.setName("rr"); + self.assertTrue(not mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + da1,da2=mesh1.checkGeoEquivalWith(mesh2,2,1e-12); + self.assertRaises(Exception,mesh1.checkGeoEquivalWith,mesh2,0,1e-12); + mesh2.setName(""); + self.assertTrue(mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2.getCoords().setInfoOnComponent(0,"tty"); + self.assertTrue(not mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2.getCoords().setInfoOnComponent(0,""); + self.assertTrue(mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2.getCoords().setInfoOnComponent(1,"tty"); + self.assertTrue(not mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2.getCoords().setInfoOnComponent(1,""); + self.assertTrue(mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + tmp=mesh2.getCoords().getIJ(0,3); + mesh2.getCoords().setIJ(0,3,9999.); + self.assertTrue(not mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(not mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2.getCoords().setIJ(0,3,tmp); + self.assertTrue(mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + tmp2=mesh2.getNodalConnectivity().getIJ(0,4); + mesh2.getNodalConnectivity().setIJ(0,4,0); + self.assertTrue(not mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(not mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + mesh2.getNodalConnectivity().setIJ(0,4,tmp2); + self.assertTrue(mesh1.isEqual(mesh2,1e-12)); + self.assertTrue(mesh1.isEqualWithoutConsideringStr(mesh2,1e-12)); + # + f1=mesh1.getMeasureField(True); + f2=mesh2.getMeasureField(True); + self.assertTrue(f1.isEqual(f2,1e-12,1e-12)); + self.assertTrue(f1.isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + f2.setName("ftest"); + self.assertTrue(not f1.isEqual(f2,1e-12,1e-12)); + self.assertTrue(f1.isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + f1.setName("ftest"); + self.assertTrue(f1.isEqual(f2,1e-12,1e-12)); + self.assertTrue(f1.isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + # + f2.getArray().setInfoOnComponent(0,"eee"); + self.assertTrue(not f1.isEqual(f2,1e-12,1e-12)); + self.assertTrue(f1.isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + f2.getArray().setInfoOnComponent(0,""); + self.assertTrue(f1.isEqual(f2,1e-12,1e-12)); + self.assertTrue(f1.isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + # + f2.getArray().setIJ(1,0,0.123); + self.assertTrue(not f1.isEqual(f2,1e-12,1e-12)); + self.assertTrue(not f1.isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + f2.getArray().setIJ(1,0,0.125); + self.assertTrue(f1.isEqual(f2,1e-12,1e-12)); + self.assertTrue(f1.isEqualWithoutConsideringStr(f2,1e-12,1e-12)); + # + pass + def testGetNodeIdsOfCell1(self): + mesh1=MEDCouplingDataForTest.build2DTargetMesh_1(); + li=mesh1.getNodeIdsOfCell(1) + expected1=[1, 4, 2] + self.assertEqual(expected1,list(li)) + li=mesh1.getCoordinatesOfNode(4) + self.assertEqual(2,len(li)) + self.assertAlmostEqual(0.2,li[0],13); + self.assertAlmostEqual(0.2,li[1],13); + li=mesh1.getCoords().getValuesAsTuple() + self.assertEqual(9,len(li)) + li2=mesh1.getNodalConnectivityIndex().getValuesAsTuple() + self.assertEqual(6,len(li2)) + pass + + def testGetEdgeRatioField1(self): + m1=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=m1.getEdgeRatioField(); + self.assertEqual(m1.getNumberOfCells(),f1.getNumberOfTuples()); + self.assertEqual(5,f1.getNumberOfTuples()); + self.assertEqual(1,f1.getNumberOfComponents()); + expected1=[1.,1.4142135623730951, 1.4142135623730951,1.,1.] + for i in xrange(5): + self.assertAlmostEqual(expected1[i],f1.getIJ(i,0),14); + pass + # + m1=MEDCouplingDataForTest.build3DSurfTargetMesh_1(); + f1=m1.getEdgeRatioField(); + self.assertEqual(m1.getNumberOfCells(),f1.getNumberOfTuples()); + self.assertEqual(5,f1.getNumberOfTuples()); + self.assertEqual(1,f1.getNumberOfComponents()); + expected2=[1.4142135623730951, 1.7320508075688772, 1.7320508075688772, 1.4142135623730951, 1.4142135623730951] + for i in xrange(5): + self.assertAlmostEqual(expected2[i],f1.getIJ(i,0),14); + pass + pass + + def testFillFromAnalytic3(self): + m=MEDCouplingDataForTest.build2DTargetMesh_1() + f1=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME) + self.assertRaises(Exception,f1.fillFromAnalytic,1,"y+x"); + f1.setMesh(m) + f1.setName("myField"); + f1.fillFromAnalytic(1,"y+x"); + f1.checkCoherency(); + self.assertEqual(f1.getName(),"myField"); + self.assertEqual(f1.getTypeOfField(),ON_CELLS); + self.assertEqual(f1.getTimeDiscretization(),ONE_TIME); + self.assertEqual(1,f1.getNumberOfComponents()); + self.assertEqual(5,f1.getNumberOfTuples()); + values1=[-0.1,0.23333333333333336,0.56666666666666665,0.4,0.9] + tmp=f1.getArray().getValues(); + self.assertEqual(len(values1),len(tmp)) + for i in xrange(len(values1)): + self.assertTrue(abs(values1[i]-tmp[i])<1.e-12); + pass + # + f1=MEDCouplingFieldDouble.New(ON_NODES,CONST_ON_TIME_INTERVAL) + f1.setMesh(m) + f1.fillFromAnalytic(1,"y+2*x"); + f1.setEndTime(1.2,3,4); + f1.checkCoherency(); + self.assertEqual(f1.getTypeOfField(),ON_NODES); + self.assertEqual(f1.getTimeDiscretization(),CONST_ON_TIME_INTERVAL); + self.assertEqual(1,f1.getNumberOfComponents()); + self.assertEqual(9,f1.getNumberOfTuples()); + values2=[-0.9,0.1,1.1,-0.4,0.6,1.6,0.1,1.1,2.1] + tmp=f1.getArray().getValues(); + self.assertEqual(len(values2),len(tmp)) + for i in xrange(len(values2)): + self.assertTrue(abs(values2[i]-tmp[i])<1.e-12); + pass + f1=MEDCouplingFieldDouble.New(ON_NODES,LINEAR_TIME); + f1.setMesh(m) + f1.fillFromAnalytic(1,"2.*x+y"); + f1.setEndTime(1.2,3,4); + f1.checkCoherency(); + self.assertEqual(f1.getTypeOfField(),ON_NODES); + self.assertEqual(f1.getTimeDiscretization(),LINEAR_TIME); + self.assertEqual(1,f1.getNumberOfComponents()); + self.assertEqual(9,f1.getNumberOfTuples()); + tmp=f1.getArray().getValues(); + values2Bis=[-0.9,0.1,1.1,-0.4,0.6,1.6,0.1,1.1,2.1] + self.assertEqual(len(values2Bis),len(tmp)) + for i in xrange(len(values2Bis)): + self.assertTrue(abs(values2Bis[i]-tmp[i])<1.e-12); + pass + tmp=f1.getEndArray().getValues(); + self.assertEqual(len(values2Bis),len(tmp)) + for i in xrange(len(values2Bis)): + self.assertTrue(abs(values2Bis[i]-tmp[i])<1.e-12); + pass + # + f1=MEDCouplingFieldDouble.New(ON_NODES,ONE_TIME); + f1.setMesh(m) + f1.fillFromAnalytic(2,"(x+y)*IVec+2*(x+y)*JVec"); + f1.checkCoherency(); + self.assertEqual(f1.getTypeOfField(),ON_NODES); + self.assertEqual(f1.getTimeDiscretization(),ONE_TIME); + self.assertEqual(2,f1.getNumberOfComponents()); + self.assertEqual(9,f1.getNumberOfTuples()); + values3=[-0.6,-1.2,-0.1,-0.2,0.4,0.8,-0.1,-0.2,0.4,0.8,0.9,1.8,0.4,0.8,0.9,1.8,1.4,2.8] + tmp=f1.getArray().getValues(); + self.assertEqual(len(values3),len(tmp)) + for i in xrange(len(values3)): + self.assertTrue(abs(values3[i]-tmp[i])<1.e-12); + pass + values4=f1.accumulate(); + self.assertTrue(abs(3.6-values4[0])<1.e-12); + self.assertTrue(abs(7.2-values4[1])<1.e-12); + values4=f1.integral(True); + self.assertTrue(abs(0.5-values4[0])<1.e-12); + self.assertTrue(abs(1.-values4[1])<1.e-12); + # + f1=MEDCouplingFieldDouble.New(ON_NODES,NO_TIME); + f1.setMesh(m); + self.assertRaises(Exception,f1.fillFromAnalytic,1,"1./(x-0.2)"); + pass + + def testFieldDoubleOpEqual1(self): + m=MEDCouplingDataForTest.build2DTargetMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME); + self.assertRaises(Exception,f1.assign,0.07); + f1.setMesh(m); + f1.assign(0.07); + f1.checkCoherency(); + self.assertEqual(1,f1.getNumberOfComponents()); + self.assertEqual(5,f1.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(0.07,f1.getIJ(i,0),16); + pass + f1.assign(0.09); + f1.checkCoherency(); + self.assertEqual(1,f1.getNumberOfComponents()); + self.assertEqual(5,f1.getNumberOfTuples()); + for i in xrange(5): + self.assertAlmostEqual(0.09,f1.getIJ(i,0),16); + pass + # + f1=MEDCouplingFieldDouble.New(ON_NODES,LINEAR_TIME); + f1.setEndTime(4.5,2,3); + f1.setMesh(m); + f1.assign(0.08); + f1.checkCoherency(); + self.assertEqual(1,f1.getNumberOfComponents()); + self.assertEqual(9,f1.getNumberOfTuples()); + for i in xrange(9): + self.assertAlmostEqual(0.08,f1.getIJ(i,0),16); + pass + self.assertEqual(1,f1.getEndArray().getNumberOfComponents()); + self.assertEqual(9,f1.getEndArray().getNumberOfTuples()); + for i in xrange(9): + self.assertAlmostEqual(0.08,f1.getEndArray().getIJ(i,0),16); + pass + pass + + def testAreaBary3D2(self): + coordsForHexa8=[-75.45749305371, 180.95495078401, 39.515472018008, + -9.755591679144, 23.394927935279, 5.108794294848, + 14.337630157832, 61.705351002702, 160.42422501908, + -27.273893776752, 167.567731083961, 192.830034145464, + 99.857193154796,264.499264735586,-8.287335493412, + 144.939882761126,156.38626563134,-31.896173894226, + 161.34096835726,182.4654895809,73.832387065572, + 132.680430393685,255.37973247196,96.15235602819]; + volHexa8=3258520.29637466; + baryHexa8=[43.925705821778, 155.31893955289, 65.874418109644] + + coordsForPenta6=[-68.199829618726,178.938498373416,62.608505919588, + 8.461744647847,76.653979804423,165.00018874933, + -27.273893776752,167.567731083961,192.830034145464, + 106.586501038965,262.629609408327,13.124533008813, + 155.465082847275,197.414118382622,78.408350795821, + 132.680430393685,255.37973247196,96.15235602819]; + volPenta6=944849.868507338; + baryPenta6=[39.631002313543,182.692711783428,106.98540473964] + + coordsForPyra5=[132.680430393685,255.37973247196,96.15235602819, + -27.273893776752,167.567731083961,192.830034145464, + 8.461744647847,76.653979804423,165.00018874933, + 155.465082847275,197.414118382622,78.408350795821, + -68.199829618726,178.938498373416,62.608505919588]; + volPyra5=756943.92980254; + baryPyra5=[29.204294116618,172.540129749156,118.01035951483] + mesh=MEDCouplingUMesh.New("Bary3D2",3); + coo=DataArrayDouble.New(); + tmp=coordsForHexa8+coordsForPenta6+coordsForPyra5 + coo.setValues(tmp,19,3); + mesh.setCoords(coo); + # + tmpConn=[0,1,2,3,4,5,6,7] + mesh.allocateCells(3); + mesh.insertNextCell(NORM_HEXA8,8,tmpConn[0:8]) + mesh.insertNextCell(NORM_PENTA6,6,[i+8 for i in tmpConn]) + mesh.insertNextCell(NORM_PYRA5,5,[i+14 for i in tmpConn]) + mesh.finishInsertingCells(); + mesh.checkCoherency(); + mesh.mergeNodes(1e-7) + self.assertEqual(12,mesh.getNumberOfNodes()); + vols=mesh.getMeasureField(True); + self.assertEqual(3,vols.getNumberOfTuples()); + self.assertEqual(1,vols.getNumberOfComponents()); + self.assertAlmostEqual(volHexa8,vols.getIJ(0,0),6); + self.assertAlmostEqual(volPenta6,vols.getIJ(1,0),7); + self.assertAlmostEqual(volPyra5,vols.getIJ(2,0),7); + bary=mesh.getBarycenterAndOwner(); + self.assertEqual(3,bary.getNumberOfTuples()); + self.assertEqual(3,bary.getNumberOfComponents()); + self.assertAlmostEqual(baryHexa8[0],bary.getIJ(0,0),11); + self.assertAlmostEqual(baryHexa8[1],bary.getIJ(0,1),11); + self.assertAlmostEqual(baryHexa8[2],bary.getIJ(0,2),11); + self.assertAlmostEqual(baryPenta6[0],bary.getIJ(1,0),11); + self.assertAlmostEqual(baryPenta6[1],bary.getIJ(1,1),11); + self.assertAlmostEqual(baryPenta6[2],bary.getIJ(1,2),11); + self.assertAlmostEqual(baryPyra5[0],bary.getIJ(2,0),11); + self.assertAlmostEqual(baryPyra5[1],bary.getIJ(2,1),11); + self.assertAlmostEqual(baryPyra5[2],bary.getIJ(2,2),11); + pass + + def testGetMeasureFieldCMesh1(self): + m=MEDCouplingCMesh.New(); + da=DataArrayDouble.New(); + discX=[2.3,3.4,5.8,10.2] + discY=[12.3,23.4,45.8] + discZ=[-0.7,1.2,1.25,2.13,2.67] + da.setValues(discX,4,1); + m.setCoordsAt(0,da); + m.checkCoherency(); + self.assertEqual(4,m.getNumberOfNodes()); + self.assertEqual(3,m.getNumberOfCells()); + self.assertEqual(1,m.getSpaceDimension()); + f=m.getMeasureField(True); + self.assertEqual(3,f.getNumberOfTuples()); + self.assertEqual(1,f.getNumberOfComponents()); + expected1=[1.1,2.4,4.4] + for i in xrange(3): + self.assertAlmostEqual(expected1[i],f.getIJ(i,0),12); + pass + coords=m.getCoordinatesAndOwner(); + self.assertEqual(4,coords.getNumberOfTuples()); + self.assertEqual(1,coords.getNumberOfComponents()); + for i in xrange(4): + self.assertAlmostEqual(discX[i],coords.getIJ(i,0),12); + pass + coords=m.getBarycenterAndOwner(); + self.assertEqual(3,coords.getNumberOfTuples()); + self.assertEqual(1,coords.getNumberOfComponents()); + expected1_3=[2.85,4.6,8.] + for i in xrange(3): + self.assertAlmostEqual(expected1_3[i],coords.getIJ(i,0),12); + pass + # + da=DataArrayDouble.New(); + da.setValues(discY,3,1); + m.setCoordsAt(1,da); + m.checkCoherency(); + self.assertEqual(12,m.getNumberOfNodes()); + self.assertEqual(6,m.getNumberOfCells()); + self.assertEqual(2,m.getSpaceDimension()); + f=m.getMeasureField(True); + self.assertEqual(6,f.getNumberOfTuples()); + self.assertEqual(1,f.getNumberOfComponents()); + expected2=[12.21,26.64,48.84,24.64,53.76,98.56] + for i in xrange(6): + self.assertAlmostEqual(expected2[i],f.getIJ(i,0),12); + pass + coords=m.getCoordinatesAndOwner(); + self.assertEqual(12,coords.getNumberOfTuples()); + self.assertEqual(2,coords.getNumberOfComponents()); + expected2_2=[2.3,12.3,3.4,12.3,5.8,12.3,10.2,12.3, 2.3,23.4,3.4,23.4,5.8,23.4,10.2,23.4, 2.3,45.8,3.4,45.8,5.8,45.8,10.2,45.8] + for i in xrange(24): + self.assertAlmostEqual(expected2_2[i],coords.getIJ(0,i),12); + pass + coords=m.getBarycenterAndOwner(); + self.assertEqual(6,coords.getNumberOfTuples()); + self.assertEqual(2,coords.getNumberOfComponents()); + expected2_3=[2.85,17.85,4.6,17.85,8.,17.85, 2.85,34.6,4.6,34.6,8.,34.6] + for i in xrange(12): + self.assertAlmostEqual(expected2_3[i],coords.getIJ(0,i),12); + pass + # + da=DataArrayDouble.New(); + da.setValues(discZ,5,1); + m.setCoordsAt(2,da); + m.checkCoherency(); + self.assertEqual(60,m.getNumberOfNodes()); + self.assertEqual(24,m.getNumberOfCells()); + self.assertEqual(3,m.getSpaceDimension()); + f=m.getMeasureField(True); + self.assertEqual(24,f.getNumberOfTuples()); + self.assertEqual(1,f.getNumberOfComponents()); + expected3=[23.199, 50.616, 92.796, 46.816, 102.144, 187.264, 0.6105, 1.332, 2.442, 1.232, 2.688, 4.928, 10.7448, 23.4432, 42.9792, 21.6832, 47.3088, 86.7328, 6.5934, 14.3856, 26.3736, 13.3056, 29.0304, 53.2224] + for i in xrange(24): + self.assertAlmostEqual(expected3[i],f.getIJ(i,0),12); + pass + coords=m.getCoordinatesAndOwner(); + self.assertEqual(60,coords.getNumberOfTuples()); + self.assertEqual(3,coords.getNumberOfComponents()); + expected3_2=[ + 2.3,12.3,-0.7, 3.4,12.3,-0.7, 5.8,12.3,-0.7, 10.2,12.3,-0.7, 2.3,23.4,-0.7, 3.4,23.4,-0.7, 5.8,23.4,-0.7, 10.2,23.4,-0.7, 2.3,45.8,-0.7, 3.4,45.8,-0.7, 5.8,45.8,-0.7, 10.2,45.8,-0.7, + 2.3,12.3,1.2, 3.4,12.3,1.2, 5.8,12.3,1.2, 10.2,12.3,1.2, 2.3,23.4,1.2, 3.4,23.4,1.2, 5.8,23.4,1.2, 10.2,23.4,1.2, 2.3,45.8,1.2, 3.4,45.8,1.2, 5.8,45.8,1.2, 10.2,45.8,1.2, + 2.3,12.3,1.25, 3.4,12.3,1.25, 5.8,12.3,1.25, 10.2,12.3,1.25, 2.3,23.4,1.25, 3.4,23.4,1.25, 5.8,23.4,1.25, 10.2,23.4,1.25, 2.3,45.8,1.25, 3.4,45.8,1.25, 5.8,45.8,1.25, 10.2,45.8,1.25, + 2.3,12.3,2.13, 3.4,12.3,2.13, 5.8,12.3,2.13, 10.2,12.3,2.13, 2.3,23.4,2.13, 3.4,23.4,2.13, 5.8,23.4,2.13, 10.2,23.4,2.13, 2.3,45.8,2.13, 3.4,45.8,2.13, 5.8,45.8,2.13, 10.2,45.8,2.13, + 2.3,12.3,2.67, 3.4,12.3,2.67, 5.8,12.3,2.67, 10.2,12.3,2.67, 2.3,23.4,2.67, 3.4,23.4,2.67, 5.8,23.4,2.67, 10.2,23.4,2.67, 2.3,45.8,2.67, 3.4,45.8,2.67, 5.8,45.8,2.67, 10.2,45.8,2.67]; + for i in xrange(180): + self.assertAlmostEqual(expected3_2[i],coords.getIJ(0,i),12); + pass + coords=m.getBarycenterAndOwner(); + self.assertEqual(24,coords.getNumberOfTuples()); + self.assertEqual(3,coords.getNumberOfComponents()); + expected3_3=[ + 2.85,17.85,0.25,4.6,17.85,0.25,8.,17.85,0.25, 2.85,34.6,0.25,4.6,34.6,0.25,8.,34.6,0.25, + 2.85,17.85,1.225,4.6,17.85,1.225,8.,17.85,1.225, 2.85,34.6,1.225,4.6,34.6,1.225,8.,34.6,1.225, + 2.85,17.85,1.69,4.6,17.85,1.69,8.,17.85,1.69, 2.85,34.6,1.69,4.6,34.6,1.69,8.,34.6,1.69, + 2.85,17.85,2.4,4.6,17.85,2.4,8.,17.85,2.4, 2.85,34.6,2.4,4.6,34.6,2.4,8.,34.6,2.4]; + for i in xrange(72): + self.assertAlmostEqual(expected3_3[i],coords.getIJ(0,i),12); + pass + pass + + def testFieldDoubleZipCoords1(self): + m=MEDCouplingDataForTest.build2DTargetMeshMergeNode_1(); + f=m.fillFromAnalytic(ON_NODES,2,"x*2."); + f.getArray().setInfoOnComponent(0,"titi"); + f.getArray().setInfoOnComponent(1,"tutu"); + f.checkCoherency(); + self.assertEqual(18,f.getNumberOfTuples()); + self.assertEqual(2,f.getNumberOfComponents()); + expected1=[-0.6, -0.6, 0.4, 0.4, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 1.4, 1.4, -0.6, -0.6, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 1.4, 1.4, 0.4, 0.4] + for i in xrange(36): + self.assertAlmostEqual(expected1[i],f.getIJ(0,i),12); + pass + self.assertTrue(f.zipCoords()); + f.checkCoherency(); + expected2=[-0.6, -0.6, 1.4, 1.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 0.4, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 1.4, 1.4, 1.4, 1.4, -0.6, -0.6, 0.4, 0.4, 1.4, 1.4, 0.4, 0.4] + for i in xrange(30): + self.assertAlmostEqual(expected2[i],f.getIJ(0,i),12); + pass + self.assertTrue(not f.zipCoords()); + f.checkCoherency(); + for i in xrange(30): + self.assertAlmostEqual(expected2[i],f.getIJ(0,i),12); + pass + self.assertTrue(f.getArray().getInfoOnComponent(0)=="titi"); + self.assertTrue(f.getArray().getInfoOnComponent(1)=="tutu"); + pass + + def testFieldDoubleZipConnectivity1(self): + m1=MEDCouplingDataForTest.build2DTargetMesh_1(); + m2=MEDCouplingDataForTest.build2DTargetMesh_1(); + cells1=[2,3,4] + m3_1=m2.buildPartOfMySelf(cells1,True); + m3=m3_1; + m4=MEDCouplingDataForTest.build2DSourceMesh_1(); + m5=MEDCouplingUMesh.mergeUMeshes(m1,m3); + m6=MEDCouplingUMesh.mergeUMeshes(m5,m4); + # + self.assertEqual(10,m6.getNumberOfCells()); + self.assertEqual(22,m6.getNumberOfNodes()); + arr,areNodesMerged,newNbOfNodes=m6.mergeNodes(1e-13); + self.assertEqual(9,m6.getNumberOfNodes()); + f=m6.fillFromAnalytic(ON_CELLS,2,"x"); + f2=m6.fillFromAnalytic(ON_NODES,2,"x"); + self.assertEqual(10,f.getNumberOfTuples()); + self.assertEqual(2,f.getNumberOfComponents()); + expected1=[-0.05, -0.05, 0.3666666666666667, 0.3666666666666667, 0.53333333333333321, 0.53333333333333321, + -0.05, -0.05, 0.45, 0.45, 0.53333333333333321, 0.53333333333333321, -0.05, -0.05, 0.45, 0.45, + 0.36666666666666659, 0.36666666666666659, 0.033333333333333326, 0.033333333333333326]; + for i in xrange(20): + self.assertAlmostEqual(expected1[i],f.getIJ(0,i),12); + pass + f.getArray().setInfoOnComponent(0,"titi"); + f.getArray().setInfoOnComponent(1,"tutu"); + f.checkCoherency(); + self.assertTrue(f.zipConnectivity(0)); + expected2=[-0.05, -0.05, 0.3666666666666667, 0.3666666666666667, 0.53333333333333321, 0.53333333333333321, + -0.05, -0.05, 0.45, 0.45, 0.36666666666666659, 0.36666666666666659, 0.033333333333333326, 0.033333333333333326]; + self.assertEqual(7,f.getNumberOfTuples()); + self.assertEqual(2,f.getNumberOfComponents()); + for i in xrange(14): + self.assertAlmostEqual(expected2[i],f.getIJ(0,i),12); + pass + self.assertTrue(f.getArray().getInfoOnComponent(0)=="titi"); + self.assertTrue(f.getArray().getInfoOnComponent(1)=="tutu"); + self.assertTrue(not f.zipConnectivity(0)); + # + expected3=[-0.3, -0.3, 0.2, 0.2, 0.7, 0.7, -0.3, -0.3, 0.2, 0.2, 0.7, 0.7, + -0.3, -0.3, 0.2, 0.2, 0.7, 0.7]; + self.assertEqual(9,f2.getNumberOfTuples()); + self.assertEqual(2,f2.getNumberOfComponents()); + for i in xrange(18): + self.assertAlmostEqual(expected3[i],f2.getIJ(0,i),12); + pass + self.assertTrue(f2.zipConnectivity(0)); + self.assertEqual(9,f2.getNumberOfTuples()); + self.assertEqual(2,f2.getNumberOfComponents()); + for i in xrange(18): + self.assertAlmostEqual(expected3[i],f2.getIJ(0,i),12); + pass + pass + + def testDaDoubleRenumber1(self): + a=DataArrayDouble.New(); + arr1=[1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1] + a.setValues(arr1,7,2); + a.setInfoOnComponent(0,"toto"); + a.setInfoOnComponent(1,"tata"); + # + arr2=[3,1,0,6,5,4,2] + b=a.renumber(arr2); + self.assertEqual(7,b.getNumberOfTuples()); + self.assertEqual(2,b.getNumberOfComponents()); + self.assertTrue(b.getInfoOnComponent(0)=="toto"); + self.assertTrue(b.getInfoOnComponent(1)=="tata"); + expected1=[3.1, 13.1, 2.1, 12.1, 7.1, 17.1, 1.1, 11.1, 6.1, 16.1, 5.1, 15.1, 4.1, 14.1] + for i in xrange(14): + self.assertAlmostEqual(expected1[i],b.getIJ(0,i),14); + pass + # + c=DataArrayInt.New(); + arr3=[1,11,2,12,3,13,4,14,5,15,6,16,7,17] + c.setValues(arr3,7,2); + c.setInfoOnComponent(0,"toto"); + c.setInfoOnComponent(1,"tata"); + d=c.renumber(arr2); + self.assertEqual(7,d.getNumberOfTuples()); + self.assertEqual(2,d.getNumberOfComponents()); + self.assertTrue(d.getInfoOnComponent(0)=="toto"); + self.assertTrue(d.getInfoOnComponent(1)=="tata"); + expected2=[3, 13, 2, 12, 7, 17, 1, 11, 6, 16, 5, 15, 4, 14] + for i in xrange(14): + self.assertEqual(expected2[i],d.getIJ(0,i)); + pass + pass + + def testDaDoubleRenumberAndReduce1(self): + a=DataArrayDouble.New(); + arr1=[1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1] + a.setValues(arr1,7,2); + a.setInfoOnComponent(0,"toto"); + a.setInfoOnComponent(1,"tata"); + # + arr2=[2,-1,1,-1,0,4,3] + b=a.renumberAndReduce(arr2,5); + self.assertEqual(5,b.getNumberOfTuples()); + self.assertEqual(2,b.getNumberOfComponents()); + self.assertTrue(b.getInfoOnComponent(0)=="toto"); + self.assertTrue(b.getInfoOnComponent(1)=="tata"); + expected1=[5.1,15.1,3.1,13.1,1.1,11.1,7.1,17.1,6.1,16.1] + for i in xrange(10): + self.assertAlmostEqual(expected1[i],b.getIJ(0,i),14); + pass + # + c=DataArrayInt.New(); + arr3=[1,11,2,12,3,13,4,14,5,15,6,16,7,17] + c.setValues(arr3,7,2); + c.setInfoOnComponent(0,"toto"); + c.setInfoOnComponent(1,"tata"); + d=c.renumberAndReduce(arr2,5); + self.assertEqual(5,d.getNumberOfTuples()); + self.assertEqual(2,d.getNumberOfComponents()); + self.assertTrue(d.getInfoOnComponent(0)=="toto"); + self.assertTrue(d.getInfoOnComponent(1)=="tata"); + expected2=[5,15,3,13,1,11,7,17,6,16] + for i in xrange(10): + self.assertEqual(expected2[i],d.getIJ(0,i)); + pass + pass + + def testDaDoubleRenumberInPlace1(self): + a=DataArrayDouble.New(); + arr1=[1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1] + a.setValues(arr1,7,2); + # + arr2=[3,1,0,6,5,4,2] + a.renumberInPlace(arr2); + self.assertEqual(7,a.getNumberOfTuples()); + self.assertEqual(2,a.getNumberOfComponents()); + expected1=[3.1, 13.1, 2.1, 12.1, 7.1, 17.1, 1.1, 11.1, 6.1, 16.1, 5.1, 15.1, 4.1, 14.1] + for i in xrange(14): + self.assertAlmostEqual(expected1[i],a.getIJ(0,i),14); + pass + # + c=DataArrayInt.New(); + arr3=[1,11,2,12,3,13,4,14,5,15,6,16,7,17] + c.setValues(arr3,7,2); + c.renumberInPlace(arr2); + self.assertEqual(7,c.getNumberOfTuples()); + self.assertEqual(2,c.getNumberOfComponents()); + expected2=[3, 13, 2, 12, 7, 17, 1, 11, 6, 16, 5, 15, 4, 14] + for i in xrange(14): + self.assertEqual(expected2[i],c.getIJ(0,i)); + pass + pass + + def testDaDoubleRenumberR1(self): + a=DataArrayDouble.New(); + arr1=[1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1] + a.setValues(arr1,7,2); + a.setInfoOnComponent(0,"toto"); + a.setInfoOnComponent(1,"tata"); + # + arr2=[3,1,0,6,5,4,2] + b=a.renumberR(arr2); + self.assertEqual(7,b.getNumberOfTuples()); + self.assertEqual(2,b.getNumberOfComponents()); + self.assertTrue(b.getInfoOnComponent(0)=="toto"); + self.assertTrue(b.getInfoOnComponent(1)=="tata"); + expected1=[4.1, 14.1, 2.1, 12.1, 1.1, 11.1, 7.1, 17.1, 6.1, 16.1, 5.1, 15.1, 3.1, 13.1] + for i in xrange(14): + self.assertAlmostEqual(expected1[i],b.getIJ(0,i),14); + pass + # + c=DataArrayInt.New(); + arr3=[1,11,2,12,3,13,4,14,5,15,6,16,7,17] + c.setValues(arr3,7,2); + c.setInfoOnComponent(0,"toto"); + c.setInfoOnComponent(1,"tata"); + d=c.renumberR(arr2); + self.assertEqual(7,d.getNumberOfTuples()); + self.assertEqual(2,d.getNumberOfComponents()); + self.assertTrue(d.getInfoOnComponent(0)=="toto"); + self.assertTrue(d.getInfoOnComponent(1)=="tata"); + expected2=[4, 14, 2, 12, 1, 11, 7, 17, 6, 16, 5, 15, 3, 13] + for i in xrange(14): + self.assertEqual(expected2[i],d.getIJ(0,i)); + pass + pass + + def testDaDoubleRenumberInPlaceR1(self): + a=DataArrayDouble.New(); + arr1=[1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1] + a.setValues(arr1,7,2); + # + arr2=[3,1,0,6,5,4,2] + a.renumberInPlaceR(arr2); + self.assertEqual(7,a.getNumberOfTuples()); + self.assertEqual(2,a.getNumberOfComponents()); + expected1=[4.1, 14.1, 2.1, 12.1, 1.1, 11.1, 7.1, 17.1, 6.1, 16.1, 5.1, 15.1, 3.1, 13.1] + for i in xrange(14): + self.assertAlmostEqual(expected1[i],a.getIJ(0,i),14); + pass + # + c=DataArrayInt.New(); + arr3=[1,11,2,12,3,13,4,14,5,15,6,16,7,17] + c.setValues(arr3,7,2); + c.renumberInPlaceR(arr2); + self.assertEqual(7,c.getNumberOfTuples()); + self.assertEqual(2,c.getNumberOfComponents()); + expected2=[4, 14, 2, 12, 1, 11, 7, 17, 6, 16, 5, 15, 3, 13] + for i in xrange(14): + self.assertEqual(expected2[i],c.getIJ(0,i)); + pass + pass + + def testDaDoubleSelectByTupleId1(self): + a=DataArrayDouble.New(); + arr1=[1.1,11.1,2.1,12.1,3.1,13.1,4.1,14.1,5.1,15.1,6.1,16.1,7.1,17.1] + a.setValues(arr1,7,2); + a.setInfoOnComponent(0,"toto"); + a.setInfoOnComponent(1,"tata"); + # + arr2=[4,2,0,6,5] + b=a.selectByTupleId(arr2); + self.assertEqual(5,b.getNumberOfTuples()); + self.assertEqual(2,b.getNumberOfComponents()); + self.assertTrue(b.getInfoOnComponent(0)=="toto"); + self.assertTrue(b.getInfoOnComponent(1)=="tata"); + expected1=[5.1,15.1,3.1,13.1,1.1,11.1,7.1,17.1,6.1,16.1] + for i in xrange(10): + self.assertAlmostEqual(expected1[i],b.getIJ(0,i),14); + pass + # + c=DataArrayInt.New(); + arr3=[1,11,2,12,3,13,4,14,5,15,6,16,7,17] + c.setValues(arr3,7,2); + c.setInfoOnComponent(0,"toto"); + c.setInfoOnComponent(1,"tata"); + d=c.selectByTupleId(arr2); + self.assertEqual(5,d.getNumberOfTuples()); + self.assertEqual(2,d.getNumberOfComponents()); + self.assertTrue(d.getInfoOnComponent(0)=="toto"); + self.assertTrue(d.getInfoOnComponent(1)=="tata"); + expected2=[5,15,3,13,1,11,7,17,6,16] + for i in xrange(10): + self.assertEqual(expected2[i],d.getIJ(0,i)); + pass + pass + + def testDaDoubleGetMinMaxValues1(self): + a=DataArrayDouble.New(); + arr1=[2.34,4.56,-6.77,4.55,4.56,2.24,2.34,1.02,4.56] + a.setValues(arr1,9,1); + m,where=a.getMaxValue(); + self.assertEqual(1,where); + self.assertAlmostEqual(4.56,m,12); + m,ws=a.getMaxValue2(); + self.assertAlmostEqual(4.56,m,12); + self.assertEqual(3,ws.getNumberOfTuples()); + self.assertEqual(1,ws.getNumberOfComponents()); + expected1=[1,4,8] + for i in xrange(3): + self.assertEqual(expected1[i],ws.getIJ(i,0)); + pass + a=DataArrayDouble.New(); + arr2=[-2.34,-4.56,6.77,-4.55,-4.56,-2.24,-2.34,-1.02,-4.56] + a.setValues(arr2,9,1); + m,where=a.getMinValue(); + self.assertEqual(1,where); + self.assertAlmostEqual(-4.56,m,12); + m,ws=a.getMinValue2(); + self.assertAlmostEqual(-4.56,m,12); + self.assertEqual(3,ws.getNumberOfTuples()); + self.assertEqual(1,ws.getNumberOfComponents()); + for i in xrange(3): + self.assertEqual(expected1[i],ws.getIJ(i,0)); + pass + pass + + def testFieldDoubleGetMinMaxValues2(self): + m2,m1=MEDCouplingDataForTest.build3DExtrudedUMesh_1(); + self.assertEqual(18,m2.getNumberOfCells()); + arr1=[8.71,4.53,-12.41,8.71,-8.71,8.7099,4.55,8.71,5.55,6.77,-1e-200,4.55,8.7099,0.,1.23,0.,2.22,8.71] + f=MEDCouplingFieldDouble.New(ON_CELLS,NO_TIME); + a=DataArrayDouble.New(); + a.setValues(arr1,18,1); + f.setArray(a); + f.setMesh(m2); + # + f.checkCoherency(); + m=f.getMaxValue(); + self.assertAlmostEqual(8.71,m,12); + m,ws=f.getMaxValue2(); + self.assertAlmostEqual(8.71,m,12); + self.assertEqual(4,ws.getNumberOfTuples()); + self.assertEqual(1,ws.getNumberOfComponents()); + expected1=[0,3,7,17] + for i in xrange(4): + self.assertEqual(expected1[i],ws.getIJ(i,0)); + pass + # + arr2=[-8.71,-4.53,12.41,-8.71,8.71,-8.7099,-4.55,-8.71,-5.55,-6.77,1e-200,-4.55,-8.7099,0.,-1.23,0.,-2.22,-8.71] + a.setValues(arr2,18,1); + f.checkCoherency(); + m=f.getMinValue(); + self.assertAlmostEqual(-8.71,m,12); + m,ws=f.getMinValue2(); + self.assertAlmostEqual(-8.71,m,12); + self.assertEqual(4,ws.getNumberOfTuples()); + self.assertEqual(1,ws.getNumberOfComponents()); + for i in xrange(4): + self.assertEqual(expected1[i],ws.getIJ(i,0)); + pass + pass + + def testBuildUnstructuredCMesh1(self): + m=MEDCouplingCMesh.New(); + da=DataArrayDouble.New(); + discX=[2.3,3.4,5.8,10.2] + discY=[12.3,23.4,45.8] + discZ=[-0.7,1.2,1.25,2.13,2.67] + da.setValues(discX,4,1); + m.setCoordsAt(0,da); + m.checkCoherency(); + self.assertEqual(0,m.getCellContainingPoint([2.4],12)); + self.assertEqual(1,m.getCellContainingPoint([3.7],12)); + self.assertEqual(2,m.getCellContainingPoint([5.9],12)); + self.assertEqual(-1,m.getCellContainingPoint([10.3],12)); + self.assertEqual(-1,m.getCellContainingPoint([1.3],12)); + # + m2=m.buildUnstructured(); + m2.checkCoherency(); + f1=m.getMeasureField(False); + f2=m2.getMeasureField(False); + self.assertEqual(f1.getNumberOfTuples(),3); + self.assertEqual(f2.getNumberOfTuples(),3); + self.assertEqual(1,m2.getMeshDimension()); + self.assertEqual(1,m2.getSpaceDimension()); + for i in xrange(3): + self.assertAlmostEqual(f1.getIJ(i,0),f2.getIJ(i,0),10); + pass + da=DataArrayDouble.New(); + da.setValues(discY,3,1); + m.setCoordsAt(1,da); + # + m2=m.buildUnstructured(); + m2.checkCoherency(); + f1=m.getMeasureField(False); + f2=m2.getMeasureField(False); + self.assertEqual(f1.getNumberOfTuples(),6); + self.assertEqual(f2.getNumberOfTuples(),6); + self.assertEqual(2,m2.getMeshDimension()); + self.assertEqual(2,m2.getSpaceDimension()); + for i in xrange(6): + self.assertAlmostEqual(f1.getIJ(i,0),f2.getIJ(i,0),10); + pass + # + da=DataArrayDouble.New(); + da.setValues(discZ,5,1); + m.setCoordsAt(2,da); + m2=m.buildUnstructured(); + m2.checkCoherency(); + f1=m.getMeasureField(False); + f2=m2.getMeasureField(False); + self.assertEqual(f1.getNumberOfTuples(),24); + self.assertEqual(f2.getNumberOfTuples(),24); + self.assertEqual(3,m2.getMeshDimension()); + self.assertEqual(3,m2.getSpaceDimension()); + for i in xrange(24): + self.assertAlmostEqual(f1.getIJ(i,0),f2.getIJ(i,0),10); + pass + # + pos1=[5.,30.,2.] + self.assertEqual(16,m.getCellContainingPoint(pos1,1e-12)); + # + pt=[2.4,12.7,-3.4] + m.scale(pt,3.7); + m3=m.buildUnstructured(); + m2.scale(pt,3.7); + self.assertTrue(m3.isEqual(m2,1e-12)); + pass + + def testDataArrayIntInvertO2NNO21(self): + arr1=[2,0,4,1,5,3] + da=DataArrayInt.New(); + da.setValues(arr1,6,1); + da2=da.invertArrayO2N2N2O(6); + self.assertEqual(6,da2.getNumberOfTuples()); + self.assertEqual(1,da2.getNumberOfComponents()); + expected1=[1,3,0,5,2,4] + for i in xrange(6): + self.assertEqual(expected1[i],da2.getIJ(i,0)); + pass + da3=da2.invertArrayN2O2O2N(6); + for i in xrange(6): + self.assertEqual(arr1[i],da3.getIJ(i,0)); + pass + # + arr2=[3,-1,5,4,-1,0,-1,1,2,-1] + da=DataArrayInt.New(); + da.setValues(arr2,10,1); + da2=da.invertArrayO2N2N2O(6); + self.assertEqual(6,da2.getNumberOfTuples()); + self.assertEqual(1,da2.getNumberOfComponents()); + expected2=[5,7,8,0,3,2] + for i in xrange(6): + self.assertEqual(expected2[i],da2.getIJ(i,0)); + pass + da3=da2.invertArrayN2O2O2N(10); + for i in xrange(10): + self.assertEqual(arr2[i],da3.getIJ(i,0)); + pass pass def testDoublyContractedProduct1(self): diff --git a/src/MEDCoupling_Swig/MEDCouplingTypemaps.i b/src/MEDCoupling_Swig/MEDCouplingTypemaps.i index 5bc13876d..b5d9b2a29 100644 --- a/src/MEDCoupling_Swig/MEDCouplingTypemaps.i +++ b/src/MEDCoupling_Swig/MEDCouplingTypemaps.i @@ -17,6 +17,10 @@ // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com // +#ifdef WITH_NUMPY2 +#include +#endif + static PyObject* convertMesh(ParaMEDMEM::MEDCouplingMesh* mesh, int owner) { PyObject *ret; @@ -29,19 +33,46 @@ static PyObject* convertMesh(ParaMEDMEM::MEDCouplingMesh* mesh, int owner) static PyObject *convertIntArrToPyList(const int *ptr, int size) { +#ifndef WITH_NUMPY2 PyObject *ret=PyList_New(size); for(int i=0;i(tmp)); +#endif } static PyObject *convertIntArrToPyList2(const std::vector& v) { +#ifndef WITH_NUMPY2 int size=v.size(); PyObject *ret=PyList_New(size); for(int i=0;i& arr) } else { - PyErr_SetString(PyExc_TypeError,"convertPyToNewIntArr : not a list"); +#ifndef WITH_NUMPY2 + PyErr_SetString(PyExc_TypeError,"convertPyToNewIntArr3 : not a list"); PyErr_Print(); + return ; +#else + if(PyArray_Check(pyLi)) + { + npy_intp mySize = PyArray_SIZE(pyLi); + int *ret=(int *)PyArray_BYTES(pyLi); + arr.resize(mySize); + std::copy(ret,ret+mySize,arr.begin()); + return ; + } + else + { + PyErr_SetString(PyExc_TypeError,"convertPyToNewIntArr3 : not a list nor PyArray"); + PyErr_Print(); + return ; + } +#endif } } @@ -112,6 +177,28 @@ static PyObject *convertDblArrToPyList(const double *ptr, int size) return ret; } +static PyObject *convertDblArrToPyList2(const std::vector& v) +{ + int size=v.size(); + PyObject *ret=PyList_New(size); + for(int i=0;idecrRef();" %feature("unref") MEDCouplingPointSet "$this->decrRef();" %feature("unref") MEDCouplingMesh "$this->decrRef();" @@ -145,7 +167,7 @@ using namespace INTERP_KERNEL; %feature("unref") MEDCouplingField "$this->decrRef();" %feature("unref") MEDCouplingFieldDouble "$this->decrRef();" -%ignore ParaMEDMEM::TimeLabel::operator=; +%rename(assign) *::operator=; %ignore ParaMEDMEM::MemArray::operator=; %ignore ParaMEDMEM::MemArray::operator[]; %ignore ParaMEDMEM::MEDCouplingPointSet::getCoords(); @@ -153,6 +175,7 @@ using namespace INTERP_KERNEL; %ignore ParaMEDMEM::MEDCouplingGaussLocalization::pushTinySerializationDblInfo; %ignore ParaMEDMEM::MEDCouplingGaussLocalization::fillWithValues; %ignore ParaMEDMEM::MEDCouplingGaussLocalization::buildNewInstanceFromTinyInfo; + %rename (Exception) InterpKernelException; %nodefaultctor; @@ -192,6 +215,7 @@ namespace ParaMEDMEM virtual MEDCouplingMeshType getType() const = 0; bool isStructured() const; virtual bool isEqual(const MEDCouplingMesh *other, double prec) const; + virtual bool isEqualWithoutConsideringStr(const MEDCouplingMesh *other, double prec) const = 0; virtual void copyTinyStringsFrom(const MEDCouplingMesh *other) throw(INTERP_KERNEL::Exception); virtual void checkCoherency() const throw(INTERP_KERNEL::Exception) = 0; virtual int getNumberOfCells() const throw(INTERP_KERNEL::Exception) = 0; @@ -203,13 +227,10 @@ namespace ParaMEDMEM virtual INTERP_KERNEL::NormalizedCellType getTypeOfCell(int cellId) const = 0; virtual std::string simpleRepr() const = 0; virtual std::string advancedRepr() const = 0; - virtual void getNodeIdsOfCell(int cellId, std::vector& conn) const = 0; - virtual void getCoordinatesOfNode(int nodeId, std::vector& coo) const = 0; // tools virtual void getBoundingBox(double *bbox) const = 0; virtual MEDCouplingFieldDouble *getMeasureField(bool isAbs) const = 0; virtual MEDCouplingFieldDouble *getMeasureFieldOnNode(bool isAbs) const = 0; - virtual int getCellContainingPoint(const double *pos, double eps) const = 0; virtual MEDCouplingFieldDouble *fillFromAnalytic(TypeOfField t, int nbOfComp, const char *func) const throw(INTERP_KERNEL::Exception); virtual MEDCouplingFieldDouble *buildOrthogonalField() const = 0; virtual void rotate(const double *center, const double *vector, double angle) = 0; @@ -225,6 +246,15 @@ namespace ParaMEDMEM return self->simpleRepr(); } + int getCellContainingPoint(PyObject *p, double eps) const + { + int sz; + double *pos=convertPyToNewDblArr2(p,&sz); + int ret=self->getCellContainingPoint(pos,eps); + delete [] pos; + return ret; + } + void renumberCells(PyObject *li, bool check) throw(INTERP_KERNEL::Exception) { int size; @@ -242,6 +272,35 @@ namespace ParaMEDMEM PyList_SetItem(res,1,SWIG_NewPointerObj(SWIG_as_voidptr(nodeCor),SWIGTYPE_p_ParaMEDMEM__DataArrayInt, nodeCor?SWIG_POINTER_OWN | 0:0 )); return res; } + DataArrayInt *getCellIdsFullyIncludedInNodeIds(PyObject *li) const + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + DataArrayInt *ret=self->getCellIdsFullyIncludedInNodeIds(tmp,tmp+size); + delete [] tmp; + return ret; + } + PyObject *getNodeIdsOfCell(int cellId) const + { + std::vector conn; + self->getNodeIdsOfCell(cellId,conn); + return convertIntArrToPyList2(conn); + } + + PyObject *getCoordinatesOfNode(int nodeId) const + { + std::vector coo; + self->getCoordinatesOfNode(nodeId,coo); + return convertDblArrToPyList2(coo); + } + + void scale(PyObject *point, double factor) + { + int sz; + double *p=convertPyToNewDblArr2(point,&sz); + self->scale(p,factor); + delete [] p; + } } }; } @@ -260,13 +319,11 @@ namespace ParaMEDMEM void updateTime(); void setCoords(DataArrayDouble *coords); DataArrayDouble *getCoordinatesAndOwner() const; - bool isEqual(const MEDCouplingMesh *other, double prec) const; bool areCoordsEqual(const MEDCouplingPointSet& other, double prec) const; void getBoundingBox(double *bbox) const; void zipCoords(); double getCaracteristicDimension() const; void translate(const double *vector); - void scale(const double *point, double factor); void changeSpaceDimension(int newSpaceDim, double dftVal=0.) throw(INTERP_KERNEL::Exception); void tryToShareSameCoords(const MEDCouplingPointSet& other, double epsilon) throw(INTERP_KERNEL::Exception); virtual void tryToShareSameCoordsPermute(const MEDCouplingPointSet& other, double epsilon) throw(INTERP_KERNEL::Exception) = 0; @@ -294,10 +351,10 @@ namespace ParaMEDMEM return self->simpleRepr(); } - PyObject *buildNewNumberingFromCommNodesFrmt(const DataArrayInt *comm, const DataArrayInt *commIndex) const + PyObject *buildNewNumberingFromCommonNodesFormat(const DataArrayInt *comm, const DataArrayInt *commIndex) const { int newNbOfNodes; - DataArrayInt *ret0=self->buildNewNumberingFromCommNodesFrmt(comm,commIndex,newNbOfNodes); + DataArrayInt *ret0=self->buildNewNumberingFromCommonNodesFormat(comm,commIndex,newNbOfNodes); PyObject *res = PyList_New(2); PyList_SetItem(res,0,SWIG_NewPointerObj(SWIG_as_voidptr(ret0),SWIGTYPE_p_ParaMEDMEM__DataArrayInt, SWIG_POINTER_OWN | 0 )); PyList_SetItem(res,1,SWIG_From_int(newNbOfNodes)); @@ -348,7 +405,7 @@ namespace ParaMEDMEM { std::vector nodes; self->findBoundaryNodes(nodes); - return convertIntArrToPyList(&nodes[0],nodes.size()); + return convertIntArrToPyList2(nodes); } void rotate(PyObject *center, PyObject *vector, double alpha) { @@ -370,13 +427,6 @@ namespace ParaMEDMEM self->translate(v); delete [] v; } - void scale(PyObject *point, double factor) - { - int sz; - double *p=convertPyToNewDblArr2(point,&sz); - self->scale(p,factor); - delete [] p; - } void renumberNodes(PyObject *li, int newNbOfNodes) { int size; @@ -449,21 +499,17 @@ namespace ParaMEDMEM MEDCouplingUMesh *buildDescendingConnectivity(DataArrayInt *desc, DataArrayInt *descIndx, DataArrayInt *revDesc, DataArrayInt *revDescIndx) const; void orientCorrectlyPolyhedrons() throw(INTERP_KERNEL::Exception); bool isPresenceOfQuadratic() const; + MEDCouplingFieldDouble *buildDirectionVectorField() const; void convertQuadraticCellsToLinear() throw(INTERP_KERNEL::Exception); + MEDCouplingFieldDouble *getEdgeRatioField() const throw(INTERP_KERNEL::Exception); + MEDCouplingFieldDouble *getAspectRatioField() const throw(INTERP_KERNEL::Exception); + MEDCouplingFieldDouble *getWarpField() const throw(INTERP_KERNEL::Exception); + MEDCouplingFieldDouble *getSkewField() const throw(INTERP_KERNEL::Exception); %extend { std::string __str__() const { return self->simpleRepr(); } - - int getCellContainingPoint(PyObject *p, double eps) const - { - int sz; - double *pos=convertPyToNewDblArr2(p,&sz); - int ret=self->getCellContainingPoint(pos,eps); - delete [] pos; - return ret; - } void insertNextCell(INTERP_KERNEL::NormalizedCellType type, int size, PyObject *li) { int sz; @@ -525,11 +571,11 @@ namespace ParaMEDMEM return ret; } - DataArrayInt *getRenumArrForConsctvCellTypesSpe(PyObject *li) const + DataArrayInt *getRenumArrForConsecutiveCellTypesSpec(PyObject *li) const { int sz; INTERP_KERNEL::NormalizedCellType *order=(INTERP_KERNEL::NormalizedCellType *)convertPyToNewIntArr2(li,&sz); - DataArrayInt *ret=self->getRenumArrForConsctvCellTypesSpe(order,order+sz); + DataArrayInt *ret=self->getRenumArrForConsecutiveCellTypesSpec(order,order+sz); delete [] order; return ret; } @@ -639,6 +685,17 @@ namespace ParaMEDMEM self->arePolyhedronsNotCorrectlyOriented(cells); return convertIntArrToPyList2(cells); } + + PyObject *getFastAveragePlaneOfThis() const throw(INTERP_KERNEL::Exception) + { + double vec[3]; + double pos[3]; + self->getFastAveragePlaneOfThis(vec,pos); + double vals[6]; + std::copy(vec,vec+3,vals); + std::copy(pos,pos+3,vals+3); + return convertDblArrToPyListOfTuple(vals,3,2); + } } void convertToPolyTypes(const std::vector& cellIdsToConvert); MEDCouplingUMesh *buildExtrudedMeshFromThis(const MEDCouplingUMesh *mesh1D, int policy); @@ -684,6 +741,7 @@ namespace ParaMEDMEM DataArrayDouble *coordsY=0, DataArrayDouble *coordsZ=0); void setCoordsAt(int i, DataArrayDouble *arr) throw(INTERP_KERNEL::Exception); + MEDCouplingUMesh *buildUnstructured() const; %extend { std::string __str__() const { @@ -712,6 +770,131 @@ namespace ParaMEDMEM const double *vals=self->getPointer(); return convertDblArrToPyList(vals,self->getNbOfElems()); } + + PyObject *getValuesAsTuple() + { + const double *vals=self->getPointer(); + int nbOfComp=self->getNumberOfComponents(); + int nbOfTuples=self->getNumberOfTuples(); + return convertDblArrToPyListOfTuple(vals,nbOfComp,nbOfTuples); + } + + DataArrayDouble *renumber(PyObject *li) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + DataArrayDouble *ret=self->renumber(tmp); + delete [] tmp; + return ret; + } + + DataArrayDouble *renumberR(PyObject *li) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + DataArrayDouble *ret=self->renumberR(tmp); + delete [] tmp; + return ret; + } + + DataArrayDouble *renumberAndReduce(PyObject *li, int newNbOfTuple) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + DataArrayDouble *ret=self->renumberAndReduce(tmp,newNbOfTuple); + delete [] tmp; + return ret; + } + + void renumberInPlace(PyObject *li) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + self->renumberInPlace(tmp); + delete [] tmp; + } + + void renumberInPlaceR(PyObject *li) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + self->renumberInPlaceR(tmp); + delete [] tmp; + } + + DataArrayDouble *selectByTupleId(PyObject *li) const + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + DataArrayDouble *ret=self->selectByTupleId(tmp,tmp+size); + delete [] tmp; + return ret; + } + + PyObject *getMaxValue() const throw(INTERP_KERNEL::Exception) + { + int tmp; + double r1=self->getMaxValue(tmp); + PyObject *ret=PyTuple_New(2); + PyTuple_SetItem(ret,0,PyFloat_FromDouble(r1)); + PyTuple_SetItem(ret,1,PyInt_FromLong(tmp)); + return ret; + } + + PyObject *getMaxValue2() const throw(INTERP_KERNEL::Exception) + { + DataArrayInt *tmp; + double r1=self->getMaxValue2(tmp); + PyObject *ret=PyTuple_New(2); + PyTuple_SetItem(ret,0,PyFloat_FromDouble(r1)); + PyTuple_SetItem(ret,1,SWIG_NewPointerObj(SWIG_as_voidptr(tmp),SWIGTYPE_p_ParaMEDMEM__DataArrayInt, SWIG_POINTER_OWN | 0 )); + return ret; + } + + PyObject *getMinValue() const throw(INTERP_KERNEL::Exception) + { + int tmp; + double r1=self->getMinValue(tmp); + PyObject *ret=PyTuple_New(2); + PyTuple_SetItem(ret,0,PyFloat_FromDouble(r1)); + PyTuple_SetItem(ret,1,PyInt_FromLong(tmp)); + return ret; + } + + PyObject *getMinValue2() const throw(INTERP_KERNEL::Exception) + { + DataArrayInt *tmp; + double r1=self->getMinValue2(tmp); + PyObject *ret=PyTuple_New(2); + PyTuple_SetItem(ret,0,PyFloat_FromDouble(r1)); + PyTuple_SetItem(ret,1,SWIG_NewPointerObj(SWIG_as_voidptr(tmp),SWIGTYPE_p_ParaMEDMEM__DataArrayInt, SWIG_POINTER_OWN | 0 )); + return ret; + } }; %extend ParaMEDMEM::DataArrayInt @@ -734,6 +917,14 @@ namespace ParaMEDMEM return convertIntArrToPyList(vals,self->getNbOfElems()); } + PyObject *getValuesAsTuple() + { + const int *vals=self->getPointer(); + int nbOfComp=self->getNumberOfComponents(); + int nbOfTuples=self->getNumberOfTuples(); + return convertIntArrToPyListOfTuple(vals,nbOfComp,nbOfTuples); + } + static PyObject *makePartition(PyObject *gps, int newNb) { std::vector groups; @@ -749,6 +940,83 @@ namespace ParaMEDMEM PyList_SetItem(ret,1,ret1); return ret; } + + void renumberInPlace(PyObject *li) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + self->renumberInPlace(tmp); + delete [] tmp; + } + + void renumberInPlaceR(PyObject *li) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + self->renumberInPlaceR(tmp); + delete [] tmp; + } + + DataArrayInt *renumberAndReduce(PyObject *li, int newNbOfTuple) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + DataArrayInt *ret=self->renumberAndReduce(tmp,newNbOfTuple); + delete [] tmp; + return ret; + } + + DataArrayInt *renumber(PyObject *li) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + DataArrayInt *ret=self->renumber(tmp); + delete [] tmp; + return ret; + } + + DataArrayInt *renumberR(PyObject *li) throw(INTERP_KERNEL::Exception) + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + if(size!=self->getNumberOfTuples()) + { + throw INTERP_KERNEL::Exception("Invalid list length ! Must be equal to number of tuples !"); + delete [] tmp; + } + DataArrayInt *ret=self->renumberR(tmp); + delete [] tmp; + return ret; + } + + DataArrayInt *selectByTupleId(PyObject *li) const + { + int size; + int *tmp=convertPyToNewIntArr2(li,&size); + DataArrayInt *ret=self->selectByTupleId(tmp,tmp+size); + delete [] tmp; + return ret; + } }; namespace ParaMEDMEM @@ -759,13 +1027,14 @@ namespace ParaMEDMEM virtual void checkCoherency() const throw(INTERP_KERNEL::Exception); virtual bool areCompatibleForMerge(const MEDCouplingField *other) const; virtual bool isEqual(const MEDCouplingField *other, double meshPrec, double valsPrec) const; + virtual bool isEqualWithoutConsideringStr(const MEDCouplingField *other, double meshPrec, double valsPrec) const; void setMesh(const ParaMEDMEM::MEDCouplingMesh *mesh); void setName(const char *name); const char *getDescription() const; void setDescription(const char *desc); const char *getName() const; TypeOfField getTypeOfField() const; - MEDCouplingFieldDouble *buildWeightingField(bool isAbs) const throw(INTERP_KERNEL::Exception); + MEDCouplingFieldDouble *buildMeasureField(bool isAbs) const throw(INTERP_KERNEL::Exception); MEDCouplingFieldDiscretization *getDiscretization() const; void setGaussLocalizationOnType(INTERP_KERNEL::NormalizedCellType type, const std::vector& refCoo, const std::vector& gsCoo, const std::vector& wg) throw(INTERP_KERNEL::Exception); @@ -850,6 +1119,8 @@ namespace ParaMEDMEM void changeUnderlyingMesh(const MEDCouplingMesh *other, int levOfCheck, double prec) throw(INTERP_KERNEL::Exception); void substractInPlaceDM(const MEDCouplingFieldDouble *f, int levOfCheck, double prec) throw(INTERP_KERNEL::Exception); bool mergeNodes(double eps) throw(INTERP_KERNEL::Exception); + bool zipCoords() throw(INTERP_KERNEL::Exception); + bool zipConnectivity(int compType) throw(INTERP_KERNEL::Exception); MEDCouplingFieldDouble *doublyContractedProduct() const throw(INTERP_KERNEL::Exception); MEDCouplingFieldDouble *determinant() const throw(INTERP_KERNEL::Exception); MEDCouplingFieldDouble *eigenValues() const throw(INTERP_KERNEL::Exception); @@ -861,6 +1132,8 @@ namespace ParaMEDMEM MEDCouplingFieldDouble *maxPerTuple() const throw(INTERP_KERNEL::Exception); void changeNbOfComponents(int newNbOfComp, double dftValue=0.) throw(INTERP_KERNEL::Exception); void sortPerTuple(bool asc) throw(INTERP_KERNEL::Exception); + MEDCouplingFieldDouble &operator=(double value) throw(INTERP_KERNEL::Exception); + void fillFromAnalytic(int nbOfComp, const char *func) throw(INTERP_KERNEL::Exception); void applyFunc(int nbOfComp, const char *func) throw(INTERP_KERNEL::Exception); void applyFunc(const char *func) throw(INTERP_KERNEL::Exception); void applyFuncFast32(const char *func) throw(INTERP_KERNEL::Exception); @@ -986,7 +1259,7 @@ namespace ParaMEDMEM } PyObject *accumulate() const { - int sz=self->getNumberOfTuples(); + int sz=self->getNumberOfComponents(); double *tmp=new double[sz]; self->accumulate(tmp); PyObject *ret=convertDblArrToPyList(tmp,sz); @@ -995,7 +1268,7 @@ namespace ParaMEDMEM } PyObject *integral(bool isWAbs) const { - int sz=self->getNumberOfTuples(); + int sz=self->getNumberOfComponents(); double *tmp=new double[sz]; self->integral(isWAbs,tmp); PyObject *ret=convertDblArrToPyList(tmp,sz); @@ -1004,7 +1277,7 @@ namespace ParaMEDMEM } PyObject *normL1() const throw(INTERP_KERNEL::Exception) { - int sz=self->getNumberOfTuples(); + int sz=self->getNumberOfComponents(); double *tmp=new double[sz]; self->normL1(tmp); PyObject *ret=convertDblArrToPyList(tmp,sz); @@ -1013,7 +1286,7 @@ namespace ParaMEDMEM } PyObject *normL2() const throw(INTERP_KERNEL::Exception) { - int sz=self->getNumberOfTuples(); + int sz=self->getNumberOfComponents(); double *tmp=new double[sz]; self->normL2(tmp); PyObject *ret=convertDblArrToPyList(tmp,sz); @@ -1069,6 +1342,26 @@ namespace ParaMEDMEM delete [] tmp; return ret; } + + PyObject *getMaxValue2() const throw(INTERP_KERNEL::Exception) + { + DataArrayInt *tmp; + double r1=self->getMaxValue2(tmp); + PyObject *ret=PyTuple_New(2); + PyTuple_SetItem(ret,0,PyFloat_FromDouble(r1)); + PyTuple_SetItem(ret,1,SWIG_NewPointerObj(SWIG_as_voidptr(tmp),SWIGTYPE_p_ParaMEDMEM__DataArrayInt, SWIG_POINTER_OWN | 0 )); + return ret; + } + + PyObject *getMinValue2() const throw(INTERP_KERNEL::Exception) + { + DataArrayInt *tmp; + double r1=self->getMinValue2(tmp); + PyObject *ret=PyTuple_New(2); + PyTuple_SetItem(ret,0,PyFloat_FromDouble(r1)); + PyTuple_SetItem(ret,1,SWIG_NewPointerObj(SWIG_as_voidptr(tmp),SWIGTYPE_p_ParaMEDMEM__DataArrayInt, SWIG_POINTER_OWN | 0 )); + return ret; + } } }; } diff --git a/src/MEDLoader/MEDLoader.cxx b/src/MEDLoader/MEDLoader.cxx index b8b61edc9..1c08abd94 100644 --- a/src/MEDLoader/MEDLoader.cxx +++ b/src/MEDLoader/MEDLoader.cxx @@ -348,6 +348,57 @@ std::vector MEDLoader::GetMeshNames(const char *fileName) throw(INT return ret; } +std::vector MEDLoader::GetMeshNamesOnField(const char *fileName, const char *fieldName) throw(INTERP_KERNEL::Exception) +{ + CheckFileForRead(fileName); + std::vector ret; + med_idt fid=MEDouvrir((char *)fileName,MED_LECTURE); + med_int nbFields=MEDnChamp(fid,0); + // + med_type_champ typcha; + //med_int nbpdtnor=0,pflsize,*pflval,lnsize; + med_int ngauss=0; + med_int numdt=0,numo=0,nbrefmaa; + med_float dt=0.0; + med_booleen local; + //char pflname[MED_TAILLE_NOM+1]=""; + //char locname[MED_TAILLE_NOM+1]=""; + char *maa_ass=MEDLoaderBase::buildEmptyString(MED_TAILLE_NOM); + char *dt_unit=MEDLoaderBase::buildEmptyString(MED_TAILLE_PNOM); + char *nomcha=MEDLoaderBase::buildEmptyString(MED_TAILLE_NOM); + // + for(int i=0;i MEDLoader::GetMeshFamiliesNames(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception) { CheckFileForRead(fileName); @@ -407,6 +458,178 @@ std::vector MEDLoader::GetMeshGroupsNames(const char *fileName, con MEDfermer(fid); return ret; } +std::vector MEDLoader::GetTypesOfField(const char *fileName, const char *fieldName, const char *meshName) throw(INTERP_KERNEL::Exception) +{ + CheckFileForRead(fileName); + std::vector ret; + med_idt fid=MEDouvrir((char *)fileName,MED_LECTURE); + med_int nbFields=MEDnChamp(fid,0); + // + med_type_champ typcha; + //med_int nbpdtnor=0,pflsize,*pflval,lnsize; + med_int ngauss=0; + med_int numdt=0,numo=0,nbrefmaa; + med_float dt=0.0; + med_booleen local; + //char pflname[MED_TAILLE_NOM+1]=""; + //char locname[MED_TAILLE_NOM+1]=""; + char *maa_ass=MEDLoaderBase::buildEmptyString(MED_TAILLE_NOM); + char *dt_unit=MEDLoaderBase::buildEmptyString(MED_TAILLE_PNOM); + char *nomcha=MEDLoaderBase::buildEmptyString(MED_TAILLE_NOM); + // + for(int i=0;i0) + { + bool found=false; + for(int i=0;i0) + { + MEDpasdetempsInfo(fid,nomcha,MED_MAILLE,typmai[j],1, &ngauss, &numdt, &numo, dt_unit,&dt, maa_ass, &local, &nbrefmaa); + std::string curMeshName=MEDLoaderBase::buildStringFromFortran(maa_ass,MED_TAILLE_NOM+1); + if(curMeshName==meshName) + { + found=true; + ret.push_back(ON_CELLS); + } + } + } + } + } + delete [] maa_ass; + delete [] dt_unit; + delete [] nomcha; + MEDfermer(fid); + return ret; +} + +std::vector MEDLoader::GetAllFieldNames(const char *fileName) throw(INTERP_KERNEL::Exception) +{ + CheckFileForRead(fileName); + std::vector ret; + med_idt fid=MEDouvrir((char *)fileName,MED_LECTURE); + med_int nbFields=MEDnChamp(fid,0); + med_type_champ typcha; + for(int i=0;i MEDLoader::GetAllFieldNamesOnMesh(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception) +{ + CheckFileForRead(fileName); + std::vector ret; + med_idt fid=MEDouvrir((char *)fileName,MED_LECTURE); + med_int nbFields=MEDnChamp(fid,0); + // + med_type_champ typcha; + //med_int nbpdtnor=0,pflsize,*pflval,lnsize; + med_int ngauss=0; + med_int numdt=0,numo=0,nbrefmaa; + med_float dt=0.0; + med_booleen local; + //char pflname[MED_TAILLE_NOM+1]=""; + //char locname[MED_TAILLE_NOM+1]=""; + char *maa_ass=MEDLoaderBase::buildEmptyString(MED_TAILLE_NOM); + char *dt_unit=MEDLoaderBase::buildEmptyString(MED_TAILLE_PNOM); + char *nomcha=MEDLoaderBase::buildEmptyString(MED_TAILLE_NOM); + // + for(int i=0;i0) + { + for(int i=0;i0) + { + MEDpasdetempsInfo(fid,nomcha,MED_MAILLE,typmai[j],1, &ngauss, &numdt, &numo, dt_unit,&dt, maa_ass, &local, &nbrefmaa); + std::string curMeshName=MEDLoaderBase::buildStringFromFortran(maa_ass,MED_TAILLE_NOM+1); + if(curMeshName==meshName) + { + found=true; + ret.push_back(curFieldName); + } + } + } + } + delete [] maa_ass; + delete [] dt_unit; + delete [] nomcha; + MEDfermer(fid); + return ret; +} + +std::vector MEDLoader::GetFieldNamesOnMesh(ParaMEDMEM::TypeOfField type, const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception) +{ + CheckFileForRead(fileName); + switch(type) + { + case ON_CELLS: + return GetCellFieldNamesOnMesh(fileName,meshName); + case ON_NODES: + return GetNodeFieldNamesOnMesh(fileName,meshName); + default: + throw INTERP_KERNEL::Exception("Type of field specified not managed ! manages are ON_NODES or ON_CELLS !"); + } +} std::vector MEDLoader::GetCellFieldNamesOnMesh(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception) { @@ -515,7 +738,7 @@ std::vector< std::pair > MEDLoader::GetFieldIterations(ParaMEDMEM::Type return GetNodeFieldIterations(fileName,meshName,fieldName); default: throw INTERP_KERNEL::Exception("Type of field specified not managed ! manages are ON_NODES or ON_CELLS !"); - } + } } std::vector< std::pair > MEDLoader::GetCellFieldIterations(const char *fileName, const char *meshName, const char *fieldName) throw(INTERP_KERNEL::Exception) @@ -617,6 +840,11 @@ std::vector< std::pair > MEDLoader::GetNodeFieldIterations(const char * return ret; } +/*! + * This method reads all the content of a field 'fieldName' at a time specified by (iteration,order) lying on a mesh 'meshName' with a specified type 'TypeOfOutField' + * The returned values are strored in 'field' (sorted by type of cell), time corresponding to field, and 'infos' to load properly little strings. + * The principle of this method is to put into 'field' only data that fulfills \b perfectly request. + */ void MEDLoaderNS::readFieldDoubleDataInMedFile(const char *fileName, const char *meshName, const char *fieldName, int iteration, int order, ParaMEDMEM::TypeOfField typeOfOutField, std::list& field, @@ -1416,6 +1644,7 @@ ParaMEDMEM::MEDCouplingFieldDouble *MEDLoaderNS::readFieldDoubleLev2(const char MEDLoaderNS::keepSpecifiedMeshDim(fieldPerCellType,meshDim); //for profiles ParaMEDMEM::MEDCouplingUMesh *newMesh=0; + std::string mName(mesh->getName()); for(std::list::const_iterator iter=fieldPerCellType.begin();iter!=fieldPerCellType.end();iter++) { const std::vector& cellIds=(*iter).getCellIdPerType(); @@ -1424,10 +1653,60 @@ ParaMEDMEM::MEDCouplingFieldDouble *MEDLoaderNS::readFieldDoubleLev2(const char std::vector ci(cellIds.size()); std::transform(cellIds.begin(),cellIds.end(),ci.begin(),std::bind2nd(std::plus(),-1)); ParaMEDMEM::MEDCouplingUMesh *mesh2; - if(newMesh) - mesh2=newMesh->keepSpecifiedCells((*iter).getType(),ci); - else - mesh2=mesh->keepSpecifiedCells((*iter).getType(),ci); + if(typeOfOutField==ON_CELLS) + { + if(newMesh) + mesh2=newMesh->keepSpecifiedCells((*iter).getType(),ci); + else + mesh2=mesh->keepSpecifiedCells((*iter).getType(),ci); + } + else if(typeOfOutField==ON_NODES) + { + DataArrayInt *da=0,*da2=0; + if(newMesh) + { + if((int)ci.size()!=newMesh->getNumberOfNodes()) + { + da=newMesh->getCellIdsFullyIncludedInNodeIds(&ci[0],&ci[ci.size()]); + mesh2=dynamic_cast(newMesh->buildPartAndReduceNodes(da->getConstPointer(),da->getConstPointer()+da->getNbOfElems(),da2)); + } + } + else + { + if((int)ci.size()!=mesh->getNumberOfNodes()) + { + da=mesh->getCellIdsFullyIncludedInNodeIds(&ci[0],&ci[ci.size()]); + mesh2=dynamic_cast(mesh->buildPartAndReduceNodes(da->getConstPointer(),da->getConstPointer()+da->getNbOfElems(),da2)); + // + int nnodes=mesh2->getNumberOfNodes(); + DataArrayInt *da3=DataArrayInt::New(); + const int *da2Ptr=da2->getConstPointer(); + da3->alloc(nnodes,1); + int *da3Ptr=da3->getPointer(); + for(int i=0;i<(int)ci.size();i++) + { + int val=da2Ptr[ci[i]]; + if(val!=-1) + da3Ptr[val]=i; + } + mesh2->renumberNodes(da3->getConstPointer(),nnodes); + da3->decrRef(); + } + else + { + mesh2=mesh->clone(true); + da=DataArrayInt::New(); + da->alloc((int)ci.size(),1); + std::copy(ci.begin(),ci.end(),da->getPointer()); + da2=da->invertArrayO2N2N2O(ci.size()); + mesh2->renumberNodes(da2->getConstPointer(),(int)ci.size()); + } + } + if(da) + da->decrRef(); + if(da2) + da2->decrRef(); + } if(newMesh) newMesh->decrRef(); newMesh=mesh2; @@ -1439,6 +1718,7 @@ ParaMEDMEM::MEDCouplingFieldDouble *MEDLoaderNS::readFieldDoubleLev2(const char ret->setTime(time,iteration,order); if(newMesh) { + newMesh->setName(mName.c_str());//retrieving mesh name to avoid renaming due to mesh restriction in case of profile. ret->setMesh(newMesh); newMesh->decrRef(); } @@ -1818,11 +2098,25 @@ void MEDLoaderNS::writeUMeshesPartitionDirectly(const char *fileName, const char */ void MEDLoaderNS::appendNodeProfileField(const char *fileName, const ParaMEDMEM::MEDCouplingFieldDouble *f, const int *thisMeshNodeIds) { - //not implemented yet. med_int numdt,numo; med_float dt; - //int nbComp=f->getNumberOfComponents(); + char *nommaa=MEDLoaderBase::buildEmptyString(MED_TAILLE_NOM); + MEDLoaderBase::safeStrCpy(f->getMesh()->getName(),MED_TAILLE_NOM,nommaa,MEDLoader::_TOO_LONG_STR); med_idt fid=appendFieldSimpleAtt(fileName,f,numdt,numo,dt); + int nbOfNodes=f->getMesh()->getNumberOfNodes(); + const double *pt=f->getArray()->getConstPointer(); + int *profile=new int[nbOfNodes]; + std::ostringstream oss; oss << "Pfln" << f->getName(); + char *profileName=MEDLoaderBase::buildEmptyString(MED_TAILLE_NOM); + MEDLoaderBase::safeStrCpy(oss.str().c_str(),MED_TAILLE_NOM,profileName,MEDLoader::_TOO_LONG_STR); + std::transform(thisMeshNodeIds,thisMeshNodeIds+nbOfNodes,profile,std::bind2nd(std::plus(),1)); + MEDprofilEcr(fid,profile,nbOfNodes,profileName); + delete [] profile; + MEDchampEcr(fid,nommaa,(char *)f->getName(),(unsigned char*)pt,MED_FULL_INTERLACE,nbOfNodes, + (char *)MED_NOGAUSS,MED_ALL,profileName,MED_COMPACT,MED_NOEUD, + MED_NONE,numdt,(char *)"",dt,numo); + delete [] profileName; + delete [] nommaa; MEDfermer(fid); } @@ -1911,7 +2205,7 @@ void MEDLoaderNS::appendFieldDirectly(const char *fileName, const ParaMEDMEM::ME if(renum) { ParaMEDMEM::MEDCouplingFieldDouble *f3=f2->clone(true); - DataArrayInt *da=meshC->getRenumArrForConsctvCellTypesSpe(typmai2,typmai2+MED_NBR_GEOMETRIE_MAILLE+2); + DataArrayInt *da=meshC->getRenumArrForConsecutiveCellTypesSpec(typmai2,typmai2+MED_NBR_GEOMETRIE_MAILLE+2); f3->renumberCells(da->getConstPointer(),false); da->decrRef(); f=f3; @@ -2044,7 +2338,7 @@ void MEDLoaderNS::writeFieldAndMeshDirectly(const char *fileName, const ParaMEDM if(isRenumbering) { ParaMEDMEM::MEDCouplingFieldDouble *f2=f->clone(true); - DataArrayInt *da=mesh->getRenumArrForConsctvCellTypesSpe(typmai2,typmai2+MED_NBR_GEOMETRIE_MAILLE+2); + DataArrayInt *da=mesh->getRenumArrForConsecutiveCellTypesSpec(typmai2,typmai2+MED_NBR_GEOMETRIE_MAILLE+2); f2->renumberCells(da->getConstPointer(),false); da->decrRef(); appendFieldDirectly(fileName,f2); @@ -2297,6 +2591,9 @@ void MEDLoader::WriteUMeshes(const char *fileName, const std::vectorgetName()); + if(meshName.empty()) + throw INTERP_KERNEL::Exception("Trying to write a unstructured mesh with no name ! MED file format needs a not empty mesh name : change name of first element of 2nd parameter !"); DataArrayDouble *coords=meshes.front()->getCoords(); for(std::vector::const_iterator iter=meshes.begin();iter!=meshes.end();iter++) if(coords!=(*iter)->getCoords()) diff --git a/src/MEDLoader/MEDLoader.hxx b/src/MEDLoader/MEDLoader.hxx index f302c023c..d262c04a3 100644 --- a/src/MEDLoader/MEDLoader.hxx +++ b/src/MEDLoader/MEDLoader.hxx @@ -87,8 +87,13 @@ class MEDLOADER_EXPORT MEDLoader static void setTooLongStrPolicy(int val) throw(INTERP_KERNEL::Exception); static void CheckFileForRead(const char *fileName) throw(INTERP_KERNEL::Exception); static std::vector GetMeshNames(const char *fileName) throw(INTERP_KERNEL::Exception); + static std::vector GetMeshNamesOnField(const char *fileName, const char *fieldName) throw(INTERP_KERNEL::Exception); static std::vector GetMeshGroupsNames(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); static std::vector GetMeshFamiliesNames(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); + static std::vector GetAllFieldNames(const char *fileName) throw(INTERP_KERNEL::Exception); + static std::vector GetAllFieldNamesOnMesh(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); + static std::vector GetTypesOfField(const char *fileName, const char *fieldName, const char *meshName) throw(INTERP_KERNEL::Exception); + static std::vector GetFieldNamesOnMesh(ParaMEDMEM::TypeOfField type, const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); static std::vector GetCellFieldNamesOnMesh(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); static std::vector GetNodeFieldNamesOnMesh(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); static std::vector< std::pair > GetFieldIterations(ParaMEDMEM::TypeOfField type, const char *fileName, const char *meshName, const char *fieldName) throw(INTERP_KERNEL::Exception); diff --git a/src/MEDLoader/MEDLoaderBase.cxx b/src/MEDLoader/MEDLoaderBase.cxx index 057c2869d..14c33ac1e 100644 --- a/src/MEDLoader/MEDLoaderBase.cxx +++ b/src/MEDLoader/MEDLoaderBase.cxx @@ -31,38 +31,17 @@ int MEDLoaderBase::getStatusOfFile(const char *fileName) { std::ifstream ifs; ifs.open(fileName); - unsigned int res=0; if((ifs.rdstate() & std::ifstream::failbit)!=0) { - res+=1; ifs.close(); + return NOT_EXIST; } std::ofstream ofs(fileName,std::ios_base::app); if((ofs.rdstate() & std::ofstream::failbit)!=0) { - ofs.close(); - res+=2; - } - switch(res) - { - case 0: - return EXIST_RW; - case 1: - { - std::ifstream ifs2; - ifs2.open(fileName); - if((ifs2.rdstate() & std::ifstream::failbit)!=0) - return EXIST_WRONLY; - else - return NOT_EXIST; - } - case 2: return EXIST_RDONLY; - case 3: - return DIR_LOCKED; - default: - throw INTERP_KERNEL::Exception("Internal error !"); } + return EXIST_RW; } char *MEDLoaderBase::buildEmptyString(int lgth) diff --git a/src/MEDLoader/Makefile.am b/src/MEDLoader/Makefile.am index 939523c30..3a2fbb760 100755 --- a/src/MEDLoader/Makefile.am +++ b/src/MEDLoader/Makefile.am @@ -41,12 +41,11 @@ MEDLoader.hxx MEDLoaderBase.hxx dist_libmedloader_la_SOURCES= \ MEDLoader.cxx MEDLoaderBase.cxx -libmedloader_la_CPPFLAGS= $(MPI_INCLUDES) $(MED2_INCLUDES) $(HDF5_INCLUDES) @CXXTMPDPTHFLAGS@ \ +libmedloader_la_CPPFLAGS= $(MED2_INCLUDES) $(HDF5_INCLUDES) @CXXTMPDPTHFLAGS@ \ -I$(srcdir)/../INTERP_KERNEL \ -I$(srcdir)/../INTERP_KERNEL/Geometric2D \ -I$(srcdir)/../INTERP_KERNEL/Bases \ -I$(srcdir)/../MEDCoupling -# change motivated by the bug KERNEL4778. libmedloader_la_LDFLAGS= ../MEDCoupling/libmedcoupling.la \ -../INTERP_KERNEL/libinterpkernel.la $(MPI_LIBS) $(MED2_LIBS) $(HDF5_LIBS) +../INTERP_KERNEL/libinterpkernel.la $(MED2_LIBS) $(HDF5_LIBS) diff --git a/src/MEDLoader/Swig/MEDLoaderTest.py b/src/MEDLoader/Swig/MEDLoaderTest.py index 1b1103bed..e0c9a080a 100644 --- a/src/MEDLoader/Swig/MEDLoaderTest.py +++ b/src/MEDLoader/Swig/MEDLoaderTest.py @@ -150,6 +150,10 @@ class MEDLoaderTest(unittest.TestCase): f1.setTime(10.55,28,29); f1.getArray().setIJ(0,0,3*VAL1); MEDLoader.WriteField(fileName,f1,False); + vec=MEDLoader.GetMeshNamesOnField(fileName,name1); + self.assertEqual(2,len(vec)); + self.assertTrue(vec[0]==name3); + self.assertTrue(vec[1]==name2); f1.setTime(10.66,38,39); f1.getArray().setIJ(0,0,3*VAL2); MEDLoader.WriteFieldUsingAlreadyWrittenMesh(fileName,f1); @@ -387,6 +391,152 @@ class MEDLoaderTest(unittest.TestCase): f2=MEDLoader.ReadFieldCell(fileName,f1.getMesh().getName(),-1,f1.getName(),2,7); self.assertTrue(f2.isEqual(f1,1e-12,1e-12)); pass + + def testFieldNodeProfilRW1(self): + fileName="Pyfile19.med"; + fileName2="Pyfile20.med"; + m=MEDLoaderDataForTest.build2DMesh_1(); + nbOfNodes=m.getNumberOfNodes(); + MEDLoader.WriteUMesh(fileName,m,True); + f1=MEDCouplingFieldDouble.New(ON_NODES,ONE_TIME); + f1.setName("VFieldOnNodes"); + f1.setMesh(m); + array=DataArrayDouble.New(); + arr1=[1.,101.,2.,102.,3.,103.,4.,104.,5.,105.,6.,106.,7.,107.,8.,108.,9.,109.,10.,110.,11.,111.,12.,112.] + array.setValues(arr1,nbOfNodes,2); + f1.setArray(array); + array.setInfoOnComponent(0,"tyty (mm)"); + array.setInfoOnComponent(1,"uiop (MW)"); + f1.setTime(3.14,2,7); + f1.checkCoherency(); + arr2=[2,4,5,3,6,7] + f2=f1.buildSubPart(arr2); + f2.getMesh().setName(f1.getMesh().getName()); + MEDLoader.WriteField(fileName,f2,False);#<- False important for the test + # + f3=MEDLoader.ReadFieldNode(fileName,f2.getMesh().getName(),0,f2.getName(),2,7); + f3.checkCoherency(); + self.assertTrue(f3.isEqual(f2,1e-12,1e-12)); + # + arr3=[1,3,0,5,2,4] + f2.renumberNodes(arr3); + MEDLoader.WriteUMesh(fileName2,m,True); + MEDLoader.WriteField(fileName2,f2,False);#<- False important for the test + f3=MEDLoader.ReadFieldNode(fileName2,f2.getMesh().getName(),0,f2.getName(),2,7); + f3.checkCoherency(); + self.assertTrue(f3.isEqual(f2,1e-12,1e-12)); + # + pass + + def testFieldNodeProfilRW2(self): + fileName="Pyfile23.med"; + mesh=MEDLoaderDataForTest.build3DSurfMesh_1(); + MEDLoader.WriteUMesh(fileName,mesh,True); + # + f1=MEDCouplingFieldDouble.New(ON_NODES,ONE_TIME); + f1.setName("FieldMix"); + f1.setMesh(mesh); + arr2=[1071.,1171.,1010.,1110.,1020.,1120.,1030.,1130.,1040.,1140.,1050.,1150., + 1060.,1160.,1070.,1170.,1080.,1180.,1090.,1190.,1091.,1191.,1092.,1192.]; + array=DataArrayDouble.New(); + array.setValues(arr2,12,2); + f1.setArray(array); + array.setInfoOnComponent(0,"plkj (mm)"); + array.setInfoOnComponent(1,"pqqqss (mm)"); + tmp=array.getPointer(); + f1.setTime(3.17,2,7); + # + renumArr=[3,7,2,1,5,11,10,0,9,6,8,4] + f1.renumberNodes(renumArr); + f1.checkCoherency(); + MEDLoader.WriteField(fileName,f1,False);#<- False important for the test + f2=MEDLoader.ReadFieldNode(fileName,f1.getMesh().getName(),0,f1.getName(),2,7); + self.assertTrue(f2.isEqual(f1,1e-12,1e-12)); + # + pass + + def testMixCellAndNodesFieldRW1(self): + fileName="Pyfile21.med"; + mesh=MEDLoaderDataForTest.build3DSurfMesh_1(); + f1=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME); + f1.setName("FieldMix"); + f1.setMesh(mesh); + array=DataArrayDouble.New(); + f1.setArray(array); + arr1=[71.,171.,10.,110.,20.,120.,30.,130.,40.,140.,50.,150.] + array.setValues(arr1,6,2); + array.setInfoOnComponent(0,"plkj (mm)"); + array.setInfoOnComponent(1,"pqqqss (mm)"); + f1.setTime(3.14,2,7); + f1.checkCoherency(); + # + f2=MEDCouplingFieldDouble.New(ON_NODES,ONE_TIME); + f2.setName("FieldMix"); + f2.setMesh(mesh); + array=DataArrayDouble.New(); + f2.setArray(array); + arr2=[1071.,1171.,1010.,1110.,1020.,1120.,1030.,1130.,1040.,1140.,1050.,1150., + 1060.,1160.,1070.,1170.,1080.,1180.,1090.,1190.,1091.,1191.,1092.,1192.] + array.setValues(arr2,12,2) + array.setInfoOnComponent(0,"plkj (mm)"); + array.setInfoOnComponent(1,"pqqqss (mm)"); + f2.setTime(3.17,2,7); + f2.checkCoherency(); + # + MEDLoader.WriteField(fileName,f1,True); + ts=MEDLoader.GetTypesOfField(fileName,f1.getName(),f1.getMesh().getName()); + self.assertEqual(1,len(ts)); + self.assertEqual(ON_CELLS,ts[0]); + fs=MEDLoader.GetAllFieldNamesOnMesh(fileName,f1.getMesh().getName()); + self.assertEqual(1,len(fs)); + self.assertTrue(fs[0]=="FieldMix"); + MEDLoader.WriteFieldUsingAlreadyWrittenMesh(fileName,f2); + fs=MEDLoader.GetAllFieldNamesOnMesh(fileName,f1.getMesh().getName()); + self.assertEqual(1,len(fs)); + self.assertTrue(fs[0]=="FieldMix"); + # + ts=MEDLoader.GetTypesOfField(fileName,f1.getName(),f1.getMesh().getName()); + self.assertEqual(2,len(ts)); + self.assertEqual(ON_NODES,ts[0]); + self.assertEqual(ON_CELLS,ts[1]); + # + f3=MEDLoader.ReadFieldNode(fileName,f1.getMesh().getName(),0,f1.getName(),2,7); + self.assertTrue(f3.isEqual(f2,1e-12,1e-12)); + f3=MEDLoader.ReadFieldCell(fileName,f1.getMesh().getName(),0,f1.getName(),2,7); + self.assertTrue(f3.isEqual(f1,1e-12,1e-12)); + # + pass + + def testGetAllFieldNamesRW1(self): + fileName="Pyfile22.med"; + mesh=MEDLoaderDataForTest.build2DMesh_2(); + f1=MEDCouplingFieldDouble.New(ON_NODES,ONE_TIME); + f1.setName("Field1"); + f1.setTime(3.44,5,6); + f1.setMesh(mesh); + f1.fillFromAnalytic(2,"x+y"); + MEDLoader.WriteField(fileName,f1,True); + f1.setTime(1002.3,7,8); + f1.fillFromAnalytic(2,"x+77.*y"); + MEDLoader.WriteFieldUsingAlreadyWrittenMesh(fileName,f1); + f1.setName("Field2"); + MEDLoader.WriteField(fileName,f1,False); + f1.setName("Field3"); + mesh.setName("2DMesh_2Bis"); + MEDLoader.WriteField(fileName,f1,False); + f1=MEDCouplingFieldDouble.New(ON_CELLS,ONE_TIME); + f1.setName("Field8"); + f1.setTime(8.99,7,9); + f1.setMesh(mesh); + f1.fillFromAnalytic(3,"3*x+y"); + MEDLoader.WriteField(fileName,f1,False); + fs=MEDLoader.GetAllFieldNames(fileName); + self.assertEqual(4,len(fs)); + self.assertTrue(fs[0]=="Field1"); + self.assertTrue(fs[1]=="Field2"); + self.assertTrue(fs[2]=="Field3"); + self.assertTrue(fs[3]=="Field8"); + pass pass unittest.main() diff --git a/src/MEDLoader/Swig/libMEDLoader_Swig.i b/src/MEDLoader/Swig/libMEDLoader_Swig.i index 37648ec84..ddf0c24c0 100644 --- a/src/MEDLoader/Swig/libMEDLoader_Swig.i +++ b/src/MEDLoader/Swig/libMEDLoader_Swig.i @@ -50,8 +50,12 @@ public: static void setTooLongStrPolicy(int val) throw(INTERP_KERNEL::Exception); static void CheckFileForRead(const char *fileName) throw(INTERP_KERNEL::Exception); static std::vector GetMeshNames(const char *fileName) throw(INTERP_KERNEL::Exception); + static std::vector GetMeshNamesOnField(const char *fileName, const char *fieldName) throw(INTERP_KERNEL::Exception); static std::vector GetMeshGroupsNames(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); static std::vector GetMeshFamiliesNames(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); + static std::vector GetAllFieldNamesOnMesh(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); + static std::vector GetAllFieldNames(const char *fileName) throw(INTERP_KERNEL::Exception); + static std::vector GetFieldNamesOnMesh(ParaMEDMEM::TypeOfField type, const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); static std::vector GetCellFieldNamesOnMesh(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); static std::vector GetNodeFieldNamesOnMesh(const char *fileName, const char *meshName) throw(INTERP_KERNEL::Exception); %extend @@ -122,6 +126,15 @@ public: std::vector v2(v.begin(),v.end()); MEDLoader::WriteUMeshes(fileName,v2,writeFromScratch); } + static PyObject *GetTypesOfField(const char *fileName, const char *fieldName, const char *meshName) throw(INTERP_KERNEL::Exception) + { + std::vector< ParaMEDMEM::TypeOfField > v=MEDLoader::GetTypesOfField(fileName,fieldName,meshName); + int size=v.size(); + PyObject *ret=PyList_New(size); + for(int i=0;i& fams) throw(INTERP_KERNEL::Exception); static ParaMEDMEM::MEDCouplingUMesh *ReadUMeshFromGroups(const char *fileName, const char *meshName, int meshDimRelToMax, const std::vector& grps) throw(INTERP_KERNEL::Exception); diff --git a/src/MEDLoader/Test/MEDLoaderTest.cxx b/src/MEDLoader/Test/MEDLoaderTest.cxx index 7c3451419..6dadebf48 100644 --- a/src/MEDLoader/Test/MEDLoaderTest.cxx +++ b/src/MEDLoader/Test/MEDLoaderTest.cxx @@ -193,6 +193,10 @@ void MEDLoaderTest::testFieldRW3() f1->setTime(10.55,28,29); tmp[0]=3*VAL1; MEDLoader::WriteField(fileName,f1,false); + std::vector vec=MEDLoader::GetMeshNamesOnField(fileName,name1); + CPPUNIT_ASSERT_EQUAL(2,(int)vec.size()); + CPPUNIT_ASSERT(vec[0]==name3); + CPPUNIT_ASSERT(vec[1]==name2); f1->setTime(10.66,38,39); tmp[0]=3*VAL2; MEDLoader::WriteFieldUsingAlreadyWrittenMesh(fileName,f1); @@ -372,6 +376,85 @@ void MEDLoaderTest::testFieldProfilRW1() mesh2->decrRef(); } +void MEDLoaderTest::testFieldNodeProfilRW1() +{ + const char fileName[]="file19.med"; + const char fileName2[]="file20.med"; + MEDCouplingUMesh *m=build2DMesh_1(); + int nbOfNodes=m->getNumberOfNodes(); + MEDLoader::WriteUMesh(fileName,m,true); + MEDCouplingFieldDouble *f1=MEDCouplingFieldDouble::New(ON_NODES,ONE_TIME); + f1->setName("VFieldOnNodes"); + f1->setMesh(m); + DataArrayDouble *array=DataArrayDouble::New(); + const double arr1[24]={1.,101.,2.,102.,3.,103.,4.,104.,5.,105.,6.,106.,7.,107.,8.,108.,9.,109.,10.,110.,11.,111.,12.,112.}; + array->alloc(nbOfNodes,2); + std::copy(arr1,arr1+24,array->getPointer()); + f1->setArray(array); + array->setInfoOnComponent(0,"tyty (mm)"); + array->setInfoOnComponent(1,"uiop (MW)"); + array->decrRef(); + f1->setTime(3.14,2,7); + f1->checkCoherency(); + const int arr2[6]={2,4,5,3,6,7}; + MEDCouplingFieldDouble *f2=f1->buildSubPart(arr2,arr2+6); + ((MEDCouplingMesh *)f2->getMesh())->setName(f1->getMesh()->getName()); + MEDLoader::WriteField(fileName,f2,false);//<- false important for the test + // + MEDCouplingFieldDouble *f3=MEDLoader::ReadFieldNode(fileName,f2->getMesh()->getName(),0,f2->getName(),2,7); + f3->checkCoherency(); + CPPUNIT_ASSERT(f3->isEqual(f2,1e-12,1e-12)); + f3->decrRef(); + // + const int arr3[6]={1,3,0,5,2,4}; + f2->renumberNodes(arr3); + MEDLoader::WriteUMesh(fileName2,m,true); + MEDLoader::WriteField(fileName2,f2,false);//<- false important for the test + f3=MEDLoader::ReadFieldNode(fileName2,f2->getMesh()->getName(),0,f2->getName(),2,7); + f3->checkCoherency(); + CPPUNIT_ASSERT(f3->isEqual(f2,1e-12,1e-12)); + f3->decrRef(); + f2->decrRef(); + // + f1->decrRef(); + m->decrRef(); +} + +void MEDLoaderTest::testFieldNodeProfilRW2() +{ + const char fileName[]="file23.med"; + MEDCouplingUMesh *mesh=build3DSurfMesh_1(); + MEDLoader::WriteUMesh(fileName,mesh,true); + // + MEDCouplingFieldDouble *f1=MEDCouplingFieldDouble::New(ON_NODES,ONE_TIME); + f1->setName("FieldMix"); + f1->setMesh(mesh); + const double arr2[24]={ + 1071.,1171.,1010.,1110.,1020.,1120.,1030.,1130.,1040.,1140.,1050.,1150., + 1060.,1160.,1070.,1170.,1080.,1180.,1090.,1190.,1091.,1191.,1092.,1192. + }; + DataArrayDouble *array=DataArrayDouble::New(); + array->alloc(12,2); + f1->setArray(array); + array->setInfoOnComponent(0,"plkj (mm)"); + array->setInfoOnComponent(1,"pqqqss (mm)"); + array->decrRef(); + double *tmp=array->getPointer(); + std::copy(arr2,arr2+24,tmp); + f1->setTime(3.17,2,7); + // + const int renumArr[12]={3,7,2,1,5,11,10,0,9,6,8,4}; + f1->renumberNodes(renumArr); + f1->checkCoherency(); + MEDLoader::WriteField(fileName,f1,false);//<- false important for the test + MEDCouplingFieldDouble *f2=MEDLoader::ReadFieldNode(fileName,f1->getMesh()->getName(),0,f1->getName(),2,7); + CPPUNIT_ASSERT(f2->isEqual(f1,1e-12,1e-12)); + // + f2->decrRef(); + mesh->decrRef(); + f1->decrRef(); +} + void MEDLoaderTest::testFieldGaussRW1() { const char fileName[]="file13.med"; @@ -544,6 +627,107 @@ void MEDLoaderTest::testWriteUMeshesRW1() m3d->decrRef(); } +void MEDLoaderTest::testMixCellAndNodesFieldRW1() +{ + const char fileName[]="file21.med"; + MEDCouplingUMesh *mesh=build3DSurfMesh_1(); + MEDCouplingFieldDouble *f1=MEDCouplingFieldDouble::New(ON_CELLS,ONE_TIME); + f1->setName("FieldMix"); + f1->setMesh(mesh); + DataArrayDouble *array=DataArrayDouble::New(); + array->alloc(6,2); + f1->setArray(array); + array->setInfoOnComponent(0,"plkj (mm)"); + array->setInfoOnComponent(1,"pqqqss (mm)"); + array->decrRef(); + double *tmp=array->getPointer(); + const double arr1[12]={71.,171.,10.,110.,20.,120.,30.,130.,40.,140.,50.,150.}; + std::copy(arr1,arr1+12,tmp); + f1->setTime(3.14,2,7); + f1->checkCoherency(); + // + MEDCouplingFieldDouble *f2=MEDCouplingFieldDouble::New(ON_NODES,ONE_TIME); + f2->setName("FieldMix"); + f2->setMesh(mesh); + array=DataArrayDouble::New(); + array->alloc(12,2); + f2->setArray(array); + array->setInfoOnComponent(0,"plkj (mm)"); + array->setInfoOnComponent(1,"pqqqss (mm)"); + array->decrRef(); + tmp=array->getPointer(); + const double arr2[24]={ + 1071.,1171.,1010.,1110.,1020.,1120.,1030.,1130.,1040.,1140.,1050.,1150., + 1060.,1160.,1070.,1170.,1080.,1180.,1090.,1190.,1091.,1191.,1092.,1192. + }; + std::copy(arr2,arr2+24,tmp); + f2->setTime(3.17,2,7); + f2->checkCoherency(); + // + MEDLoader::WriteField(fileName,f1,true); + std::vector ts=MEDLoader::GetTypesOfField(fileName,f1->getName(),f1->getMesh()->getName()); + CPPUNIT_ASSERT_EQUAL(1,(int)ts.size()); + CPPUNIT_ASSERT_EQUAL(ON_CELLS,ts[0]); + std::vector fs=MEDLoader::GetAllFieldNamesOnMesh(fileName,f1->getMesh()->getName()); + CPPUNIT_ASSERT_EQUAL(1,(int)fs.size()); + CPPUNIT_ASSERT(fs[0]=="FieldMix"); + MEDLoader::WriteFieldUsingAlreadyWrittenMesh(fileName,f2); + fs=MEDLoader::GetAllFieldNamesOnMesh(fileName,f1->getMesh()->getName()); + CPPUNIT_ASSERT_EQUAL(1,(int)fs.size()); + CPPUNIT_ASSERT(fs[0]=="FieldMix"); + // + ts=MEDLoader::GetTypesOfField(fileName,f1->getName(),f1->getMesh()->getName()); + CPPUNIT_ASSERT_EQUAL(2,(int)ts.size()); + CPPUNIT_ASSERT_EQUAL(ON_NODES,ts[0]); + CPPUNIT_ASSERT_EQUAL(ON_CELLS,ts[1]); + // + MEDCouplingFieldDouble *f3=MEDLoader::ReadFieldNode(fileName,f1->getMesh()->getName(),0,f1->getName(),2,7); + CPPUNIT_ASSERT(f3->isEqual(f2,1e-12,1e-12)); + f3->decrRef(); + f3=MEDLoader::ReadFieldCell(fileName,f1->getMesh()->getName(),0,f1->getName(),2,7); + CPPUNIT_ASSERT(f3->isEqual(f1,1e-12,1e-12)); + f3->decrRef(); + // + f1->decrRef(); + f2->decrRef(); + mesh->decrRef(); +} + +void MEDLoaderTest::testGetAllFieldNamesRW1() +{ + const char fileName[]="file22.med"; + MEDCouplingUMesh *mesh=build2DMesh_2(); + MEDCouplingFieldDouble *f1=MEDCouplingFieldDouble::New(ON_NODES,ONE_TIME); + f1->setName("Field1"); + f1->setTime(3.44,5,6); + f1->setMesh(mesh); + f1->fillFromAnalytic(2,"x+y"); + MEDLoader::WriteField(fileName,f1,true); + f1->setTime(1002.3,7,8); + f1->fillFromAnalytic(2,"x+77.*y"); + MEDLoader::WriteFieldUsingAlreadyWrittenMesh(fileName,f1); + f1->setName("Field2"); + MEDLoader::WriteField(fileName,f1,false); + f1->setName("Field3"); + mesh->setName("2DMesh_2Bis"); + MEDLoader::WriteField(fileName,f1,false); + f1->decrRef(); + f1=MEDCouplingFieldDouble::New(ON_CELLS,ONE_TIME); + f1->setName("Field8"); + f1->setTime(8.99,7,9); + f1->setMesh(mesh); + f1->fillFromAnalytic(3,"3*x+y"); + MEDLoader::WriteField(fileName,f1,false); + f1->decrRef(); + std::vector fs=MEDLoader::GetAllFieldNames(fileName); + CPPUNIT_ASSERT_EQUAL(4,(int)fs.size()); + CPPUNIT_ASSERT(fs[0]=="Field1"); + CPPUNIT_ASSERT(fs[1]=="Field2"); + CPPUNIT_ASSERT(fs[2]=="Field3"); + CPPUNIT_ASSERT(fs[3]=="Field8"); + mesh->decrRef(); +} + MEDCouplingUMesh *MEDLoaderTest::build1DMesh_1() { double coords[6]={ 0.0, 0.3, 0.75, 1.0, 1.4, 1.3 }; @@ -589,7 +773,7 @@ MEDCouplingUMesh *MEDLoaderTest::build2DCurveMesh_1() MEDCouplingUMesh *MEDLoaderTest::build2DMesh_1() { - double targetCoords[24]={-0.3,-0.3, 0.2,-0.3, 0.7,-0.3, -0.3,0.2, 0.2,0.2, 0.7,0.2, -0.3,0.7, 0.2,0.7, 0.7,0.7 }; + double targetCoords[24]={-0.3,-0.3, 0.2,-0.3, 0.7,-0.3, -0.3,0.2, 0.2,0.2, 0.7,0.2, -0.3,0.7, 0.2,0.7, 0.7,0.7, -0.05,0.95, 0.2,1.2, 0.45,0.95 }; int targetConn[24]={1,4,2, 4,5,2, 6,10,8,9,11,7, 0,3,4,1, 6,7,4,3, 7,8,5,4}; MEDCouplingUMesh *targetMesh=MEDCouplingUMesh::New(); targetMesh->setMeshDimension(2); diff --git a/src/MEDLoader/Test/MEDLoaderTest.hxx b/src/MEDLoader/Test/MEDLoaderTest.hxx index fce8a331b..aa17ea35f 100644 --- a/src/MEDLoader/Test/MEDLoaderTest.hxx +++ b/src/MEDLoader/Test/MEDLoaderTest.hxx @@ -40,6 +40,8 @@ namespace ParaMEDMEM CPPUNIT_TEST( testFieldRW3 ); CPPUNIT_TEST( testMultiMeshRW1 ); CPPUNIT_TEST( testFieldProfilRW1 ); + CPPUNIT_TEST( testFieldNodeProfilRW1 ); + CPPUNIT_TEST( testFieldNodeProfilRW2 ); CPPUNIT_TEST( testFieldGaussRW1 ); CPPUNIT_TEST( testFieldGaussNERW1 ); CPPUNIT_TEST( testLittleStrings1 ); @@ -47,6 +49,8 @@ namespace ParaMEDMEM CPPUNIT_TEST( testFieldShuffleRW1 ); CPPUNIT_TEST( testMultiFieldShuffleRW1 ); CPPUNIT_TEST( testWriteUMeshesRW1 ); + CPPUNIT_TEST( testMixCellAndNodesFieldRW1 ); + CPPUNIT_TEST( testGetAllFieldNamesRW1 ); CPPUNIT_TEST_SUITE_END(); public: void testMesh1DRW(); @@ -59,6 +63,8 @@ namespace ParaMEDMEM void testFieldRW3(); void testMultiMeshRW1(); void testFieldProfilRW1(); + void testFieldNodeProfilRW1(); + void testFieldNodeProfilRW2(); void testFieldGaussRW1(); void testFieldGaussNERW1(); void testLittleStrings1(); @@ -66,6 +72,8 @@ namespace ParaMEDMEM void testFieldShuffleRW1(); void testMultiFieldShuffleRW1(); void testWriteUMeshesRW1(); + void testMixCellAndNodesFieldRW1(); + void testGetAllFieldNamesRW1(); private: MEDCouplingUMesh *build1DMesh_1(); MEDCouplingUMesh *build2DCurveMesh_1(); diff --git a/src/ParaMEDMEMTest/Makefile.am b/src/ParaMEDMEMTest/Makefile.am index 39d8c27fc..f5478b9b9 100644 --- a/src/ParaMEDMEMTest/Makefile.am +++ b/src/ParaMEDMEMTest/Makefile.am @@ -25,9 +25,8 @@ salomeinclude_HEADERS = \ MPIMainTest.hxx \ MPIAccessDECTest.hxx \ MPIAccessTest.hxx \ - ParaMEDMEMTest.hxx - -EXTRA_DIST += MPIMainTest.hxx ParaMEDMEMTest_NonCoincidentDEC.cxx + ParaMEDMEMTest.hxx \ + MPI2Connector.hxx dist_libParaMEDMEMTest_la_SOURCES = \ ParaMEDMEMTest.cxx \ @@ -39,6 +38,7 @@ dist_libParaMEDMEMTest_la_SOURCES = \ ParaMEDMEMTest_ICocoTrio.cxx \ ParaMEDMEMTest_Gauthier1.cxx \ ParaMEDMEMTest_FabienAPI.cxx \ + ParaMEDMEMTest_NonCoincidentDEC.cxx \ MPIAccessDECTest.cxx \ test_AllToAllDEC.cxx \ test_AllToAllvDEC.cxx \ @@ -111,7 +111,6 @@ LDADD = $(MED2_LIBS) $(libMEDMEMTest_la_LDFLAGS) -lm $(MPI_LIBS) \ if MED_ENABLE_FVM LDADD += $(FVM_LIBS) - dist_libParaMEDMEMTest_la_SOURCES += ParaMEDMEMTest_NonCoincidentDEC.cxx libParaMEDMEMTest_la_CPPFLAGS += -DMED_ENABLE_FVM $(FVM_INCLUDES) libParaMEDMEMTest_la_LDFLAGS += $(FVM_LIBS) endif diff --git a/src/ParaMEDMEMTest/ParaMEDMEMTest.hxx b/src/ParaMEDMEMTest/ParaMEDMEMTest.hxx index 885da5f55..be30599ae 100644 --- a/src/ParaMEDMEMTest/ParaMEDMEMTest.hxx +++ b/src/ParaMEDMEMTest/ParaMEDMEMTest.hxx @@ -138,11 +138,13 @@ public: std::string makeTmpFile( const std::string&, const std::string& = "" ); private: +#ifdef MED_ENABLE_FVM void testNonCoincidentDEC(const std::string& filename1, const std::string& meshname1, const std::string& filename2, const std::string& meshname2, int nbprocsource, double epsilon); +#endif void testAsynchronousInterpKernelDEC_2D(double dtA, double tmaxA, double dtB, double tmaxB, bool WithPointToPoint, bool Asynchronous, bool WithInterp, const char *srcMeth, const char *targetMeth); diff --git a/src/ParaMEDMEMTest/ParaMEDMEMTest_InterpKernelDEC.cxx b/src/ParaMEDMEMTest/ParaMEDMEMTest_InterpKernelDEC.cxx index af66e57bb..f4e941ee0 100644 --- a/src/ParaMEDMEMTest/ParaMEDMEMTest_InterpKernelDEC.cxx +++ b/src/ParaMEDMEMTest/ParaMEDMEMTest_InterpKernelDEC.cxx @@ -1948,11 +1948,11 @@ void ParaMEDMEMTest::testInterpKernelDEC3DSurfEmptyBBox() if(source_group->containsMyRank()) { double coords[15]={1.,0.,0., 2.,0.,0., 2.,2.,0., 0.,2.,0., 0.5,0.5,1.}; - int conn[4]={0,1,2,3}; + int conn[7]={0,1,2,3,0,3,4}; mesh=MEDCouplingUMesh::New("Source mesh Proc0",2); mesh->allocateCells(2); mesh->insertNextCell(INTERP_KERNEL::NORM_QUAD4,4,conn); - mesh->insertNextCell(INTERP_KERNEL::NORM_TRI3,2,conn+4); + mesh->insertNextCell(INTERP_KERNEL::NORM_TRI3,3,conn+4); mesh->finishInsertingCells(); DataArrayDouble *myCoords=DataArrayDouble::New(); myCoords->alloc(5,3); diff --git a/src/ParaMEDMEMTest/ParaMEDMEMTest_NonCoincidentDEC.cxx b/src/ParaMEDMEMTest/ParaMEDMEMTest_NonCoincidentDEC.cxx index ee55782a8..8911fba39 100644 --- a/src/ParaMEDMEMTest/ParaMEDMEMTest_NonCoincidentDEC.cxx +++ b/src/ParaMEDMEMTest/ParaMEDMEMTest_NonCoincidentDEC.cxx @@ -17,6 +17,8 @@ // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com // +#ifdef MED_ENABLE_FVM + #include "ParaMEDMEMTest.hxx" #include @@ -251,3 +253,4 @@ void ParaMEDMEMTest::testNonCoincidentDEC(const string& filename1, MPI_Barrier(MPI_COMM_WORLD); } +#endif -- 2.39.2