libmesh解析
本工作只是尝试解析原libmesh的代码,供学习使用
 全部  命名空间 文件 函数 变量 类型定义 枚举 枚举值 友元 
Public 成员函数 | Protected 成员函数 | Private 属性 | 所有成员列表
libMesh::ParsedFEMFunction< Output > 模板类 参考

ParsedFEMFunction 提供对 FEMSystem 中基于 FParser 的解析函数的支持。 更多...

#include <parsed_fem_function.h>

类 libMesh::ParsedFEMFunction< Output > 继承关系图:
[图例]

Public 成员函数

 ParsedFEMFunction (const System &sys, std::string expression, const std::vector< std::string > *additional_vars=nullptr, const std::vector< Output > *initial_vals=nullptr)
 构造函数。 更多...
 
ParsedFEMFunctionoperator= (const ParsedFEMFunction &)
 赋值运算符。 更多...
 
 ParsedFEMFunction (const ParsedFEMFunction &)
 复制构造函数。 更多...
 
void reparse (std::string expression)
 重新解析使用新表达式。 更多...
 
virtual void init_context (const FEMContext &c) override
 初始化上下文。 更多...
 
virtual std::unique_ptr
< FEMFunctionBase< Output > > 
clone () const override
 克隆函数。 更多...
 
virtual Output operator() (const FEMContext &c, const Point &p, const Real time=0.) override
 调用运算符,用于计算解析函数的值。 更多...
 
void operator() (const FEMContext &c, const Point &p, const Real time, DenseVector< Output > &output) override
 调用运算符,用于计算解析函数的值。 更多...
 
virtual Output component (const FEMContext &c, unsigned int i, const Point &p, Real time=0.) override
 计算解析函数的第 i 个分量的值。 更多...
 
const std::string & expression ()
 获取解析表达式。 更多...
 
Output get_inline_value (std::string_view inline_var_name) const
 获取内联变量的值。 更多...
 
void set_inline_value (std::string_view inline_var_name, Output newval)
 更改内联变量的值。 更多...
 
void operator() (const FEMContext &, const Point &p, DenseVector< Output > &output)
 计算时间无关的向量值函数的评估函数。将输出值设置在传入的output DenseVector中。 更多...
 

Protected 成员函数

void partial_reparse (std::string expression)
 用于重新解析表达式的辅助函数。 更多...
 
std::size_t find_name (std::string_view varname, std::string_view expr) const
 用于解析变量名称的辅助函数。 更多...
 
void eval_args (const FEMContext &c, const Point &p, const Real time)
 用于计算函数参数的辅助函数。 更多...
 
Output eval (FunctionParserBase< Output > &parser, std::string_view libmesh_dbg_var(function_name), unsigned int libmesh_dbg_var(component_idx)) const
 评估第 i 个 FunctionParser 并检查结果。 更多...
 
Output eval (char &libmesh_dbg_var(parser), std::string_view libmesh_dbg_var(function_name), unsigned int libmesh_dbg_var(component_idx)) const
 评估字符对象。 更多...
 

Private 属性

const System & _sys
 
std::string _expression
 
std::vector< std::string > _subexpressions
 
unsigned int _n_vars
 
unsigned int _n_requested_vars
 
unsigned int _n_requested_grad_components
 
unsigned int _n_requested_hess_components
 
bool _requested_normals
 
std::vector< std::unique_ptr
< FunctionParserBase< Output > > > 
parsers
 
std::vector< char * > parsers
 
std::vector< Output > _spacetime
 
std::vector< bool > _need_var
 
std::vector< bool > _need_var_grad
 
std::vector< bool > _need_var_hess
 
std::string variables
 
std::vector< std::string > _additional_vars
 
std::vector< Output > _initial_vals
 

详细描述

template<typename Output = Number>
class libMesh::ParsedFEMFunction< Output >

ParsedFEMFunction 提供对 FEMSystem 中基于 FParser 的解析函数的支持。

所有覆盖的虚拟函数在 fem_function_base.h 中有文档说明。

作者
Roy Stogner
日期
2014 用于在 FEMSystem 中使用解析函数的支持。
模板参数
Output输出类型,默认为 Number。

在文件 parsed_fem_function.h59 行定义.

构造及析构函数说明

template<typename Output>
libMesh::ParsedFEMFunction< Output >::ParsedFEMFunction ( const System &  sys,
std::string  expression,
const std::vector< std::string > *  additional_vars = nullptr,
const std::vector< Output > *  initial_vals = nullptr 
)
inlineexplicit

构造函数。

参数
sysSystem 对象的引用。
expression解析表达式。
additional_vars其他变量的字符串向量(可选,默认为 nullptr)。
initial_vals初始值的输出向量(可选,默认为 nullptr)。

在文件 parsed_fem_function.h292 行定义.

参考 libMesh::ParsedFEMFunction< Output >::reparse().

295  :
296  _sys(sys),
297  _expression (), // overridden by parse()
298  _n_vars(sys.n_vars()),
302  _requested_normals(false),
303  _need_var(_n_vars, false),
304  _need_var_grad(_n_vars*LIBMESH_DIM, false),
305 #ifdef LIBMESH_ENABLE_SECOND_DERIVATIVES
306  _need_var_hess(_n_vars*LIBMESH_DIM*LIBMESH_DIM, false),
307 #endif // LIBMESH_ENABLE_SECOND_DERIVATIVES
308  _additional_vars (additional_vars ? *additional_vars : std::vector<std::string>()),
309  _initial_vals (initial_vals ? *initial_vals : std::vector<Output>())
310 {
311  this->reparse(std::move(expression));
312 }
std::vector< bool > _need_var_grad
std::vector< Output > _initial_vals
std::vector< std::string > _additional_vars
void reparse(std::string expression)
重新解析使用新表达式。
std::vector< bool > _need_var_hess
const std::string & expression()
获取解析表达式。
template<typename Output>
libMesh::ParsedFEMFunction< Output >::ParsedFEMFunction ( const ParsedFEMFunction< Output > &  other)
inline

复制构造函数。

此类包含 unique_ptrs,因此无法进行默认复制构造或赋值。

可以进行默认移动和删除。

在文件 parsed_fem_function.h317 行定义.

参考 libMesh::ParsedFEMFunction< Output >::_expression , 以及 libMesh::ParsedFEMFunction< Output >::reparse().

317  :
318  FEMFunctionBase<Output>(other),
319  _sys(other._sys),
320  _expression(other._expression),
321  _subexpressions(other._subexpressions),
322  _n_vars(other._n_vars),
323  _n_requested_vars(other._n_requested_vars),
324  _n_requested_grad_components(other._n_requested_grad_components),
325  _n_requested_hess_components(other._n_requested_hess_components),
326  _requested_normals(other._requested_normals),
327  _spacetime(other._spacetime),
328  _need_var(other._need_var),
329  _need_var_grad(other._need_var_grad),
330 #ifdef LIBMESH_ENABLE_SECOND_DERIVATIVES
331  _need_var_hess(other._need_var_hess),
332 #endif // LIBMESH_ENABLE_SECOND_DERIVATIVES
333  variables(other.variables),
334  _additional_vars(other._additional_vars),
335  _initial_vals(other._initial_vals)
336 {
337  this->reparse(_expression);
338 }
std::vector< bool > _need_var_grad
std::vector< Output > _initial_vals
std::vector< std::string > _additional_vars
std::vector< std::string > _subexpressions
std::vector< Output > _spacetime
void reparse(std::string expression)
重新解析使用新表达式。
std::vector< bool > _need_var_hess

成员函数说明

template<typename Output >
std::unique_ptr< FEMFunctionBase< Output > > libMesh::ParsedFEMFunction< Output >::clone ( ) const
inlineoverridevirtual

克隆函数。

返回
返回一个 FEMFunctionBase 类型的新对象的独立指针。

实现了 libMesh::FEMFunctionBase< Output >.

在文件 parsed_fem_function.h520 行定义.

521 {
522  return std::make_unique<ParsedFEMFunction>
524 }
std::vector< Output > _initial_vals
std::vector< std::string > _additional_vars
template<typename Output >
Output libMesh::ParsedFEMFunction< Output >::component ( const FEMContext &  c,
unsigned int  i,
const Point &  p,
Real  time = 0. 
)
inlineoverridevirtual

计算解析函数的第 i 个分量的值。

参数
cFEMContext 对象的引用。
i分量的索引。
p点的引用。
time时间,默认值为 0。
返回
返回解析函数的第 i 个分量的值。

重载 libMesh::FEMFunctionBase< Output > .

在文件 parsed_fem_function.h562 行定义.

566 {
567  eval_args(c, p, time);
568 
569  libmesh_assert_less (i, parsers.size());
570  return eval(*parsers[i], "f", i);
571 }
Output eval(FunctionParserBase< Output > &parser, std::string_view libmesh_dbg_var(function_name), unsigned int libmesh_dbg_var(component_idx)) const
评估第 i 个 FunctionParser 并检查结果。
std::vector< std::unique_ptr< FunctionParserBase< Output > > > parsers
void eval_args(const FEMContext &c, const Point &p, const Real time)
用于计算函数参数的辅助函数。
template<typename Output>
Output libMesh::ParsedFEMFunction< Output >::eval ( FunctionParserBase< Output > &  parser,
std::string_view   libmesh_dbg_varfunction_name,
unsigned int   libmesh_dbg_varcomponent_idx 
) const
inlineprotected

评估第 i 个 FunctionParser 并检查结果。

参数
parser要评估的 FunctionParserBase 对象。
function_name函数名称。
component_idx分量索引。
返回
返回评估结果。

在文件 parsed_fem_function.h934 行定义.

参考 libMesh::err.

937 {
938 #ifndef NDEBUG
939  Output result = parser.Eval(_spacetime.data());
940  int error_code = parser.EvalError();
941  if (error_code)
942  {
943  libMesh::err << "ERROR: FunctionParser is unable to evaluate component "
944  << component_idx
945  << " for '"
946  << function_name;
947 
948  for (auto i : index_range(parsers))
949  if (parsers[i].get() == &parser)
950  libMesh::err << "' of expression '"
951  << _subexpressions[i];
952 
953  libMesh::err << "' with arguments:\n";
954  for (const auto & st : _spacetime)
955  libMesh::err << '\t' << st << '\n';
956  libMesh::err << '\n';
957 
958  // Currently no API to report error messages, we'll do it manually
959  std::string error_message = "Reason: ";
960 
961  switch (error_code)
962  {
963  case 1:
964  error_message += "Division by zero";
965  break;
966  case 2:
967  error_message += "Square Root error (negative value)";
968  break;
969  case 3:
970  error_message += "Log error (negative value)";
971  break;
972  case 4:
973  error_message += "Trigonometric error (asin or acos of illegal value)";
974  break;
975  case 5:
976  error_message += "Maximum recursion level reached";
977  break;
978  default:
979  error_message += "Unknown";
980  break;
981  }
982  libmesh_error_msg(error_message);
983  }
984 
985  return result;
986 #else
987  return parser.Eval(_spacetime.data());
988 #endif
989 }
std::vector< std::string > _subexpressions
std::vector< Output > _spacetime
std::vector< std::unique_ptr< FunctionParserBase< Output > > > parsers
OStreamProxy err
template<typename Output = Number>
Output libMesh::ParsedFEMFunction< Output >::eval ( char &  libmesh_dbg_varparser,
std::string_view   libmesh_dbg_varfunction_name,
unsigned int   libmesh_dbg_varcomponent_idx 
) const
inlineprotected

评估字符对象。

参数
parser要评估的字符对象。
function_name函数名称。
component_idx分量索引。
返回
返回评估结果。
template<typename Output >
void libMesh::ParsedFEMFunction< Output >::eval_args ( const FEMContext &  c,
const Point &  p,
const Real  time 
)
inlineprotected

用于计算函数参数的辅助函数。

参数
cFEMContext 对象的引用。
p点的引用。
time时间。

在文件 parsed_fem_function.h805 行定义.

808 {
809  _spacetime[0] = p(0);
810 #if LIBMESH_DIM > 1
811  _spacetime[1] = p(1);
812 #endif
813 #if LIBMESH_DIM > 2
814  _spacetime[2] = p(2);
815 #endif
816  _spacetime[LIBMESH_DIM] = time;
817 
818  unsigned int request_index = 0;
819  for (unsigned int v=0; v != _n_vars; ++v)
820  {
821  if (!_need_var[v])
822  continue;
823 
824  c.point_value(v, p, _spacetime[LIBMESH_DIM+1+request_index]);
825  request_index++;
826  }
827 
829  for (unsigned int v=0; v != _n_vars; ++v)
830  {
831  if (!_need_var_grad[v*LIBMESH_DIM]
832 #if LIBMESH_DIM > 1
833  && !_need_var_grad[v*LIBMESH_DIM+1]
834 #if LIBMESH_DIM > 2
835  && !_need_var_grad[v*LIBMESH_DIM+2]
836 #endif
837 #endif
838  )
839  continue;
840 
841  Gradient g;
842  c.point_gradient(v, p, g);
843 
844  for (unsigned int d=0; d != LIBMESH_DIM; ++d)
845  {
846  if (!_need_var_grad[v*LIBMESH_DIM+d])
847  continue;
848 
849  _spacetime[LIBMESH_DIM+1+request_index] = g(d);
850  request_index++;
851  }
852  }
853 
854 #ifdef LIBMESH_ENABLE_SECOND_DERIVATIVES
856  for (unsigned int v=0; v != _n_vars; ++v)
857  {
858  if (!_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM]
859 #if LIBMESH_DIM > 1
860  && !_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+1]
861  && !_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+2]
862  && !_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+3]
863 #if LIBMESH_DIM > 2
864  && !_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+4]
865  && !_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+5]
866  && !_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+6]
867  && !_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+7]
868  && !_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+8]
869 #endif
870 #endif
871  )
872  continue;
873 
874  Tensor h;
875  c.point_hessian(v, p, h);
876 
877  for (unsigned int d1=0; d1 != LIBMESH_DIM; ++d1)
878  for (unsigned int d2=0; d2 != LIBMESH_DIM; ++d2)
879  {
880  if (!_need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+d1*LIBMESH_DIM+d2])
881  continue;
882 
883  _spacetime[LIBMESH_DIM+1+request_index] = h(d1,d2);
884  request_index++;
885  }
886  }
887 #endif // LIBMESH_ENABLE_SECOND_DERIVATIVES
888 
889  if (_requested_normals)
890  {
891  FEBase * side_fe;
892  c.get_side_fe(0, side_fe);
893 
894  const std::vector<Point> & normals = side_fe->get_normals();
895 
896  const std::vector<Point> & xyz = side_fe->get_xyz();
897 
898  libmesh_assert_equal_to(normals.size(), xyz.size());
899 
900  // We currently only support normals at quadrature points!
901 #ifndef NDEBUG
902  bool at_quadrature_point = false;
903 #endif
904  for (auto qp : index_range(normals))
905  {
906  if (p == xyz[qp])
907  {
908  const Point & n = normals[qp];
909  for (unsigned int d=0; d != LIBMESH_DIM; ++d)
910  {
911  _spacetime[LIBMESH_DIM+1+request_index] = n(d);
912  request_index++;
913  }
914 #ifndef NDEBUG
915  at_quadrature_point = true;
916 #endif
917  break;
918  }
919  }
920 
921  libmesh_assert(at_quadrature_point);
922  }
923 
924  // The remaining locations in _spacetime are currently set at construction
925  // but could potentially be made dynamic
926 }
std::vector< bool > _need_var_grad
std::vector< Output > _spacetime
NumberVectorValue Gradient
Definition: vector_value.h:151
std::vector< bool > _need_var_hess
NumberTensorValue Tensor
Definition: tensor_value.h:223
template<typename Output = Number>
const std::string& libMesh::ParsedFEMFunction< Output >::expression ( )
inline

获取解析表达式。

返回
返回解析表达式的引用。

在文件 parsed_fem_function.h165 行定义.

165 { return _expression; }
template<typename Output >
std::size_t libMesh::ParsedFEMFunction< Output >::find_name ( std::string_view  varname,
std::string_view  expr 
) const
inlineprotected

用于解析变量名称的辅助函数。

参数
varname要查找的变量名称。
expr解析表达式。
返回
返回变量名称在表达式中的位置。

在文件 parsed_fem_function.h779 行定义.

781 {
782  const std::size_t namesize = varname.size();
783  std::size_t varname_i = expr.find(varname);
784 
785  while ((varname_i != std::string::npos) &&
786  (((varname_i > 0) &&
787  (std::isalnum(expr[varname_i-1]) ||
788  (expr[varname_i-1] == '_'))) ||
789  ((varname_i+namesize < expr.size()) &&
790  (std::isalnum(expr[varname_i+namesize]) ||
791  (expr[varname_i+namesize] == '_')))))
792  {
793  varname_i = expr.find(varname, varname_i+1);
794  }
795 
796  return varname_i;
797 }
template<typename Output >
Output libMesh::ParsedFEMFunction< Output >::get_inline_value ( std::string_view  inline_var_name) const
inline

获取内联变量的值。

参数
inline_var_name内联变量的名称。
返回
返回内联变量的值。
注解
仅当内联变量值与输入变量无关时,内联变量在任何子表达式中未被重新定义, 并且在出现内联变量的任何子表达式中取相同值时,才能正确使用此函数。

在文件 parsed_fem_function.h576 行定义.

参考 libMesh::Real.

参考自 libMesh::ParsedFEMFunctionParameter< T >::get().

577 {
578  libmesh_assert_greater (_subexpressions.size(), 0);
579 
580 #ifndef NDEBUG
581  bool found_var_name = false;
582 #endif
583  Output old_var_value(0.);
584 
585  for (const std::string & subexpression : _subexpressions)
586  {
587  const std::size_t varname_i =
588  find_name(inline_var_name, subexpression);
589  if (varname_i == std::string::npos)
590  continue;
591 
592  const std::size_t assignment_i =
593  subexpression.find(":", varname_i+1);
594 
595  libmesh_assert_not_equal_to(assignment_i, std::string::npos);
596 
597  libmesh_assert_equal_to(subexpression[assignment_i+1], '=');
598  for (std::size_t i = varname_i+1; i != assignment_i; ++i)
599  libmesh_assert_equal_to(subexpression[i], ' ');
600 
601  std::size_t end_assignment_i =
602  subexpression.find(";", assignment_i+1);
603 
604  libmesh_assert_not_equal_to(end_assignment_i, std::string::npos);
605 
606  std::string new_subexpression =
607  subexpression.substr(0, end_assignment_i+1).
608  append(inline_var_name);
609 
610 #ifdef LIBMESH_HAVE_FPARSER
611  // Parse and evaluate the new subexpression.
612  // Add the same constants as we used originally.
613  auto fp = std::make_unique<FunctionParserBase<Output>>();
614  fp->AddConstant("NaN", std::numeric_limits<Real>::quiet_NaN());
615  fp->AddConstant("pi", std::acos(Real(-1)));
616  fp->AddConstant("e", std::exp(Real(1)));
617  libmesh_error_msg_if
618  (fp->Parse(new_subexpression, variables) != -1, // -1 for success
619  "ERROR: FunctionParser is unable to parse modified expression: "
620  << new_subexpression << '\n' << fp->ErrorMsg());
621 
622  Output new_var_value = this->eval(*fp, new_subexpression, 0);
623 #ifdef NDEBUG
624  return new_var_value;
625 #else
626  if (found_var_name)
627  {
628  libmesh_assert_equal_to(old_var_value, new_var_value);
629  }
630  else
631  {
632  old_var_value = new_var_value;
633  found_var_name = true;
634  }
635 #endif
636 
637 #else
638  libmesh_error_msg("ERROR: This functionality requires fparser!");
639 #endif
640  }
641 
642  libmesh_assert(found_var_name);
643  return old_var_value;
644 }
Output eval(FunctionParserBase< Output > &parser, std::string_view libmesh_dbg_var(function_name), unsigned int libmesh_dbg_var(component_idx)) const
评估第 i 个 FunctionParser 并检查结果。
std::vector< std::string > _subexpressions
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
std::size_t find_name(std::string_view varname, std::string_view expr) const
用于解析变量名称的辅助函数。
template<typename Output >
void libMesh::ParsedFEMFunction< Output >::init_context ( const FEMContext &  c)
inlineoverridevirtual

初始化上下文。

参数
cFEMContext 对象的引用。

重载 libMesh::FEMFunctionBase< Output > .

在文件 parsed_fem_function.h488 行定义.

489 {
490  for (unsigned int v=0; v != _n_vars; ++v)
491  {
492  FEBase * elem_fe;
493  c.get_element_fe(v, elem_fe);
494  if (_n_requested_vars)
495  elem_fe->get_phi();
497  elem_fe->get_dphi();
498 #ifdef LIBMESH_ENABLE_SECOND_DERIVATIVES
500  elem_fe->get_d2phi();
501 #endif // LIBMESH_ENABLE_SECOND_DERIVATIVES
502  }
503 
504  if (_requested_normals)
505  {
506  FEBase * side_fe;
507  c.get_side_fe(0, side_fe);
508 
509  side_fe->get_normals();
510 
511  // FIXME: this is a hack to support normals at quadrature
512  // points; we don't support normals elsewhere.
513  side_fe->get_xyz();
514  }
515 }
template<typename Output >
void libMesh::FEMFunctionBase< Output >::operator() ( const FEMContext &  context,
const Point &  p,
DenseVector< Output > &  output 
)
inlineinherited

计算时间无关的向量值函数的评估函数。将输出值设置在传入的output DenseVector中。

参数
contextFEM上下文对象。
p坐标点。
output输出的向量。

在文件 fem_function_base.h153 行定义.

156 {
157  // 调用时间相关的函数,t=0。
158  this->operator()(context, p, 0., output);
159 }
virtual Output operator()(const FEMContext &, const Point &p, const Real time=0.)=0
计算坐标p和时间time(默认为0)处的标量函数值。
template<typename Output >
Output libMesh::ParsedFEMFunction< Output >::operator() ( const FEMContext &  c,
const Point &  p,
const Real  time = 0. 
)
inlineoverridevirtual

调用运算符,用于计算解析函数的值。

参数
cFEMContext 对象的引用。
p点的引用。
time时间,默认值为 0。
返回
返回解析函数的值。

实现了 libMesh::FEMFunctionBase< Output >.

在文件 parsed_fem_function.h529 行定义.

532 {
533  eval_args(c, p, time);
534 
535  return eval(*parsers[0], "f", 0);
536 }
Output eval(FunctionParserBase< Output > &parser, std::string_view libmesh_dbg_var(function_name), unsigned int libmesh_dbg_var(component_idx)) const
评估第 i 个 FunctionParser 并检查结果。
std::vector< std::unique_ptr< FunctionParserBase< Output > > > parsers
void eval_args(const FEMContext &c, const Point &p, const Real time)
用于计算函数参数的辅助函数。
template<typename Output>
void libMesh::ParsedFEMFunction< Output >::operator() ( const FEMContext &  c,
const Point &  p,
const Real  time,
DenseVector< Output > &  output 
)
inlineoverridevirtual

调用运算符,用于计算解析函数的值。

参数
cFEMContext 对象的引用。
p点的引用。
time时间。
output输出向量的引用。

实现了 libMesh::FEMFunctionBase< Output >.

在文件 parsed_fem_function.h543 行定义.

参考 libMesh::DenseVector< T >::size().

547 {
548  eval_args(c, p, time);
549 
550  unsigned int size = output.size();
551 
552  libmesh_assert_equal_to (size, parsers.size());
553 
554  for (unsigned int i=0; i != size; ++i)
555  output(i) = eval(*parsers[i], "f", i);
556 }
Output eval(FunctionParserBase< Output > &parser, std::string_view libmesh_dbg_var(function_name), unsigned int libmesh_dbg_var(component_idx)) const
评估第 i 个 FunctionParser 并检查结果。
std::vector< std::unique_ptr< FunctionParserBase< Output > > > parsers
void eval_args(const FEMContext &c, const Point &p, const Real time)
用于计算函数参数的辅助函数。
virtual unsigned int size() const overridefinal
Definition: dense_vector.h:111
template<typename Output >
ParsedFEMFunction< Output > & libMesh::ParsedFEMFunction< Output >::operator= ( const ParsedFEMFunction< Output > &  other)
inline

赋值运算符。

此类包含一个 const 引用,因此无法进行默认复制或移动赋值。我们手动实现了前者。

此类包含 unique_ptrs,因此无法进行默认复制构造或赋值。

可以进行默认移动和删除。

在文件 parsed_fem_function.h344 行定义.

参考 libMesh::ParsedFEMFunction< Output >::_sys.

345 {
346  // We can only be assigned another ParsedFEMFunction defined on the same System
347  libmesh_assert(&_sys == &other._sys);
348 
349  // Use copy-and-swap idiom
350  ParsedFEMFunction<Output> tmp(other);
351  std::swap(tmp, *this);
352  return *this;
353 }
template<typename Output >
void libMesh::ParsedFEMFunction< Output >::partial_reparse ( std::string  expression)
inlineprotected

用于重新解析表达式的辅助函数。

参数
expression新的解析表达式。

在文件 parsed_fem_function.h715 行定义.

参考 libMesh::Real.

716 {
717  _expression = std::move(expression);
718  _subexpressions.clear();
719  parsers.clear();
720 
721  size_t nextstart = 0, end = 0;
722 
723  while (end != std::string::npos)
724  {
725  // If we're past the end of the string, we can't make any more
726  // subparsers
727  if (nextstart >= _expression.size())
728  break;
729 
730  // If we're at the start of a brace delimited section, then we
731  // parse just that section:
732  if (_expression[nextstart] == '{')
733  {
734  nextstart++;
735  end = _expression.find('}', nextstart);
736  }
737  // otherwise we parse the whole thing
738  else
739  end = std::string::npos;
740 
741  // We either want the whole end of the string (end == npos) or
742  // a substring in the middle.
743  _subexpressions.push_back
744  (_expression.substr(nextstart, (end == std::string::npos) ?
745  std::string::npos : end - nextstart));
746 
747  // fparser can crash on empty expressions
748  libmesh_error_msg_if(_subexpressions.back().empty(),
749  "ERROR: FunctionParser is unable to parse empty expression.\n");
750 
751 
752 #ifdef LIBMESH_HAVE_FPARSER
753  // Parse (and optimize if possible) the subexpression.
754  // Add some basic constants, to Real precision.
755  auto fp = std::make_unique<FunctionParserBase<Output>>();
756  fp->AddConstant("NaN", std::numeric_limits<Real>::quiet_NaN());
757  fp->AddConstant("pi", std::acos(Real(-1)));
758  fp->AddConstant("e", std::exp(Real(1)));
759  libmesh_error_msg_if
760  (fp->Parse(_subexpressions.back(), variables) != -1, // -1 for success
761  "ERROR: FunctionParser is unable to parse expression: "
762  << _subexpressions.back() << '\n' << fp->ErrorMsg());
763  fp->Optimize();
764  parsers.push_back(std::move(fp));
765 #else
766  libmesh_error_msg("ERROR: This functionality requires fparser!");
767 #endif
768 
769  // If at end, use nextstart=maxSize. Else start at next
770  // character.
771  nextstart = (end == std::string::npos) ?
772  std::string::npos : end + 1;
773  }
774 }
std::vector< std::string > _subexpressions
std::vector< std::unique_ptr< FunctionParserBase< Output > > > parsers
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
const std::string & expression()
获取解析表达式。
template<typename Output >
void libMesh::ParsedFEMFunction< Output >::reparse ( std::string  expression)
inline

重新解析使用新表达式。

参数
expression新的解析表达式。

在文件 parsed_fem_function.h359 行定义.

参考自 libMesh::ParsedFEMFunction< Output >::ParsedFEMFunction().

360 {
361  variables = "x";
362 #if LIBMESH_DIM > 1
363  variables += ",y";
364 #endif
365 #if LIBMESH_DIM > 2
366  variables += ",z";
367 #endif
368  variables += ",t";
369 
370  for (unsigned int v=0; v != _n_vars; ++v)
371  {
372  const std::string & varname = _sys.variable_name(v);
373  std::size_t varname_i = find_name(varname, expression);
374 
375  // If we didn't find our variable name then let's go to the
376  // next.
377  if (varname_i == std::string::npos)
378  continue;
379 
380  _need_var[v] = true;
381  variables += ',';
382  variables += varname;
384  }
385 
386  for (unsigned int v=0; v != _n_vars; ++v)
387  {
388  const std::string & varname = _sys.variable_name(v);
389 
390  for (unsigned int d=0; d != LIBMESH_DIM; ++d)
391  {
392  std::string gradname = std::string("grad_") +
393  "xyz"[d] + '_' + varname;
394  std::size_t gradname_i = find_name(gradname, expression);
395 
396  // If we didn't find that gradient component of our
397  // variable name then let's go to the next.
398  if (gradname_i == std::string::npos)
399  continue;
400 
401  _need_var_grad[v*LIBMESH_DIM+d] = true;
402  variables += ',';
403  variables += gradname;
405  }
406  }
407 
408 #ifdef LIBMESH_ENABLE_SECOND_DERIVATIVES
409  for (unsigned int v=0; v != _n_vars; ++v)
410  {
411  const std::string & varname = _sys.variable_name(v);
412 
413  for (unsigned int d1=0; d1 != LIBMESH_DIM; ++d1)
414  for (unsigned int d2=0; d2 != LIBMESH_DIM; ++d2)
415  {
416  std::string hessname = std::string("hess_") +
417  "xyz"[d1] + "xyz"[d2] + '_' + varname;
418  std::size_t hessname_i = find_name(hessname, expression);
419 
420  // If we didn't find that hessian component of our
421  // variable name then let's go to the next.
422  if (hessname_i == std::string::npos)
423  continue;
424 
425  _need_var_hess[v*LIBMESH_DIM*LIBMESH_DIM+d1*LIBMESH_DIM+d2]
426  = true;
427  variables += ',';
428  variables += hessname;
430  }
431  }
432 #endif // LIBMESH_ENABLE_SECOND_DERIVATIVES
433 
434  {
435  std::size_t nx_i = find_name("n_x", expression);
436  std::size_t ny_i = find_name("n_y", expression);
437  std::size_t nz_i = find_name("n_z", expression);
438 
439  // If we found any requests for normal components then we'll
440  // compute normals
441  if (nx_i != std::string::npos ||
442  ny_i != std::string::npos ||
443  nz_i != std::string::npos)
444  {
445  _requested_normals = true;
446  variables += ',';
447  variables += "n_x";
448  if (LIBMESH_DIM > 1)
449  {
450  variables += ',';
451  variables += "n_y";
452  }
453  if (LIBMESH_DIM > 2)
454  {
455  variables += ',';
456  variables += "n_z";
457  }
458  }
459  }
460 
461  _spacetime.resize
462  (LIBMESH_DIM + 1 + _n_requested_vars +
464  (_requested_normals ? LIBMESH_DIM : 0) +
465  _additional_vars.size());
466 
467  // If additional vars were passed, append them to the string
468  // that we send to the function parser. Also add them to the
469  // end of our spacetime vector
470  unsigned int offset = LIBMESH_DIM + 1 + _n_requested_vars +
472 
473  for (auto i : index_range(_additional_vars))
474  {
475  variables += "," + _additional_vars[i];
476  // Initialize extra variables to the vector passed in or zero
477  // Note: The initial_vals vector can be shorter than the additional_vars vector
478  _spacetime[offset + i] =
479  (i < _initial_vals.size()) ? _initial_vals[i] : 0;
480  }
481 
482  this->partial_reparse(std::move(expression));
483 }
std::vector< bool > _need_var_grad
std::vector< Output > _initial_vals
std::vector< std::string > _additional_vars
void partial_reparse(std::string expression)
用于重新解析表达式的辅助函数。
std::vector< Output > _spacetime
std::vector< bool > _need_var_hess
std::size_t find_name(std::string_view varname, std::string_view expr) const
用于解析变量名称的辅助函数。
const std::string & expression()
获取解析表达式。
template<typename Output>
void libMesh::ParsedFEMFunction< Output >::set_inline_value ( std::string_view  inline_var_name,
Output  newval 
)
inline

更改内联变量的值。

参数
inline_var_name内联变量的名称。
newval新的内联变量值。
注解
以后,该变量值将在已定义该变量的每个子表达式中采用给定的常量值, 与输入变量无关。
当前仅在内联变量未在任何一个子表达式中重新定义时有效。

在文件 parsed_fem_function.h649 行定义.

参考自 libMesh::ParsedFEMFunctionParameter< T >::set().

651 {
652  libmesh_assert_greater (_subexpressions.size(), 0);
653 
654 #ifndef NDEBUG
655  bool found_var_name = false;
656 #endif
657  for (auto s : index_range(_subexpressions))
658  {
659  const std::string & subexpression = _subexpressions[s];
660  const std::size_t varname_i =
661  find_name(inline_var_name, subexpression);
662  if (varname_i == std::string::npos)
663  continue;
664 
665 #ifndef NDEBUG
666  found_var_name = true;
667 #endif
668 
669  const std::size_t assignment_i =
670  subexpression.find(":", varname_i+1);
671 
672  libmesh_assert_not_equal_to(assignment_i, std::string::npos);
673 
674  libmesh_assert_equal_to(subexpression[assignment_i+1], '=');
675  for (std::size_t i = varname_i+1; i != assignment_i; ++i)
676  libmesh_assert_equal_to(subexpression[i], ' ');
677 
678  std::size_t end_assignment_i =
679  subexpression.find(";", assignment_i+1);
680 
681  libmesh_assert_not_equal_to(end_assignment_i, std::string::npos);
682 
683  std::ostringstream new_subexpression;
684  new_subexpression << subexpression.substr(0, assignment_i+2)
685  << std::setprecision(std::numeric_limits<Output>::digits10+2)
686 #ifdef LIBMESH_USE_COMPLEX_NUMBERS
687  << '(' << newval.real() << '+'
688  << newval.imag() << 'i' << ')'
689 #else
690  << newval
691 #endif
692  << subexpression.substr(end_assignment_i,
693  std::string::npos);
694  _subexpressions[s] = new_subexpression.str();
695  }
696 
697  libmesh_assert(found_var_name);
698 
699  std::string new_expression;
700 
701  for (const auto & subexpression : _subexpressions)
702  {
703  new_expression += '{';
704  new_expression += subexpression;
705  new_expression += '}';
706  }
707 
708  this->partial_reparse(new_expression);
709 }
std::vector< std::string > _subexpressions
void partial_reparse(std::string expression)
用于重新解析表达式的辅助函数。
std::size_t find_name(std::string_view varname, std::string_view expr) const
用于解析变量名称的辅助函数。

类成员变量说明

template<typename Output = Number>
std::vector<std::string> libMesh::ParsedFEMFunction< Output >::_additional_vars
private

在文件 parsed_fem_function.h283 行定义.

template<typename Output = Number>
std::string libMesh::ParsedFEMFunction< Output >::_expression
private
template<typename Output = Number>
std::vector<Output> libMesh::ParsedFEMFunction< Output >::_initial_vals
private

在文件 parsed_fem_function.h284 行定义.

template<typename Output = Number>
unsigned int libMesh::ParsedFEMFunction< Output >::_n_requested_grad_components
private

在文件 parsed_fem_function.h255 行定义.

template<typename Output = Number>
unsigned int libMesh::ParsedFEMFunction< Output >::_n_requested_hess_components
private

在文件 parsed_fem_function.h255 行定义.

template<typename Output = Number>
unsigned int libMesh::ParsedFEMFunction< Output >::_n_requested_vars
private

在文件 parsed_fem_function.h255 行定义.

template<typename Output = Number>
unsigned int libMesh::ParsedFEMFunction< Output >::_n_vars
private

在文件 parsed_fem_function.h255 行定义.

template<typename Output = Number>
std::vector<bool> libMesh::ParsedFEMFunction< Output >::_need_var
private

在文件 parsed_fem_function.h270 行定义.

template<typename Output = Number>
std::vector<bool> libMesh::ParsedFEMFunction< Output >::_need_var_grad
private

在文件 parsed_fem_function.h273 行定义.

template<typename Output = Number>
std::vector<bool> libMesh::ParsedFEMFunction< Output >::_need_var_hess
private

在文件 parsed_fem_function.h278 行定义.

template<typename Output = Number>
bool libMesh::ParsedFEMFunction< Output >::_requested_normals
private

在文件 parsed_fem_function.h259 行定义.

template<typename Output = Number>
std::vector<Output> libMesh::ParsedFEMFunction< Output >::_spacetime
private

在文件 parsed_fem_function.h265 行定义.

template<typename Output = Number>
std::vector<std::string> libMesh::ParsedFEMFunction< Output >::_subexpressions
private

在文件 parsed_fem_function.h254 行定义.

template<typename Output = Number>
const System& libMesh::ParsedFEMFunction< Output >::_sys
private
template<typename Output = Number>
std::vector<std::unique_ptr<FunctionParserBase<Output> > > libMesh::ParsedFEMFunction< Output >::parsers
private

在文件 parsed_fem_function.h261 行定义.

template<typename Output = Number>
std::vector<char*> libMesh::ParsedFEMFunction< Output >::parsers
private

在文件 parsed_fem_function.h263 行定义.

template<typename Output = Number>
std::string libMesh::ParsedFEMFunction< Output >::variables
private

在文件 parsed_fem_function.h282 行定义.


该类的文档由以下文件生成: