14 using namespace MoFEM;
16 static char help[] =
"...\n\n";
54 :
public boost::enable_shared_from_this<Example::CommonData> {
59 return boost::shared_ptr<VectorDouble>(shared_from_this(),
60 &rhoAtIntegrationPts);
88 OpZero(boost::shared_ptr<CommonData> &common_data_ptr)
89 :
OpElement(
"rho", OPROW), commonDataPtr(common_data_ptr) {
90 std::fill(&doEntities[MBEDGE], &doEntities[MBMAXTYPE],
false);
99 OpFirst(boost::shared_ptr<CommonData> &common_data_ptr)
100 :
OpElement(
"rho", OPROW), commonDataPtr(common_data_ptr) {
101 std::fill(&doEntities[MBEDGE], &doEntities[MBMAXTYPE],
false);
111 OpSecond(boost::shared_ptr<CommonData> &common_data_ptr)
112 :
OpElement(
"rho", OPROW), commonDataPtr(common_data_ptr) {
113 std::fill(&doEntities[MBEDGE], &doEntities[MBMAXTYPE],
false);
126 CHKERR createCommonData();
129 CHKERR integrateElements();
144 constexpr
int order = 1;
154 commonDataPtr = boost::make_shared<CommonData>();
157 if (mField.get_comm_rank() == 0)
159 local_size = CommonData::LAST_ELEMENT;
164 commonDataPtr->petscVec =
createVectorMPI(mField.get_comm(), local_size,
165 CommonData::LAST_ELEMENT);
174 auto set_density = [&](
VectorAdaptor &&field_data,
double *xcoord,
175 double *ycoord,
double *zcoord) {
181 CHKERR mField.getInterface(field_blas);
195 "rho", commonDataPtr->getRhoAtIntegrationPtsPtr()));
221 CHKERR VecZeroEntries(commonDataPtr->petscVec);
228 CHKERR VecAssemblyBegin(commonDataPtr->petscVec);
229 CHKERR VecAssemblyEnd(commonDataPtr->petscVec);
238 CHKERR VecGetArrayRead(commonDataPtr->petscVec, &array);
239 if (mField.get_comm_rank() == 0) {
240 MOFEM_LOG_C(
"SELF", Sev::inform,
"Mass %6.4e", array[CommonData::ZERO]);
242 "First moment of inertia [ %6.4e, %6.4e, %6.4e ]",
243 array[CommonData::FIRST_X], array[CommonData::FIRST_Y],
244 array[CommonData::FIRST_Z]);
246 "Second moment of inertia [ %6.4e, %6.4e, %6.4e; %6.4e %6.4e; "
248 array[CommonData::SECOND_XX], array[CommonData::SECOND_XY],
249 array[CommonData::SECOND_XZ], array[CommonData::SECOND_YY],
250 array[CommonData::SECOND_YZ], array[CommonData::SECOND_ZZ]);
252 CHKERR VecRestoreArrayRead(commonDataPtr->petscVec, &array);
261 CHKERR VecGetArrayRead(commonDataPtr->petscVec, &array);
263 PetscBool test = PETSC_FALSE;
265 if (mField.get_comm_rank() == 0 && test) {
266 constexpr
double eps = 1e-8;
267 constexpr
double expected_volume = 1.;
268 constexpr
double expected_first_moment = 0.;
269 constexpr
double expected_second_moment = 1. / 12.;
270 if (std::abs(array[CommonData::ZERO] - expected_volume) >
eps)
272 "Wrong area %6.4e != %6.4e", expected_volume,
273 array[CommonData::ZERO]);
275 {CommonData::FIRST_X, CommonData::FIRST_Y, CommonData::FIRST_Z}) {
276 if (std::abs(array[
i] - expected_first_moment) >
eps)
278 "Wrong first moment %6.4e != %6.4e", expected_first_moment,
281 for (
auto i : {CommonData::SECOND_XX, CommonData::SECOND_YY,
282 CommonData::SECOND_ZZ}) {
283 if (std::abs(array[
i] - expected_second_moment) >
eps)
285 "Wrong second moment %6.4e != %6.4e", expected_second_moment,
289 CHKERR VecRestoreArrayRead(commonDataPtr->petscVec, &array);
296 int main(
int argc,
char *argv[]) {
299 const char param_file[] =
"param_file.petsc";
306 DMType dm_name =
"DMMOFEM";
333 if (
type == MBVERTEX) {
335 const int nb_integration_pts =
336 getGaussPts().size2();
337 auto t_w = getFTensor0IntegrationWeight();
339 commonDataPtr->rhoAtIntegrationPts);
340 const double volume = getMeasure();
343 double element_local_value = 0;
344 for (
int gg = 0; gg != nb_integration_pts; ++gg) {
345 element_local_value += t_w * t_rho * volume;
351 const int index = CommonData::ZERO;
352 CHKERR VecSetValue(commonDataPtr->petscVec, index, element_local_value,
363 const int nb_integration_pts = getGaussPts().size2();
364 auto t_w = getFTensor0IntegrationWeight();
366 commonDataPtr->rhoAtIntegrationPts);
368 getFTensor1CoordsAtGaussPts();
369 const double volume = getMeasure();
378 for (
int gg = 0; gg != nb_integration_pts; ++gg) {
380 t_s(
i) += t_w * t_rho * volume * t_x(
i);
388 constexpr std::array<int, 3> indices = {
389 CommonData::FIRST_X, CommonData::FIRST_Y, CommonData::FIRST_Z};
403 const int nb_integration_pts = getGaussPts().size2();
404 auto t_w = getFTensor0IntegrationWeight();
406 auto t_x = getFTensor1CoordsAtGaussPts();
407 const double volume = getMeasure();
410 std::array<double, 6> element_local_value;
411 std::fill(element_local_value.begin(), element_local_value.end(), 0.0);
415 &element_local_value[0], &element_local_value[1], &element_local_value[2],
416 &element_local_value[3], &element_local_value[4],
417 &element_local_value[5]);
423 for (
int gg = 0; gg != nb_integration_pts; ++gg) {
426 t_I(
i,
j) += (t_w * t_rho * volume) * (t_x(
i) ^ t_x(
j));
434 constexpr std::array<int, 6> indices = {
435 CommonData::SECOND_XX, CommonData::SECOND_XY, CommonData::SECOND_XZ,
436 CommonData::SECOND_YY, CommonData::SECOND_YZ, CommonData::SECOND_ZZ};
440 &element_local_value[0], ADD_VALUES);