www.mooseframework.org
DiscreteNucleationFromFile.C
Go to the documentation of this file.
1 //* This file is part of the MOOSE framework
2 //* https://www.mooseframework.org
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 
11 #include "MooseMesh.h"
12 #include "SystemBase.h"
13 
14 #include <algorithm>
15 
17 
20 {
22  params.addClassDescription(
23  "Manages the list of currently active nucleation sites and adds new "
24  "sites according to a predetermined list from a CSV file (use this with sync_times).");
25  params.addRequiredParam<FileName>(
26  "file",
27  "CSV file with (time, x, y, z) coordinates for nucleation events and optionally radius.");
28  params.addRequiredParam<Real>("hold_time", "Time to keep each nucleus active");
29  params.addParam<Real>("tolerance", 1e-9, "Tolerance for determining insertion time");
30  params.addRangeCheckedParam<Real>("radius", "radius > 0.0", "fixed radius (if using)");
31 
32  return params;
33 }
34 
36  : DiscreteNucleationInserterBase(parameters),
37  _hold_time(getParam<Real>("hold_time")),
38  _reader(getParam<FileName>("file")),
39  _history_pointer(0),
40  _tol(getParam<Real>("tolerance")),
41  _nucleation_rate(0.0),
42  _fixed_radius(isParamValid("radius")),
43  _radius(_fixed_radius ? getParam<Real>("radius") : 0)
44 {
45  _reader.read();
46 
47  auto & names = _reader.getNames();
48  auto & data = _reader.getData();
49 
50  const std::size_t rows = data[0].size();
51  _nucleation_history.resize(rows);
52 
53  bool found_time = false;
54  bool found_x = false;
55  bool found_y = false;
56  bool found_z = false;
57  bool found_r = false;
58 
59  for (std::size_t i = 0; i < names.size(); ++i)
60  {
61  // make sure all data columns have the same length
62  if (data[i].size() != rows)
63  paramError("file", "Mismatching column lengths in file");
64 
65  if (names[i] == "time")
66  {
67  for (std::size_t j = 0; j < rows; ++j)
68  _nucleation_history[j].time = data[i][j];
69  found_time = true;
70  }
71  else if (names[i] == "x")
72  {
73  for (std::size_t j = 0; j < rows; ++j)
74  _nucleation_history[j].center(0) = data[i][j];
75  found_x = true;
76  }
77  else if (names[i] == "y")
78  {
79  for (std::size_t j = 0; j < rows; ++j)
80  _nucleation_history[j].center(1) = data[i][j];
81  found_y = true;
82  }
83  else if (names[i] == "z")
84  {
85  for (std::size_t j = 0; j < rows; ++j)
86  _nucleation_history[j].center(2) = data[i][j];
87  found_z = true;
88  }
89  else if (names[i] == "r")
90  {
91  for (std::size_t j = 0; j < rows; ++j)
92  _nucleation_history[j].radius = data[i][j];
93  found_r = true;
94  }
95  if (_fixed_radius)
96  for (std::size_t j = 0; j < rows; ++j)
98  }
99 
100  // check if all required columns were found
101  if (!found_time)
102  paramError("file", "Missing 'time' column in file");
103  if (!found_x)
104  paramError("file", "Missing 'x' column in file");
105  if (!found_y && _mesh.dimension() >= 2)
106  paramError("file", "Missing 'y' column in file");
107  if (!found_z && _mesh.dimension() >= 3)
108  paramError("file", "Missing 'z' column in file");
109  if (!found_r && !_fixed_radius)
110  paramError("file", "Missing 'r' column in file");
111 
112  // sort the nucleation history primarily according to time
113  std::sort(_nucleation_history.begin(),
114  _nucleation_history.end(),
115  [](NucleusLocation a, NucleusLocation b) { return a.time < b.time; });
116 }
117 
118 void
120 {
121  // clear insertion and deletion counter
122  _changes_made = {0, 0};
123 
124  // expire entries from the local nucleus list (if the current time step converged)
126  {
127  unsigned int i = 0;
128  while (i < _global_nucleus_list.size())
129  {
130  if (_global_nucleus_list[i].time - _tol <= _fe_problem.time())
131  {
132  // remove entry (by replacing with last element and shrinking size by one)
134  _global_nucleus_list.pop_back();
135  _changes_made.second++;
136  }
137  else
138  ++i;
139  }
140  }
141 
142  // check if it is time to insert from the nucleus history
143  while (_history_pointer < _nucleation_history.size() &&
145  {
146  NucleusLocation nucleus;
148  nucleus.center = _nucleation_history[_history_pointer].center;
149  nucleus.radius = _nucleation_history[_history_pointer].radius;
150 
151  _global_nucleus_list.push_back(nucleus);
152 
153  _changes_made.first++;
155  }
156 }
157 
158 void
160 {
161  // no communication necessary as all ranks have the full nucleus history from the
162  // DelimitedFileReader
163  _update_required = _changes_made.first > 0 || _changes_made.second > 0;
164 }
registerMooseObject("PhaseFieldApp", DiscreteNucleationFromFile)
NucleusChanges _changes_made
count the number of nucleus insertions and deletions
This UserObject manages the insertion and expiration of nuclei in the simulation domain.
virtual Real & time() const
const Real radius
virtual bool converged(const unsigned int nl_sys_num)
void addParam(const std::string &name, const std::initializer_list< typename T::value_type > &value, const std::string &doc_string)
const std::vector< std::vector< double > > & getData() const
NucleusList _nucleation_history
Total nucleation history read from file.
MooseUtils::DelimitedFileReader _reader
CSV file to read.
static InputParameters validParams()
A nucleus has an expiration time, a location, and a size.
void addRequiredParam(const std::string &name, const std::string &doc_string)
This UserObject manages the insertion and expiration of nuclei in the simulation domain it manages a ...
virtual unsigned int dimension() const
SystemBase & _sys
void paramError(const std::string &param, Args... args) const
unsigned int number() const
const std::vector< std::string > & getNames() const
bool _fixed_radius
Is a fixed radius or variable radius used?
bool _update_required
is a map update required
DiscreteNucleationFromFile(const InputParameters &parameters)
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
FEProblemBase & _fe_problem
const Real _radius
hold the radius of the nucleus
NucleusList & _global_nucleus_list
the global list of all nuclei over all processors
const Real _hold_time
Duration of time each nucleus is kept active after insertion.
std::size_t _history_pointer
pointer to the next nucleation event in the history
const Real _tol
tolerance for determining insertion time
void addClassDescription(const std::string &doc_string)
static const std::complex< double > j(0, 1)
Complex number "j" (also known as "i")
void addRangeCheckedParam(const std::string &name, const T &value, const std::string &parsed_function, const std::string &doc_string)
MooseMesh & _mesh
static const std::string center
Definition: NS.h:28