MAST
indicator_function_constrain_dofs.cpp
Go to the documentation of this file.
1 /*
2  * MAST: Multidisciplinary-design Adaptation and Sensitivity Toolkit
3  * Copyright (C) 2013-2019 Manav Bhatia
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2.1 of the License, or (at your option) any later version.
9  *
10  * This library is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with this library; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18  */
19 
20 // MAST includes
24 #include "base/nonlinear_system.h"
26 
27 
28 // libMesh includes
29 #include "libmesh/dof_map.h"
30 
31 
32 
35  MAST::FieldFunction<Real>& level_set,
37 MAST::LevelSetConstrainDofs(sys, level_set),
38 _indicator (indicator) {
39 
40 }
41 
42 
43 
45 
46 }
47 
48 
49 
50 void
52 
53  // first constrain dofs based on level-set
55 
56  // now, we add additional constraints based on indicator function
57  MAST::NonlinearSystem& nonlin_sys = _sys.system();
58 
59  libMesh::DofMap& dof_map = nonlin_sys.get_dof_map();
60 
61  libMesh::MeshBase::const_element_iterator el =
62  nonlin_sys.get_mesh().active_local_elements_begin();
63  const libMesh::MeshBase::const_element_iterator end_el =
64  nonlin_sys.get_mesh().active_local_elements_end();
65 
66 
67  std::vector<libMesh::dof_id_type>
68  dof_indices;
69  std::set<libMesh::dof_id_type>
70  exclude_dof_indices,
71  constrained_dof_indices;
72 
73  bool
74  exclude_elem = true,
75  constrain_elem = true;
76 
78  nd_vals,
79  vec = RealVectorX::Zero(1);
80 
81  Real
82  tol = 1.e-10;
83 
84  // our intent is to constrain only those dofs that belong to elements
85  // where all nodes have zero indicator function value
86  for ( ; el != end_el; ++el) {
87 
88  const libMesh::Elem* elem = *el;
89  _intersection->init(_level_set, *elem, nonlin_sys.time,
90  nonlin_sys.get_mesh().max_elem_id(),
91  nonlin_sys.get_mesh().max_node_id());
92 
93  nd_vals.setZero(elem->n_nodes());
94  for (unsigned int i=0; i<elem->n_nodes(); i++) {
95  _indicator(elem->node_ref(i), nonlin_sys.time, vec);
96  nd_vals(i) = vec(0);
97  }
98 
99  // if the element is entirely on the negative side of the level set,
100  // we will constrain all dofs of the element to zero
101  //
102  // if any of the nodes have a positive value, we will not constrain
103  // the element
104  if (nd_vals.maxCoeff() > tol)
105  constrain_elem = false;
106  else
107  constrain_elem = true;
108 
109  //
110  // we also exclude all dofs from elements with atleast one node
111  // on it that belongs to positive indicator
112  //
113  if (_intersection->if_elem_has_boundary() && nd_vals.maxCoeff() > tol)
114  exclude_elem = true;
115  else
116  exclude_elem = false;
117 
118  //
119  // now populate the dof index vectors
120  //
121  if (constrain_elem || exclude_elem) {
122 
123  dof_indices.clear();
124  dof_map.dof_indices(elem, dof_indices);
125 
126  if (constrain_elem)
127  for (unsigned int i=0; i<dof_indices.size(); i++)
128  constrained_dof_indices.insert(dof_indices[i]);
129 
130  if (exclude_elem)
131  for (unsigned int i=0; i<dof_indices.size(); i++)
132  exclude_dof_indices.insert(dof_indices[i]);
133  }
134 
135  _intersection->clear();
136  }
137 
138  // create a set so that we only deal with unique set of ids.
139  dof_indices.clear();
140 
141  // now, constrain everythign in the set
142  std::set<libMesh::dof_id_type>::const_iterator
143  dof_it = constrained_dof_indices.begin(),
144  dof_end = constrained_dof_indices.end();
145 
146  for ( ; dof_it != dof_end; dof_it++) {
147 
148  // if the dof is already Dirichlet constrained, then we do not
149  // add another constraint on it
150  if (!dof_map.is_constrained_dof(*dof_it) &&
151  !exclude_dof_indices.count(*dof_it)) {
152 
153  libMesh::DofConstraintRow c_row;
154  dof_map.add_constraint_row(*dof_it, c_row, true);
155  }
156  }
157 }
158 
159 
160 
MAST::SystemInitialization & _sys
MAST::FieldFunction< Real > & _level_set
MAST::NonlinearSystem & system()
constrains the dofs based on level set function.
This class implements a system for solution of nonlinear systems.
libMesh::Real Real
void init(const MAST::FieldFunction< Real > &phi, const libMesh::Elem &e, const Real t, unsigned int max_elem_id, unsigned int max_node_id)
virtual void constrain()
provides implementation of the libMesh::System::Constraint::constrain() virtual method ...
MAST::FieldFunction< RealVectorX > & _indicator
MAST::LevelSetIntersection * _intersection
Matrix< Real, Dynamic, 1 > RealVectorX
IndicatorFunctionConstrainDofs(MAST::SystemInitialization &sys, MAST::FieldFunction< Real > &level_set, MAST::FieldFunction< RealVectorX > &indicator)
virtual void constrain()
provides implementation of the libMesh::System::Constraint::constrain() virtual method ...
void clear()
clears the data structures