Line data Source code
1 : //* This file is part of the MOOSE framework 2 : //* https://mooseframework.inl.gov 3 : //* 4 : //* All rights reserved, see COPYRIGHT for full restrictions 5 : //* https://github.com/idaholab/moose/blob/master/COPYRIGHT 6 : //* 7 : //* Licensed under LGPL 2.1, please see LICENSE for details 8 : //* https://www.gnu.org/licenses/lgpl-2.1.html 9 : 10 : #include "MultiAppVectorPostprocessorTransfer.h" 11 : 12 : // MOOSE includes 13 : #include "MooseTypes.h" 14 : #include "FEProblem.h" 15 : #include "MultiApp.h" 16 : 17 : // libMesh 18 : #include "libmesh/meshfree_interpolation.h" 19 : #include "libmesh/system.h" 20 : 21 : registerMooseObject("MooseApp", MultiAppVectorPostprocessorTransfer); 22 : 23 : InputParameters 24 14361 : MultiAppVectorPostprocessorTransfer::validParams() 25 : { 26 14361 : InputParameters params = MultiAppTransfer::validParams(); 27 57444 : params.addRequiredParam<PostprocessorName>( 28 : "postprocessor", "The name of the Postprocessors on the sub-app to transfer from/to."); 29 57444 : params.addRequiredParam<VectorPostprocessorName>("vector_postprocessor", 30 : "The name of the VectorPostprocessor in " 31 : "the MultiApp to transfer values " 32 : "from/to."); 33 57444 : params.addRequiredParam<std::string>( 34 : "vector_name", "Named vector quantity to transfer from/to in VectorPostprocessor."); 35 14361 : params.addClassDescription("This transfer distributes the N values of a " 36 : "VectorPostprocessor to Postprocessors located in " 37 : "N sub-apps or" 38 : " collects Postprocessor values from N sub-apps " 39 : "into a VectorPostprocessor"); 40 14361 : MultiAppTransfer::addUserObjectExecutionCheckParam(params); 41 : 42 14361 : return params; 43 0 : } 44 : 45 48 : MultiAppVectorPostprocessorTransfer::MultiAppVectorPostprocessorTransfer( 46 48 : const InputParameters & parameters) 47 : : MultiAppTransfer(parameters), 48 48 : _sub_pp_name(getParam<PostprocessorName>("postprocessor")), 49 96 : _master_vpp_name(getParam<VectorPostprocessorName>("vector_postprocessor")), 50 144 : _vector_name(getParam<std::string>("vector_name")) 51 : { 52 48 : if (_directions.size() != 1) 53 0 : paramError("direction", "This transfer is only unidirectional"); 54 48 : } 55 : 56 : void 57 24 : MultiAppVectorPostprocessorTransfer::executeToMultiapp() 58 : { 59 : const VectorPostprocessorValue & vpp = 60 24 : getToMultiApp()->problemBase().getVectorPostprocessorValueByName(_master_vpp_name, 61 : _vector_name); 62 : 63 : // Execute VPP if it was specified to execute on transfers 64 24 : checkParentAppUserObjectExecuteOn(_master_vpp_name); 65 24 : _fe_problem.computeUserObjectByName(EXEC_TRANSFER, Moose::PRE_AUX, _master_vpp_name); 66 24 : _fe_problem.computeUserObjectByName(EXEC_TRANSFER, Moose::POST_AUX, _master_vpp_name); 67 : 68 24 : if (vpp.size() != getToMultiApp()->numGlobalApps()) 69 0 : mooseError("VectorPostprocessor ", 70 : _master_vpp_name, 71 : " and number of sub-apps do not match: ", 72 0 : vpp.size(), 73 : "/", 74 0 : getToMultiApp()->numGlobalApps()); 75 : 76 72 : for (unsigned int i = 0; i < getToMultiApp()->numGlobalApps(); ++i) 77 48 : if (getToMultiApp()->hasLocalApp(i)) 78 28 : getToMultiApp()->appProblemBase(i).setPostprocessorValueByName(_sub_pp_name, vpp[i]); 79 24 : } 80 : 81 : void 82 24 : MultiAppVectorPostprocessorTransfer::executeFromMultiapp() 83 : { 84 : const VectorPostprocessorValue & vpp = 85 24 : getFromMultiApp()->problemBase().getVectorPostprocessorValueByName(_master_vpp_name, 86 : _vector_name); 87 24 : errorIfObjectExecutesOnTransferInSourceApp(_sub_pp_name); 88 : 89 20 : if (vpp.size() != getFromMultiApp()->numGlobalApps()) 90 0 : mooseError("VectorPostprocessor ", 91 : _master_vpp_name, 92 : " and number of sub-apps do not match: ", 93 0 : vpp.size(), 94 : "/", 95 0 : getFromMultiApp()->numGlobalApps()); 96 : 97 20 : VectorPostprocessorValue value(getFromMultiApp()->numGlobalApps(), 0.0); 98 60 : for (unsigned int i = 0; i < getFromMultiApp()->numGlobalApps(); ++i) 99 : { 100 : // To avoid duplication and thus a wrong pp value after summing value accross procs, we should 101 : // ensure that value[i] is only set by one procs. To do this, we check isFirstLocalRank to see 102 : // if the current proc is the first rank that subapp i lives on. 103 40 : if (getFromMultiApp()->hasLocalApp(i) && getFromMultiApp()->isFirstLocalRank()) 104 20 : value[i] = getFromMultiApp()->appProblemBase(i).getPostprocessorValueByName(_sub_pp_name); 105 : } 106 : 107 : // Sum to distribute entries of 'value' accross all procs 108 60 : for (auto & v : value) 109 40 : _communicator.sum(v); 110 : 111 40 : getFromMultiApp()->problemBase().setVectorPostprocessorValueByName( 112 20 : _master_vpp_name, _vector_name, value); 113 20 : } 114 : 115 : void 116 48 : MultiAppVectorPostprocessorTransfer::execute() 117 : { 118 240 : TIME_SECTION( 119 : "MultiAppVectorPostprocessorTransfer::execute()", 5, "Transferring a vector postprocessor"); 120 : 121 48 : if (_current_direction == FROM_MULTIAPP) 122 24 : executeFromMultiapp(); 123 : else 124 24 : executeToMultiapp(); 125 44 : }