opm-common
FieldPropsManager.hpp
1 /*
2  Copyright 2019 Equinor ASA.
3 
4  This file is part of the Open Porous Media project (OPM).
5 
6  OPM is free software: you can redistribute it and/or modify it under the terms
7  of the GNU General Public License as published by the Free Software
8  Foundation, either version 3 of the License, or (at your option) any later
9  version.
10 
11  OPM is distributed in the hope that it will be useful, but WITHOUT ANY
12  WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
13  A PARTICULAR PURPOSE. See the GNU General Public License for more details.
14 
15  You should have received a copy of the GNU General Public License along with
16  OPM. If not, see <http://www.gnu.org/licenses/>.
17 */
18 
19 #ifndef FIELDPROPS_MANAGER_HPP
20 #define FIELDPROPS_MANAGER_HPP
21 
22 #include <memory>
23 #include <string>
24 #include <string_view>
25 #include <unordered_map>
26 #include <vector>
27 
28 namespace Opm {
29 
30 class EclipseGrid;
31 class Deck;
32 class DeckKeyword;
33 namespace Fieldprops {
34 class TranCalculator;
35 template<typename T> struct FieldData;
36 }
37 class FieldProps;
38 class Phases;
39 class TableManager;
40 class NumericalAquifers;
41 
43 
44 
45 public:
46  // The default constructor should be removed when the FieldPropsManager is mandatory
47  // The default constructed fieldProps object is **NOT** usable
48  FieldPropsManager() = default;
49  FieldPropsManager(const Deck& deck, const Phases& ph, EclipseGrid& grid, const TableManager& tables,
50  const std::size_t ncomps = 0); // TODO: removing the default value for ncomps
51  virtual ~FieldPropsManager() = default;
52 
53  virtual void reset_actnum(const std::vector<int>& actnum);
54  void deleteMINPVV();
55  const std::string& default_region() const;
56  virtual std::vector<int> actnum() const;
57  virtual std::vector<double> porv(bool global = false) const;
58 
59 
60  void apply_schedule_keywords(const std::vector<DeckKeyword>& keywords);
61 
63  bool is_usable() const;
64 
65  /*
66  The number of cells in the fields managed by this FieldPropsManager.
67  Initially this will correspond to the number of active cells in the grid
68  used when constructing the FieldPropsManager, but using the reset_actnum()
69  method it is possible to deactivate additional cells.
70  */
71  std::size_t active_size() const;
72 
73  bool operator==(const FieldPropsManager& other) const;
74  static bool rst_cmp(const FieldPropsManager& full_arg, const FieldPropsManager& rst_arg);
75 
76  /*
77  Because the FieldProps class can autocreate properties the semantics of
78  get() and has() is slightly non intuitve:
79 
80  - The has<T>("KW") method will check if the current FieldProps container
81  has an installed "KW" keyword; if the container has the keyword in
82  question it will check if all elements have been assigned a value - only
83  in that case will it return true. The has<T>("KW") method will *not* try
84  to create a new keyword.
85 
86  - The has<T>("KW") method will *not* consult the supported<T>("KW")
87  method; i.e. if you ask has<T>("UNKNOWN_KEYWORD") you will just get a
88  false.
89 
90  - The get<T>("KW") method will try to create a new keyword if it does not
91  already have the keyword you are asking for. This implies that you can
92  get the following non intuitive sequence of events:
93 
94  FieldPropsManager fpm(deck, grid);
95 
96  fpm.has<int>("SATNUM"); => false
97  auto satnum = fpm.get<int>("SATNUM"); => SATNUM is autocreated
98  fpm.has<int>("SATNUM"); => true
99 
100  - When checking whether the container has the keyword you should rephrase
101  the question slightly:
102 
103  * Does the container have the keyword *right now* => has<T>("KW")
104  * Can the container provide the keyword => ptr = try_get<T>("KW")
105 
106  - It is quite simple to create a deck where the keywords are only partly
107  initialized, all the methods in the FieldPropsManager only consider
108  fully initialized keywords.
109  */
110 
111 
112  /*
113  The get_copy() has exactly the same behaviour as get(), but the important
114  difference is that said keyword is not already in the container it is not
115  installed in the container; if we look at SATNUM which is a keywor which
116  can be automatically instantiated we have the following behavior:
117 
118  get():
119  fp.has<int>("SATNUM") -> false
120  const std::vector<int>& satnum = fp.get<int>("SATNUM")
121  fp.has<int>("SATNUM") -> true;
122 
123 
124  get_copy():
125  fp.has<int>("SATNUM") -> false
126  const std::vector<int>& satnum = fp.get_copy<int>("SATNUM")
127  fp.has<int>("SATNUM") -> false
128  */
129 
130 
131  template <typename T>
132  std::vector<T> get_copy(const std::string& keyword, bool global=false) const;
133 
134  /*
135  Will return a pointer to the keyword data, or nullptr if the container
136  does not have suce a keyword. Observe that container will hold on to an
137  manage the underlying keyword data.
138 
139  The try_get function will return a nullptr if the container does not
140  contain said keyword, or if the keyword has not been fully initialized. If
141  you ask for a totally unknown keyword the method will return nullptr.
142  */
143  template <typename T>
144  const std::vector<T>* try_get(const std::string& keyword) const;
145 
146  /*
147  You can ask whether the elements in the keyword have a default value -
148  which typically is calculated in some way, or if it has been explicitly
149  assigned to in the deck.
150  */
151  template <typename T>
152  std::vector<bool> defaulted(const std::string& keyword) const;
153 
154 
155  /*
156  Check whether the container supports/recognizes a keyword at all:
157 
158  supported<double>("PORO") => true
159  supported<double>("NO_SUCH_KEYWORD") => false
160 
161  The method does not at all consult the content of the container - it is a
162  static method.
163  */
164  template <typename T>
165  static bool supported(const std::string& keyword);
166 
167  /*
168  The keys() function will return a list of keys corresponding to the fully
169  initialized keywords in the container. Observe that the implementation
170  special cases the PORV and ACTNUM keywords, since these are present with
171  special functions porv(bool) and actnum() the "PORV" and "ACTNUM" string
172  literals are excluded from the keys() list.
173  */
174  template <typename T>
175  std::vector<std::string> keys() const;
176 
177  virtual std::vector<std::string> fip_regions() const;
178 
180  get_int_field_data(const std::string& keyword) const;
181 
187  get_double_field_data(const std::string& keyword, bool allow_unsupported = false) const;
188  virtual const std::vector<int>& get_int(const std::string& keyword) const { return this->get<int>(keyword); }
189  virtual std::vector<int> get_global_int(const std::string& keyword) const { return this->get_global<int>(keyword); }
190 
191  virtual const std::vector<double>& get_double(const std::string& keyword) const { return this->get<double>(keyword); }
192  virtual std::vector<double> get_global_double(const std::string& keyword) const { return this->get_global<double>(keyword); }
193 
194  virtual bool has_int(const std::string& keyword) const { return this->has<int>(keyword); }
195  virtual bool has_double(const std::string& keyword) const { return this->has<double>(keyword); }
196 
197  bool depth_edited() const;
198 
199  /*
200  The transmissibility keywords TRANX, TRANY and TRANZ do not really fit
201  well in the FieldProps system. The opm codebase is based on a full
202  internalization in the parse phase, and then passing fully assembled
203  objects to the simulator. When it comes to the transmissibilities this
204  model breaks down because the input code in opm-common is not capable of
205  calculating the transmissibility, that is performed in the simulator.
206 
207  The EDIT section can have modifiers on TRAN, these must be applied *after*
208  the initial transmissibilities are calculated. To support this all the
209  modifiers to the TRAN{XYZ} fields are assembled in "transmissibility
210  calculators", and then these modifiers can be applied to a TRAN vector
211  after it has been calculated in the simulator. Usage from the simulator
212  could look like:
213 
214 
215  const auto& fp = eclState.fieldProps();
216 
217  // Calculate transmissibilities using grid and permeability
218  std::vector<double> tranx = ....
219 
220  // Check if there are any active TRANX modifiers and apply them
221  if (fp.tran_active("TRANX"))
222  fp.apply_tran("TRANX", tranx);
223 
224 
225  */
226 
227  /*
228  Will check if there are any TRAN{XYZ} modifiers active in the deck.
229  */
230  virtual bool tran_active(const std::string& keyword) const;
231 
232 
233  /*
234  Will apply all the TRAN modifiers which are present in the deck on the
235  already initialized vector tran_data. The vector tran_data should be
236  organised as the data vectors in the fieldpropsmanager - i.e. one element
237  for each active cell - in lexicographical order. The operations which are
238  supported by the transmissibility calculator are those given by the enum
239  ScalarOperation in FieldProps.hpp.
240  */
241  virtual void apply_tran(const std::string& keyword, std::vector<double>& tran_data) const;
242 
249  void apply_tranz_global(const std::vector<std::size_t>& indices,
250  std::vector<double>& data) const;
251 
252  void apply_numerical_aquifers(const NumericalAquifers& aquifers);
253 
254  const std::unordered_map<std::string,Fieldprops::TranCalculator>& getTran() const;
255 
256  void prune_global_for_schedule_run();
257 
258  void set_active_indices(const std::vector<int>& indices);
259 
260 private:
261  /*
262  Return the keyword values as a std::vector<>. All elements in the return
263  value are guaranteed to be assigned a valid value. If the keyword is not
264  in the container, or not all elements have a valid value - an exception
265  will be raised:
266 
267  - keyword which is not supported at all -> std::logic_error
268  - keyword which is not in the deck at all -> std::out_of_range
269  - keyword which has not been fully initialized -> std::runtime_error
270 
271  Many of the keywords in the container can be automatically created, in
272  that case the get() method will silently create a new keyword and default
273  initialize if it is not already in the container. The different exceptions
274  raised for the different error conditions are the same for get(),
275  get_copy() and get_global().
276  */
277  template <typename T>
278  const std::vector<T>& get(const std::string& keyword) const;
279 
280  /*
281  Will check if the container has the keyword loaded; in a fully initialized
282  state. If you ask for a keyword which is not supported at all you will
283  just get false back.
284  */
285  template <typename T>
286  bool has(const std::string& keyword) const;
287 
288  /*
289  This is exactly like the get() method, but the returned vector will have
290  global cartesian size. If the field has a default value that value will be
291  used for filling in in the inactive cells, otherwise zero is used.
292  */
293  template <typename T>
294  std::vector<T> get_global(const std::string& keyword) const;
295 
296  std::shared_ptr<FieldProps> fp;
297 };
298 
299 template<class MapType>
300 void apply_tran(const std::unordered_map<std::string, Fieldprops::TranCalculator>& tran,
301  const MapType& double_data,
302  std::size_t active_size,
303  const std::string& keyword, std::vector<double>& data);
304 
305 template<class MapType>
306 void apply_tran(const Fieldprops::TranCalculator& tranCalc,
307  const MapType& double_data,
308  const std::vector<std::size_t>& indices,
309  std::vector<double>& data);
310 
311 }
312 
313 #endif
Definition: TranCalculator.hpp:43
Definition: FieldPropsManager.hpp:42
About cell information and dimension: The actual grid information is held in a pointer to an ERT ecl_...
Definition: EclipseGrid.hpp:63
This class implements a small container which holds the transmissibility mulitpliers for all the face...
Definition: Exceptions.hpp:30
bool is_usable() const
Whether we can call methods on the manager.
Definition: FieldPropsManager.cpp:109
void apply_tranz_global(const std::vector< std::size_t > &indices, std::vector< double > &data) const
Apply TRANZ modifiers using global indices.
Definition: FieldPropsManager.cpp:221
Definition: TableManager.hpp:71
Definition: FieldData.hpp:71
Definition: Deck.hpp:46
const Fieldprops::FieldData< double > & get_double_field_data(const std::string &keyword, bool allow_unsupported=false) const
Get double field data associated with a keyword.
Definition: FieldPropsManager.cpp:144
Definition: NumericalAquifers.hpp:36
Definition: Runspec.hpp:45