preCICE v3.1.2
Loading...
Searching...
No Matches
WatchPoint.cpp
Go to the documentation of this file.
1#include <Eigen/Core>
2#include <algorithm>
3#include <limits>
4#include <memory>
5#include <ostream>
6#include <utility>
7
8#include "WatchPoint.hpp"
10#include "com/SharedPointer.hpp"
11#include "logging/LogMacros.hpp"
12#include "mapping/Polation.hpp"
13#include "mesh/Data.hpp"
14#include "mesh/Edge.hpp"
15#include "mesh/Mesh.hpp"
16#include "mesh/Triangle.hpp"
17#include "mesh/Vertex.hpp"
19#include "utils/IntraComm.hpp"
20#include "utils/assertion.hpp"
21
22namespace precice::impl {
23
25 Eigen::VectorXd pointCoords,
26 mesh::PtrMesh meshToWatch,
27 const std::string &exportFilename)
28 : _point(std::move(pointCoords)),
29 _mesh(std::move(meshToWatch)),
30 _txtWriter(exportFilename)
31{
33 PRECICE_ASSERT(_point.size() == _mesh->getDimensions(), _point.size(),
34 _mesh->getDimensions());
35
36 io::TXTTableWriter::DataType vectorType = _mesh->getDimensions() == 2
40 _txtWriter.addData("Coordinate", vectorType);
41 for (size_t i = 0; i < _mesh->data().size(); i++) {
42 _dataToExport.push_back(_mesh->data()[i]);
43 if (_dataToExport[i]->getDimensions() > 1) {
44 _txtWriter.addData(_dataToExport[i]->getName(), vectorType);
45 } else {
47 }
48 }
49}
50
52{
53 return _mesh;
54}
55
57{
59
60 if (_mesh->nVertices() > 0) {
61 auto match = _mesh->index().findCellOrProjection(_point, 4);
62 _shortestDistance = match.polation.distance();
63 _interpolation = std::make_unique<mapping::Polation>(std::move(match.polation));
64 }
65
69 }
70
72 int closestRank = 0;
73 double closestDistanceGlobal = _shortestDistance;
74 double closestDistanceLocal = std::numeric_limits<double>::max();
75 for (Rank secondaryRank : utils::IntraComm::allSecondaryRanks()) {
76 utils::IntraComm::getCommunication()->receive(closestDistanceLocal, secondaryRank);
77 if (closestDistanceLocal < closestDistanceGlobal) {
78 closestDistanceGlobal = closestDistanceLocal;
79 closestRank = secondaryRank;
80 }
81 }
82 _isClosest = closestRank == 0;
83 for (Rank secondaryRank : utils::IntraComm::allSecondaryRanks()) {
84 utils::IntraComm::getCommunication()->send(closestRank == secondaryRank, secondaryRank);
85 }
86 }
87
88 PRECICE_DEBUG("Rank: {}, isClosest: {}", utils::IntraComm::getRank(), _isClosest);
89}
90
92 double time)
93{
94 if (!_isClosest) {
95 return;
96 }
97
98 _txtWriter.writeData("Time", time);
99 // Export watch point coordinates
100 Eigen::VectorXd coords = Eigen::VectorXd::Constant(_mesh->getDimensions(), 0.0);
101 for (const auto &elem : _interpolation->getWeightedElements()) {
102 coords += elem.weight * _mesh->vertex(elem.vertexID).getCoords();
103 }
104 if (coords.size() == 2) {
105 _txtWriter.writeData("Coordinate", Eigen::Vector2d(coords));
106 } else {
107 _txtWriter.writeData("Coordinate", Eigen::Vector3d(coords));
108 }
109 // Export watch point data
110 for (auto &elem : _dataToExport) {
111 if (elem->getDimensions() > 1) {
112 Eigen::VectorXd toExport = Eigen::VectorXd::Zero(_mesh->getDimensions());
113 getValue(toExport, elem);
114 if (coords.size() == 2) {
115 _txtWriter.writeData(elem->getName(), Eigen::Vector2d(toExport));
116 } else {
117 _txtWriter.writeData(elem->getName(), Eigen::Vector3d(toExport));
118 }
119
120 } else {
121 double valueToExport = 0.0;
122 getValue(valueToExport, elem);
123 _txtWriter.writeData(elem->getName(), valueToExport);
124 }
125 }
126}
127
129 Eigen::VectorXd &value,
130 mesh::PtrData & data)
131{
132 int dim = _mesh->getDimensions();
133 Eigen::VectorXd temp(dim);
134 const Eigen::VectorXd &values = data->values();
135 for (const auto &elem : _interpolation->getWeightedElements()) {
136 int offset = elem.vertexID * dim;
137 for (int i = 0; i < dim; i++) {
138 temp[i] = values[offset + i];
139 }
140 temp *= elem.weight;
141 value += temp;
142 }
143}
144
146 double & value,
147 mesh::PtrData &data)
148{
149 const Eigen::VectorXd &values = data->values();
150 for (const auto &elem : _interpolation->getWeightedElements()) {
151 value += elem.weight * values[elem.vertexID];
152 }
153}
154
155} // namespace precice::impl
#define PRECICE_DEBUG(...)
Definition LogMacros.hpp:64
#define PRECICE_TRACE(...)
Definition LogMacros.hpp:95
#define PRECICE_ASSERT(...)
Definition assertion.hpp:87
void getValue(Eigen::VectorXd &value, mesh::PtrData &data)
void exportPointData(double time)
Writes one line with data of the watchpoint into the output file.
std::vector< mesh::PtrData > _dataToExport
io::TXTTableWriter _txtWriter
WatchPoint(Eigen::VectorXd pointCoords, mesh::PtrMesh meshToWatch, const std::string &exportFilename)
Constructor.
const mesh::PtrMesh & mesh() const
std::unique_ptr< mapping::Polation > _interpolation
bool _isClosest
Holds the information if this processor is the closest.
DataType
Constants defining possible data types to be written.
void addData(const std::string &name, DataType type)
Adds a data entry to the table.
void writeData(const std::string &name, int value)
Writes a integral scalar data value associated to the entry name.
static Rank getRank()
Current rank.
Definition IntraComm.cpp:42
static bool isPrimary()
True if this process is running the primary rank.
Definition IntraComm.cpp:52
static auto allSecondaryRanks()
Returns an iterable range over salve ranks [1, _size)
Definition IntraComm.hpp:37
static bool isSecondary()
True if this process is running a secondary rank.
Definition IntraComm.cpp:57
static com::PtrCommunication & getCommunication()
Intra-participant communication.
Definition IntraComm.hpp:31
T max(T... args)
int Rank
Definition Types.hpp:37
STL namespace.