40
40
#include < sstream>
41
41
#include < string>
42
42
#include < vector>
43
+ #include < memory>
43
44
44
45
namespace libMesh
45
46
{
@@ -68,21 +69,13 @@ class ParsedFEMFunction : public FEMFunctionBase<Output>
68
69
const std::vector<Output> * initial_vals=nullptr );
69
70
70
71
/* *
71
- * This class contains a const reference so it can't be copy or move-assigned.
72
+ * Special functions
73
+ * - This class contains a const reference so it can't be copy or move-assigned.
74
+ * - This class contains unique_ptrs so it can't be default copy constructed.
72
75
*/
73
76
ParsedFEMFunction & operator = (const ParsedFEMFunction &) = delete ;
74
77
ParsedFEMFunction & operator = (ParsedFEMFunction &&) = delete ;
75
-
76
- /* *
77
- * The remaining 5 special functions can be safely defaulted.
78
- *
79
- * \note The underlying FunctionParserBase class has a copy
80
- * constructor, so this class should be default-constructible. And,
81
- * although FunctionParserBase's move constructor is deleted, _this_
82
- * class should still be move-constructible because
83
- * FunctionParserBase only appears in a vector.
84
- */
85
- ParsedFEMFunction (const ParsedFEMFunction &) = default ;
78
+ ParsedFEMFunction (const ParsedFEMFunction &) = delete ;
86
79
ParsedFEMFunction (ParsedFEMFunction &&) = default ;
87
80
virtual ~ParsedFEMFunction () = default ;
88
81
@@ -168,9 +161,9 @@ class ParsedFEMFunction : public FEMFunctionBase<Output>
168
161
_n_requested_hess_components;
169
162
bool _requested_normals;
170
163
#ifdef LIBMESH_HAVE_FPARSER
171
- std::vector<FunctionParserBase<Output>> parsers;
164
+ std::vector<std::unique_ptr< FunctionParserBase<Output> >> parsers;
172
165
#else
173
- std::vector<char > parsers;
166
+ std::vector<char * > parsers;
174
167
#endif
175
168
std::vector<Output> _spacetime;
176
169
@@ -401,7 +394,7 @@ ParsedFEMFunction<Output>::operator() (const FEMContext & c,
401
394
{
402
395
eval_args (c, p, time );
403
396
404
- return eval (parsers[0 ], " f" , 0 );
397
+ return eval (* parsers[0 ], " f" , 0 );
405
398
}
406
399
407
400
@@ -421,7 +414,7 @@ ParsedFEMFunction<Output>::operator() (const FEMContext & c,
421
414
libmesh_assert_equal_to (size, parsers.size ());
422
415
423
416
for (unsigned int i=0 ; i != size; ++i)
424
- output (i) = eval (parsers[i], " f" , i);
417
+ output (i) = eval (* parsers[i], " f" , i);
425
418
}
426
419
427
420
@@ -436,7 +429,7 @@ ParsedFEMFunction<Output>::component (const FEMContext & c,
436
429
eval_args (c, p, time );
437
430
438
431
libmesh_assert_less (i, parsers.size ());
439
- return eval (parsers[i], " f" , i);
432
+ return eval (* parsers[i], " f" , i);
440
433
}
441
434
442
435
template <typename Output>
@@ -479,16 +472,16 @@ ParsedFEMFunction<Output>::get_inline_value(const std::string & inline_var_name)
479
472
#ifdef LIBMESH_HAVE_FPARSER
480
473
// Parse and evaluate the new subexpression.
481
474
// Add the same constants as we used originally.
482
- FunctionParserBase<Output> fp ;
483
- fp. AddConstant (" NaN" , std::numeric_limits<Real>::quiet_NaN ());
484
- fp. AddConstant (" pi" , std::acos (Real (-1 )));
485
- fp. AddConstant (" e" , std::exp (Real (1 )));
475
+ auto fp = libmesh_make_unique< FunctionParserBase<Output>>() ;
476
+ fp-> AddConstant (" NaN" , std::numeric_limits<Real>::quiet_NaN ());
477
+ fp-> AddConstant (" pi" , std::acos (Real (-1 )));
478
+ fp-> AddConstant (" e" , std::exp (Real (1 )));
486
479
libmesh_error_msg_if
487
- (fp. Parse (new_subexpression, variables) != -1 , // -1 for success
480
+ (fp-> Parse (new_subexpression, variables) != -1 , // -1 for success
488
481
" ERROR: FunctionParser is unable to parse modified expression: "
489
- << new_subexpression << ' \n ' << fp. ErrorMsg ());
482
+ << new_subexpression << ' \n ' << fp-> ErrorMsg ());
490
483
491
- Output new_var_value = this ->eval (fp, new_subexpression, 0 );
484
+ Output new_var_value = this ->eval (* fp, new_subexpression, 0 );
492
485
#ifdef NDEBUG
493
486
return new_var_value;
494
487
#else
@@ -621,16 +614,16 @@ ParsedFEMFunction<Output>::partial_reparse (const std::string & expression)
621
614
#ifdef LIBMESH_HAVE_FPARSER
622
615
// Parse (and optimize if possible) the subexpression.
623
616
// Add some basic constants, to Real precision.
624
- FunctionParserBase<Output> fp ;
625
- fp. AddConstant (" NaN" , std::numeric_limits<Real>::quiet_NaN ());
626
- fp. AddConstant (" pi" , std::acos (Real (-1 )));
627
- fp. AddConstant (" e" , std::exp (Real (1 )));
617
+ auto fp = libmesh_make_unique< FunctionParserBase<Output>>() ;
618
+ fp-> AddConstant (" NaN" , std::numeric_limits<Real>::quiet_NaN ());
619
+ fp-> AddConstant (" pi" , std::acos (Real (-1 )));
620
+ fp-> AddConstant (" e" , std::exp (Real (1 )));
628
621
libmesh_error_msg_if
629
- (fp. Parse (_subexpressions.back (), variables) != -1 , // -1 for success
622
+ (fp-> Parse (_subexpressions.back (), variables) != -1 , // -1 for success
630
623
" ERROR: FunctionParser is unable to parse expression: "
631
- << _subexpressions.back () << ' \n ' << fp. ErrorMsg ());
632
- fp. Optimize ();
633
- parsers.push_back (fp );
624
+ << _subexpressions.back () << ' \n ' << fp-> ErrorMsg ());
625
+ fp-> Optimize ();
626
+ parsers.push_back (std::move (fp) );
634
627
#else
635
628
libmesh_error_msg (" ERROR: This functionality requires fparser!" );
636
629
#endif
0 commit comments