29template <
typename Particle_T>
37 std::vector<std::vector<std::vector<std::unique_ptr<std::mutex>>>> &spatialLocks)
38 : _spatialLocks(spatialLocks) {}
60 template <
bool newton3,
class ContainerType,
class TriwiseFunctor>
65 std::vector<Particle_T *> bufferParticles;
66 const auto numOwnedBufferParticles = collectBufferParticles(bufferParticles, particleBuffers, haloParticleBuffers);
71#if SPDLOG_ACTIVE_LEVEL <= SPDLOG_LEVEL_TRACE
75 timerBufferBufferBuffer.
start();
79 remainderHelper3bBufferBufferBufferAoS(bufferParticles, numOwnedBufferParticles, f);
81#if SPDLOG_ACTIVE_LEVEL <= SPDLOG_LEVEL_TRACE
82 timerBufferBufferBuffer.
stop();
83 timerBufferBufferContainer.
start();
87 remainderHelper3bBufferBufferContainerAoS(bufferParticles, numOwnedBufferParticles, container, f);
89#if SPDLOG_ACTIVE_LEVEL <= SPDLOG_LEVEL_TRACE
90 timerBufferBufferContainer.
stop();
91 timerBufferContainerContainer.
start();
95 remainderHelper3bBufferContainerContainerAoS<newton3>(bufferParticles, numOwnedBufferParticles, container, f);
96#if SPDLOG_ACTIVE_LEVEL <= SPDLOG_LEVEL_TRACE
97 timerBufferContainerContainer.
stop();
101 AutoPasLog(TRACE,
"Timer Buffer <-> Buffer <-> Container : {}", timerBufferBufferContainer.
getTotalTime());
102 AutoPasLog(TRACE,
"Timer Buffer <-> Container <-> Container : {}", timerBufferContainerContainer.
getTotalTime());
109 std::vector<std::vector<std::vector<std::unique_ptr<std::mutex>>>> &_spatialLocks;
121 size_t collectBufferParticles(std::vector<Particle_T *> &bufferParticles,
125 auto cellToVec = [](
auto &cell) -> std::vector<Particle_T> & {
return cell._particles; };
127 const size_t numOwnedBufferParticles =
128 std::transform_reduce(particleBuffers.begin(), particleBuffers.end(), 0, std::plus<>(),
129 [&](
auto &vec) { return cellToVec(vec).size(); });
131 const size_t numHaloBufferParticles =
132 std::transform_reduce(haloParticleBuffers.begin(), haloParticleBuffers.end(), 0, std::plus<>(),
133 [&](
auto &vec) { return cellToVec(vec).size(); });
135 bufferParticles.reserve(numOwnedBufferParticles + numHaloBufferParticles);
138 for (
auto &buffer : particleBuffers) {
139 for (
auto &p : buffer._particles) {
140 bufferParticles.push_back(&p);
144 for (
auto &buffer : haloParticleBuffers) {
145 for (
auto &p : buffer._particles) {
146 bufferParticles.push_back(&p);
149 return numOwnedBufferParticles;
161 template <
class TriwiseFunctor>
162 void remainderHelper3bBufferBufferBufferAoS(
const std::vector<Particle_T *> &bufferParticles,
163 const size_t numOwnedBufferParticles, TriwiseFunctor *f) {
165 for (
auto i = 0; i < numOwnedBufferParticles; ++i) {
166 Particle_T &p1 = *bufferParticles[i];
168 for (
auto j = 0; j < bufferParticles.size(); ++j) {
169 if (i == j)
continue;
170 Particle_T &p2 = *bufferParticles[j];
172 for (
auto k = j + 1; k < bufferParticles.size(); ++k) {
173 if (k == i)
continue;
174 Particle_T &p3 = *bufferParticles[k];
176 f->AoSFunctor(p1, p2, p3,
false);
193 template <
class ContainerType,
class TriwiseFunctor>
194 void remainderHelper3bBufferBufferContainerAoS(
const std::vector<Particle_T *> &bufferParticles,
195 size_t numOwnedBufferParticles, ContainerType &container,
198 using namespace autopas::utils::ArrayMath::literals;
200 const auto haloBoxMin = container.getBoxMin() - container.getInteractionLength();
201 const auto interactionLengthInv = 1. / container.getInteractionLength();
202 const double cutoff = container.getCutoff();
205 for (
auto i = 0; i < bufferParticles.size(); ++i) {
206 Particle_T &p1 = *bufferParticles[i];
207 const auto min = p1.getR() - cutoff;
208 const auto max = p1.getR() + cutoff;
210 for (
auto j = 0; j < bufferParticles.size(); ++j) {
211 if (j == i)
continue;
212 Particle_T &p2 = *bufferParticles[j];
213 container.forEachInRegion(
215 const auto lockCoords = static_cast_copy_array<size_t>((p3.getR() - haloBoxMin) * interactionLengthInv);
216 if (i < numOwnedBufferParticles) f->AoSFunctor(p1, p2, p3,
false);
217 if (!p3.isHalo() && i < j) {
218 const std::lock_guard<std::mutex> lock(*_spatialLocks[lockCoords[0]][lockCoords[1]][lockCoords[2]]);
219 f->AoSFunctor(p3, p1, p2,
false);
222 min,
max, IteratorBehavior::ownedOrHalo);
239 template <
bool newton3,
class ContainerType,
class TriwiseFunctor>
240 void remainderHelper3bBufferContainerContainerAoS(
const std::vector<Particle_T *> &bufferParticles,
241 size_t numOwnedBufferParticles, ContainerType &container,
245 using namespace autopas::utils::ArrayMath::literals;
247 const double cutoff = container.getCutoff();
248 for (
auto i = 0; i < bufferParticles.size(); ++i) {
249 Particle_T &p1 = *bufferParticles[i];
250 const auto boxMin = p1.getR() - cutoff;
251 const auto boxMax = p1.getR() + cutoff;
253 auto p2Iter = container.getRegionIterator(
254 boxMin, boxMax, IteratorBehavior::ownedOrHalo | IteratorBehavior::forceSequential, std::nullopt);
255 for (; p2Iter.isValid(); ++p2Iter) {
256 Particle_T &p2 = *p2Iter;
258 auto p3Iter = p2Iter;
261 for (; p3Iter.isValid(); ++p3Iter) {
262 Particle_T &p3 = *p3Iter;
264 if constexpr (newton3) {
267 if (i < numOwnedBufferParticles) {
#define AutoPasLog(lvl, fmt,...)
Macro for logging providing common meta information without filename.
Definition: Logger.h:24
#define AUTOPAS_OPENMP(args)
Empty macro to throw away any arguments.
Definition: WrapOpenMP.h:126
This class handles the storage of particles in their full form.
Definition: FullParticleCell.h:26
Handles triwise interactions involving particle buffers (particles not yet inserted into the main con...
Definition: RemainderTriwiseInteractionHandler.h:30
RemainderTriwiseInteractionHandler(std::vector< std::vector< std::vector< std::unique_ptr< std::mutex > > > > &spatialLocks)
Constructor for RemainderTriwiseInteractionHandler.
Definition: RemainderTriwiseInteractionHandler.h:36
void computeRemainderInteractions(TriwiseFunctor *f, ContainerType &container, std::vector< FullParticleCell< Particle_T > > &particleBuffers, std::vector< FullParticleCell< Particle_T > > &haloParticleBuffers)
Performs the interactions ParticleContainer::computeInteractions() did not cover.
Definition: RemainderTriwiseInteractionHandler.h:61
TriwiseFunctor class.
Definition: TriwiseFunctor.h:28
virtual void AoSFunctor(Particle_T &i, Particle_T &j, Particle_T &k, bool newton3)
TriwiseFunctor for arrays of structures (AoS).
Definition: TriwiseFunctor.h:54
Timer class to stop times.
Definition: Timer.h:20
void start()
start the timer.
Definition: Timer.cpp:17
long getTotalTime() const
Get total accumulated time.
Definition: Timer.h:53
long stop()
Stops the timer and returns the time elapsed in nanoseconds since the last call to start.
Definition: Timer.cpp:25
constexpr std::array< T, SIZE > max(const std::array< T, SIZE > &a, const std::array< T, SIZE > &b)
Takes elementwise maximum and returns the result.
Definition: ArrayMath.h:96
constexpr std::array< T, SIZE > min(const std::array< T, SIZE > &a, const std::array< T, SIZE > &b)
Takes elementwise minimum, returns the result.
Definition: ArrayMath.h:62
constexpr std::array< output_t, SIZE > static_cast_copy_array(const std::array< input_t, SIZE > &a)
Creates a new array by performing an element-wise static_cast<>.
Definition: ArrayUtils.h:33
This is the main namespace of AutoPas.
Definition: AutoPasDecl.h:32