mirror of
https://github.com/OPM/ResInsight.git
synced 2026-10-27 23:50:19 -05:00
Building the cell search tree was dominated by one small std::vector<int> allocation per leaf, and a tree with one cell per leaf becomes very deep for large grids. - BoundingBoxTree: Store leaf ids in flat arrays, and move the input data instead of copying it. The tree shape is unchanged. Queries no longer copy the ids of each leaf. - RigMainGrid: Always group at least 8 cells along K in each leaf. findIntersectingCells() removes cells not intersecting the query bounding box, so the result is the same set of cells as for a tree with one cell per leaf. This also applies to very large grids, which previously got the cells of the whole leaf. - Include cells of nested LGRs and LGR cells in invalid main grid cells in the grouped tree, as the previous tree with one cell per leaf did.
191 lines
7.9 KiB
C++
191 lines
7.9 KiB
C++
/////////////////////////////////////////////////////////////////////////////////
|
|
//
|
|
// Copyright (C) 2011- Statoil ASA
|
|
// Copyright (C) 2013- Ceetron Solutions AS
|
|
// Copyright (C) 2011-2012 Ceetron AS
|
|
//
|
|
// ResInsight is free software: you can redistribute it and/or modify
|
|
// it under the terms of the GNU General Public License as published by
|
|
// the Free Software Foundation, either version 3 of the License, or
|
|
// (at your option) any later version.
|
|
//
|
|
// ResInsight 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 General Public License at <http://www.gnu.org/licenses/gpl.html>
|
|
// for more details.
|
|
//
|
|
/////////////////////////////////////////////////////////////////////////////////
|
|
|
|
#pragma once
|
|
|
|
#include "RigCell.h"
|
|
#include "RigGridBase.h"
|
|
#include "RigLocalGrid.h"
|
|
|
|
#include "cvfBoundingBox.h"
|
|
#include "cvfCollection.h"
|
|
|
|
#include <QString>
|
|
|
|
#include <map>
|
|
#include <mutex>
|
|
#include <vector>
|
|
|
|
class RigActiveCellInfo;
|
|
class RigNNCData;
|
|
|
|
namespace cvf
|
|
{
|
|
class BoundingBoxTree;
|
|
}
|
|
|
|
class RigMainGrid : public RigGridBase
|
|
{
|
|
public:
|
|
RigMainGrid();
|
|
~RigMainGrid() override;
|
|
|
|
virtual size_t totalCellCount() const;
|
|
|
|
std::vector<cvf::Vec3d>& nodes();
|
|
const std::vector<cvf::Vec3d>& nodes() const;
|
|
|
|
virtual RigGridBase* gridAndGridLocalIdxFromGlobalCellIdx( size_t globalCellIdx, size_t* gridLocalCellIdx );
|
|
virtual const RigGridBase* gridAndGridLocalIdxFromGlobalCellIdx( size_t globalCellIdx, size_t* gridLocalCellIdx ) const;
|
|
|
|
virtual const RigCell& cellByGridAndGridLocalCellIdx( size_t gridIdx, size_t gridLocalCellIdx ) const;
|
|
virtual size_t reservoirCellIndexByGridAndGridLocalCellIndex( size_t gridIdx, size_t gridLocalCellIdx ) const;
|
|
virtual size_t findReservoirCellIndexFromPoint( const cvf::Vec3d& point ) const;
|
|
|
|
void addLocalGrid( RigLocalGrid* localGrid );
|
|
|
|
size_t gridCountOnFile() const;
|
|
size_t gridCount() const;
|
|
RigGridBase* gridByIndex( size_t localGridIndex );
|
|
const RigGridBase* gridByIndex( size_t localGridIndex ) const;
|
|
RigGridBase* gridById( int localGridId );
|
|
RigGridBase* gridByName( const std::string& name );
|
|
|
|
size_t totalTemporaryGridCellCount() const;
|
|
|
|
// Nested hybrid grid: maps a reconstructed LGR cell (global reservoir index) to the original
|
|
// flat refined cell it was built from. Used to copy result values onto the LGR cells.
|
|
void setNestedHybridLgrSourceCells( const std::map<size_t, size_t>& lgrToFlatCell );
|
|
const std::map<size_t, size_t>& nestedHybridLgrSourceCells() const;
|
|
|
|
// Nested hybrid grid: maps a flat cell (global reservoir index) to the natural index of its
|
|
// parent COARSE cell. Used for the volume-weighted QC aggregate onto coarse parents.
|
|
void setNestedHybridCoarseParents( const std::map<size_t, size_t>& cellToCoarseParent );
|
|
const std::map<size_t, size_t>& nestedHybridCoarseParents() const;
|
|
|
|
RigNNCData* nncData();
|
|
|
|
void setFaults( const cvf::Collection<RigFault>& faults );
|
|
const cvf::Collection<RigFault>& faults() const;
|
|
cvf::Collection<RigFault>& faults();
|
|
void calculateFaults( const RigActiveCellInfo* activeCellInfo );
|
|
|
|
void addUnNamedFaultFaces( int gcIdx,
|
|
const RigActiveCellInfo* activeCellInfo,
|
|
const std::vector<cvf::Vec3d>& vxs,
|
|
int unNamedFaultIdx,
|
|
int unNamedFaultWithInactiveIdx,
|
|
std::vector<RigFault::FaultFace>& unNamedFaultFaces,
|
|
std::vector<RigFault::FaultFace>& unNamedFaultFacesInactive,
|
|
RigFaultsPrCellAccumulator* faultsPrCellAcc ) const;
|
|
|
|
void distributeNNCsToFaults();
|
|
|
|
const RigFault* findFaultFromCellIndexAndCellFace( size_t reservoirCellIndex, cvf::StructGridInterface::FaceType face ) const;
|
|
bool isFaceNormalsOutwards() const;
|
|
void computeFaceNormalsDirection( const std::vector<size_t>& reservoirCellIndices ) const;
|
|
|
|
void computeCachedData( std::string* aabbTreeInfo = nullptr );
|
|
void initAllSubGridsParentGridPointer();
|
|
|
|
cvf::Vec3d displayModelOffset() const override;
|
|
void setDisplayModelOffset( cvf::Vec3d offset );
|
|
|
|
void setFlipAxis( bool flipXAxis, bool flipYAxis );
|
|
std::vector<size_t> findIntersectingCells( const cvf::BoundingBox& inputBB ) const;
|
|
|
|
cvf::BoundingBox boundingBox() const;
|
|
|
|
bool isTempGrid() const override;
|
|
const std::string& associatedWellPathName() const override;
|
|
|
|
void setUseMapAxes( bool useMapAxes );
|
|
bool useMapAxes() const;
|
|
void setMapAxes( const std::array<double, 6>& mapAxes );
|
|
const std::array<double, 6>& mapAxes() const;
|
|
std::array<float, 6> mapAxesF() const;
|
|
|
|
cvf::Mat4d mapAxisTransform() const;
|
|
|
|
bool isDualPorosity() const;
|
|
void setDualPorosity( bool enable );
|
|
|
|
// invalidate all cells with I > iLimit (0 based index)
|
|
void invalidateCellsAboveI( size_t iLimit );
|
|
|
|
std::tuple<QString, double, cvf::StructGridInterface::FaceType> minimumDistanceFaultToPoint( const cvf::Vec3d& point ) const;
|
|
|
|
protected: // only for use by file readers and internal services. TODO: replace with a better API
|
|
friend class RigGridBase;
|
|
friend class RigReservoirBuilder;
|
|
friend class RifRoffFileTools;
|
|
friend class RifEclipseOutputFileTools;
|
|
friend class RifReaderEclipseOutput;
|
|
friend class RifReaderOpmCommon;
|
|
friend class RiaGrpcCaseService;
|
|
friend class RiaGrpcActiveCellInfoStateHandler;
|
|
friend class RicCreateTemporaryLgrFeature;
|
|
friend class RimCornerPointCase;
|
|
friend class RigNestedHybridGridReconstructor;
|
|
std::vector<RigCell>& reservoirCells();
|
|
const std::vector<RigCell>& reservoirCells() const;
|
|
|
|
private:
|
|
void initAllSubCellsMainGridCellIndex();
|
|
bool hasFaultWithName( const QString& name ) const;
|
|
void computeBoundingBox();
|
|
|
|
static std::array<double, 6> defaultMapAxes();
|
|
|
|
void doBuildCellSearchTree( std::string* aabbTreeInfo = nullptr ) const;
|
|
void buildCellSearchTree( size_t cellsPerBoundingBox ) const;
|
|
cvf::BoundingBox cellBoundingBox( size_t reservoirCellIndex ) const;
|
|
|
|
private:
|
|
std::vector<cvf::Vec3d> m_nodes; ///< Global vertex table
|
|
std::vector<RigCell> m_cells; ///< Global array of all cells in the reservoir (including the ones in LGR's)
|
|
cvf::Collection<RigLocalGrid> m_localGrids; ///< List of all the LGR's in this reservoir
|
|
std::vector<size_t> m_gridIdToIndexMapping; ///< Mapping from LGR Id to index.
|
|
|
|
std::map<size_t, size_t> m_nestedHybridLgrSourceCells; ///< LGR cell global index -> source flat cell global index
|
|
std::map<size_t, size_t> m_nestedHybridCoarseParents; ///< flat cell global index -> parent coarse cell natural index
|
|
|
|
cvf::Collection<RigFault> m_faults;
|
|
cvf::ref<RigNNCData> m_nncData;
|
|
cvf::ref<RigFaultsPrCellAccumulator> m_faultsPrCellAcc;
|
|
|
|
cvf::Vec3d m_displayModelOffset;
|
|
cvf::BoundingBox m_boundingBox;
|
|
|
|
bool m_flipXAxis;
|
|
bool m_flipYAxis;
|
|
|
|
bool m_useMapAxes;
|
|
std::array<double, 6> m_mapAxes;
|
|
|
|
bool m_dualPorosity;
|
|
|
|
mutable bool m_isFaceNormalsOutwards;
|
|
mutable bool m_isFaceNormalsOutwardsComputed;
|
|
mutable cvf::ref<cvf::BoundingBoxTree> m_cellSearchTree;
|
|
mutable size_t m_cellSearchTreeCellsPerBoundingBox = 1;
|
|
mutable std::mutex m_cellSearchTreeMutex;
|
|
};
|