13#include "libmesh/utility.h"
24 "The file containing the coordinates of the points and their weightings that approximate the "
25 "line sink. The physical meaning of the weightings depend on the scenario, eg, they may be "
26 "borehole radii. Each line in the file must contain a space-separated weight and "
27 "coordinate, viz r x y z. For boreholes, the last point in the file is defined as the "
28 "borehole bottom, where the borehole pressure is bottom_pressure. If your file contains "
29 "just one point, you must also specify the line_length and line_direction parameters. Note "
30 "that you will get segementation faults if your points do not lie within your mesh!");
33 "reporter x-coordinate name of line sink. This uses the reporter syntax <reporter>/<name>. "
34 "Each point must adhere to the same requirements as those that would be given if using "
38 "reporter y-coordinate name of line sink. This uses the reporter syntax <reporter>/<name>. "
39 "Each point must adhere to the same requirements as those that would be given if using "
43 "reporter z-coordinate name of line sink. This uses the reporter syntax <reporter>/<name>. "
44 "Each point must adhere to the same requirements as those that would be given if using "
48 "reporter weight name of line sink. This uses the reporter syntax <reporter>/<name>. "
49 "Each point must adhere to the same requirements as those that would be given if using "
55 "Line length. Note this is only used if there is only one point in the point_file.");
58 RealVectorValue(0.0, 0.0, 1.0),
59 "Line direction. Note this is only used if there is only one point in the point_file.");
62 "Line base point x,y,z coordinates. This is the same format as a single-line point_file. "
63 "Note this is only used if there is no point file specified.");
64 params.
addClassDescription(
"Approximates a polyline sink in the mesh using a number of Dirac "
65 "point sinks with given weightings that are read from a file");
72 _line_length(getParam<Real>(
"line_length")),
73 _line_direction(getParam<RealVectorValue>(
"line_direction")),
74 _point_file(getParam<
std::string>(
"point_file")),
75 _x_coord(isParamValid(
"x_coord_reporter") ? &getReporterValue<
std::vector<Real>>(
78 _y_coord(isParamValid(
"y_coord_reporter") ? &getReporterValue<
std::vector<Real>>(
81 _z_coord(isParamValid(
"z_coord_reporter") ? &getReporterValue<
std::vector<Real>>(
84 _weight(isParamValid(
"weight_reporter")
87 _usingReporter(isParamValid(
"x_coord_reporter"))
91 const int checkInputFormat =
94 if (checkInputFormat > 1)
96 "PorousFlowLineGeometry: must specify only one of 'point_file' or 'line_base' or "
97 "reporter based input");
98 else if (checkInputFormat == 0)
101 "PorousFlowLineGeometry: must specify at least one of 'point_file' or 'line_base' or "
102 "reporter based input");
116 std::vector<Real> scratch;
119 if (scratch.size() >= 2)
121 _rs.push_back(scratch[0]);
122 _xs.push_back(scratch[1]);
123 if (scratch.size() >= 3)
124 _ys.push_back(scratch[2]);
127 if (scratch.size() >= 4)
128 _zs.push_back(scratch[3]);
142 "The value and coordinate vectors are a different size. \n"
143 "There must be one value per coordinate. If the sizes are \n"
144 "zero, the reporter or reporter may not have been initialized with data \n"
145 "before the Dirac Kernel is called. \n"
146 "Try setting \"execute_on = timestep_begin\" in the reporter being read. \n"
148 std::to_string(
_weight->size()) +
149 "; x_coord size = " + std::to_string(
_x_coord->size()) +
150 "; y_coord size = " + std::to_string(
_y_coord->size()) +
151 "; z_coord size = " + std::to_string(
_z_coord->size());
156 for (std::size_t i = 0; i <
_x_coord->size(); ++i)
167 _line_base = getParam<std::vector<Real>>(
"line_base");
170 "PorousFlowLineGeometry: wrong number of arguments - got ",
174 " '<weight> <x> [<y> [z]]'");
176 for (
size_t i =
_line_base.size(); i < 4; i++)
183 pl->enable_out_of_mesh_mode();
185 auto * elem = (*pl)(start);
189 paramError(
"line_base",
"base point ", start,
" lies outside the mesh");
195 paramError(
"line_length",
"length causes end point ", end,
" to lie outside the mesh");
204 const int num_pts =
_zs.size();
206 mooseError(
"PorousFlowLineGeometry: No points found in input.\nIf using reporters, make sure "
215 for (
unsigned int i = 0; i + 1 <
_xs.size(); ++i)
218 Utility::pow<2>(
_ys[i + 1] -
_ys[i]) +
219 Utility::pow<2>(
_zs[i + 1] -
_zs[i]));
221 mooseError(
"PorousFlowLineGeometry: zero-segment length detected at (x,y,z) = ",
250 std::vector<Elem *> elems;
251 std::vector<LineSegment> segs;
253 for (
size_t i = 0; i < segs.size(); i++)
256 auto & seg = segs[i];
257 if (seg.start() == seg.end())
260 auto middle = (seg.start() + seg.end()) * 0.5;
262 _xs.push_back(middle(0));
263 _ys.push_back(middle(1));
264 _zs.push_back(middle(2));
298 if (getline(ifs, line))
303 std::istringstream iss(line);
319 for (
unsigned int i = 0; i <
_x_coord->size(); i++)
Real f(Real x)
Test function for Brents method.
const ReporterMode REPORTER_MODE_REPLICATED
void ErrorVector unsigned int
void addPoint(const Elem *elem, Point p, unsigned id=libMesh::invalid_uint, Real value=1.0)
virtual void meshChanged() override
static InputParameters validParams()
void statefulPropertiesAllowed(bool)
void paramError(const std::string ¶m, Args... args) const
void mooseError(Args &&... args) const
bool isParamValid(const std::string &name) const
virtual unsigned int dimension() const
virtual std::unique_ptr< libMesh::PointLocatorBase > getPointLocator() const
const RealVectorValue _line_direction
Line direction. This is only used if there is only one borehole point.
std::vector< Real > _rs
Radii of the borehole.
static InputParameters validParams()
Creates a new PorousFlowLineGeometry This reads the file containing the lines of the form weight x y ...
std::vector< Real > _xs
x points of the borehole
std::vector< Real > _zs
z points of borehole
std::vector< Real > _ys
y points of the borehole
Point _bottom_point
The bottom point of the borehole (where bottom_pressure is defined)
PorousFlowLineGeometry(const InputParameters ¶meters)
const Real _line_length
Line length. This is only used if there is only one borehole point.
std::vector< Real > _line_base
alternative (to the point file data) line weight and start point.
bool parseNextLineReals(std::ifstream &ifs, std::vector< Real > &myvec)
Reads a space-separated line of floats from ifs and puts in myvec.
const std::vector< Real > *const _z_coord
std::vector< Real > _half_seg_len
0.5*(length of polyline segments between points)
const std::string _point_file
File defining the geometry of the borehole.
virtual void meshChanged() override
regenerate points in each cell if using line_base
const std::vector< Real > *const _y_coord
const std::vector< Real > *const _x_coord
const bool _usingReporter
virtual void addPoints() override
Add Dirac Points to the line sink.
virtual void initialSetup() override
const std::vector< Real > *const _weight
virtual MooseMesh & mesh()=0
void min(const T &r, T &o, Request &req) const
static constexpr dof_id_type invalid_id
const Parallel::Communicator & _communicator
void elementsIntersectedByLine(const Point &p0, const Point &p1, const MeshBase &mesh, const libMesh::PointLocatorBase &point_locator, std::vector< Elem * > &intersected_elems, std::vector< LineSegment > &segments)