Real Q2PBorehole::computeQpResidual() { const Real character = _character.value(_t, _q_point[_qp]); if (character == 0.0) return 0.0; const Real bh_pressure = _p_bot + _unit_weight * (_q_point[_qp] - _bottom_point); // really want to use _q_point instaed of _current_point, i think?! // Get the ID we initially assigned to this point const unsigned current_dirac_ptid = currentPointCachedID(); // If getting the ID failed, fall back to the old bodge! // if (current_dirac_ptid == libMesh::invalid_uint) // current_dirac_ptid = (_zs.size() > 2) ? 1 : 0; Real outflow(0.0); // this is the flow rate from porespace out of the system Real wc(0.0); if (current_dirac_ptid > 0) // contribution from half-segment "behind" this point (must have >1 point for // current_dirac_ptid>0) { wc = wellConstant(_permeability[0], _rot_matrix[current_dirac_ptid - 1], _half_seg_len[current_dirac_ptid - 1], _current_elem, _rs[current_dirac_ptid]); if ((character < 0.0 && _pp[_i] < bh_pressure) || (character > 0.0 && _pp[_i] > bh_pressure)) // injection, so outflow<0 || // production, so outflow>0 outflow += _test[_i][_qp] * std::abs(character) * wc * _mobility[_i] * (_pp[_i] - bh_pressure); } if (current_dirac_ptid + 1 < _zs.size() || _zs.size() == 1) // contribution from half-segment "ahead of" this point, or we only have one point { wc = wellConstant(_permeability[0], _rot_matrix[current_dirac_ptid], _half_seg_len[current_dirac_ptid], _current_elem, _rs[current_dirac_ptid]); if ((character < 0.0 && _pp[_i] < bh_pressure) || (character > 0.0 && _pp[_i] > bh_pressure)) // injection, so outflow<0 || // production, so outflow>0 outflow += _test[_i][_qp] * std::abs(character) * wc * _mobility[_i] * (_pp[_i] - bh_pressure); } _total_outflow_mass.add( outflow * _dt); // this is not thread safe, but DiracKernel's aren't currently threaded return outflow; }
Real CachingPointSource::computeQpResidual() { // Grab the user-defined ID for the Dirac point we are currently on. unsigned id = currentPointCachedID(); // If looking up the ID failed, we can't continue. if (id == libMesh::invalid_uint) mooseError("User id for point " << _current_point << " is " << id); // This is negative because it's a forcing function that has been // brought over to the left side. The value of the forcing is equal // to the ID of the point in this simple example. return -_test[_i][_qp] * static_cast<Real>(id); }
Real Q2PBorehole::jac(unsigned int jvar) { if (_i != _j) return 0.0; const Real character = _character.value(_t, _q_point[_qp]); if (character == 0.0) return 0.0; const Real bh_pressure = _p_bot + _unit_weight * (_q_point[_qp] - _bottom_point); // really want to use _q_point instaed of _current_point, i think?! const Real phi = 1; // Get the ID we initially assigned to this point const unsigned current_dirac_ptid = currentPointCachedID(); // If getting the ID failed, fall back to the old bodge! // if (current_dirac_ptid == libMesh::invalid_uint) // current_dirac_ptid = (_zs.size() > 2) ? 1 : 0; Real outflowp(0.0); const bool deriv_wrt_pp = (_var_is_pp && (jvar == _var.number())) || (!_var_is_pp && (jvar == _other_var_num)); Real wc(0.0); if (current_dirac_ptid > 0) // contribution from half-segment "behind" this point { wc = wellConstant(_permeability[0], _rot_matrix[current_dirac_ptid - 1], _half_seg_len[current_dirac_ptid - 1], _current_elem, _rs[current_dirac_ptid]); if ((character < 0.0 && _pp[_i] < bh_pressure) || (character > 0.0 && _pp[_i] > bh_pressure)) { // injection, so outflow<0 || // production, so outflow>0 if (deriv_wrt_pp) outflowp += std::abs(character) * wc * (_mobility[_i] * phi + _dmobility_dp[_i] * phi * (_pp[_i] - bh_pressure)); else outflowp += std::abs(character) * wc * _dmobility_ds[_i] * phi * (_pp[_i] - bh_pressure); } } if (current_dirac_ptid < _zs.size() - 1 || _zs.size() == 1) // contribution from half-segment "ahead of" this point { wc = wellConstant(_permeability[0], _rot_matrix[current_dirac_ptid], _half_seg_len[current_dirac_ptid], _current_elem, _rs[current_dirac_ptid]); if ((character < 0.0 && _pp[_i] < bh_pressure) || (character > 0.0 && _pp[_i] > bh_pressure)) { // injection, so outflow<0 || // production, so outflow>0 if (deriv_wrt_pp) outflowp += std::abs(character) * wc * (_mobility[_i] * phi + _dmobility_dp[_i] * phi * (_pp[_i] - bh_pressure)); else outflowp += std::abs(character) * wc * _dmobility_ds[_i] * phi * (_pp[_i] - bh_pressure); } } return _test[_i][_qp] * outflowp; }