MercuryDPM  Trunk
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
ParticleSpecies.cc
Go to the documentation of this file.
1 //Copyright (c) 2013-2020, The MercuryDPM Developers Team. All rights reserved.
2 //For the list of developers, see <http://www.MercuryDPM.org/Team>.
3 //
4 //Redistribution and use in source and binary forms, with or without
5 //modification, are permitted provided that the following conditions are met:
6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above copyright
9 // notice, this list of conditions and the following disclaimer in the
10 // documentation and/or other materials provided with the distribution.
11 // * Neither the name MercuryDPM nor the
12 // names of its contributors may be used to endorse or promote products
13 // derived from this software without specific prior written permission.
14 //
15 //THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
16 //ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
17 //WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
18 //DISCLAIMED. IN NO EVENT SHALL THE MERCURYDPM DEVELOPERS TEAM BE LIABLE FOR ANY
19 //DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
20 //(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
21 //LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
22 //ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23 //(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
24 //SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25 
26 #include "Logger.h"
27 #include "ParticleSpecies.h"
28 #include "DPMBase.h"
29 #include "Particles/BaseParticle.h"
31 
32 class BaseParticle;
33 
34 class BaseInteractable;
35 
37  : BaseSpecies(), density_(1.0)
38 {
39 #ifdef DEBUG_CONSTRUCTOR
40  std::cout<<"ParticleSpecies::ParticleSpecies() finished"<<std::endl;
41 #endif
42 }
43 
45  : BaseSpecies(normalForce,frictionForce, adhesiveForce), density_(1.0)
46 {
47 #ifdef DEBUG_CONSTRUCTOR
48  std::cout<<"ParticleSpecies::ParticleSpecies(n,f,a) finished"<<std::endl;
49 #endif
50 }
51 
52 
57  : BaseSpecies(p)
58 {
59  density_ = p.density_;
61 #ifdef DEBUG_CONSTRUCTOR
62  std::cout<<"ParticleSpecies::ParticleSpecies(const ParticleSpecies &p) finished"<<std::endl;
63 #endif
64 }
65 
67 {
68 #ifdef DEBUG_DESTRUCTOR
69  std::cout<<"ParticleSpecies::~ParticleSpecies() finished"<<std::endl;
70 #endif
71 }
72 
76 void ParticleSpecies::write(std::ostream& os) const
77 {
78  //note we inherit from BaseObject, not BaseParticle
80  os << " density " << density_;
82  //todo flip the two values
83 }
84 
88 void ParticleSpecies::read(std::istream& is)
89 {
90  BaseObject::read(is);
91  std::string dummy;
92  is >> dummy >> density_;
94 }
95 
99 std::string ParticleSpecies::getBaseName() const
100 {
101  return "Particle";
102 }
103 
108 {
109  logger.assert_always(density >= 0, "[ParticleSpecies::setDensity(%)] value cannot be negative", density);
110  density_ = density;
112 }
113 
118 {
119  return density_;
120 }
121 
123 {
124  return getDensity() * getVolumeFromRadius(radius);
125 }
126 
128 {
129  setHandler(&speciesHandler);
130  return getMassFromRadius(radius);
131 }
132 
135 {
136  if (getHandler() == nullptr)
137  {
138  logger(ERROR,
139  "[Species::VolumeFromRadius()] No handler has been set, therefore, I can't figure out the dimensions.");
140  return 0;
141  }
142 
143  unsigned int particleDimensions = getHandler()->getDPMBase()->getParticleDimensions();
144  if (particleDimensions == 3)
145  {
146  return 4.0 / 3.0 * constants::pi * radius * radius * radius;
147  }
148  else if (particleDimensions == 2)
149  {
150  return constants::pi * radius * radius;
151  }
152  else if (particleDimensions == 1)
153  {
154  return 2.0 * radius;
155  }
156  else
157  {
158  logger(ERROR, "[Species::VolumeFromRadius()] the dimension of the particle is wrongly set to %",
159  particleDimensions);
160  return 0.0;
161  }
162 }
163 
167 {
168  p->computeMass(*this);
169 }
170 
171 const std::function<double(double)>& ParticleSpecies::getTemperatureDependentDensity() const
172 {
174 }
175 
177  const std::function<double(double)>& temperatureDependentDensity)
178 {
179  temperatureDependentDensity_ = temperatureDependentDensity;
180 // density_ = temperatureDependentDensity_(0);
181 // logger(INFO,"Setting initial density to %",temperature_);
182 }
183 
188 {
189  Mdouble maxInvMass = 0;
190  logger.assert(getHandler() != nullptr && getHandler()->getDPMBase() != nullptr,"speciesHandler must be set");
191  for (BaseParticle* const p : getHandler()->getDPMBase()->particleHandler)
192  {
193  if (p->getSpecies()==this && !(p->isFixed() || p->isMPIParticle() || p->isPeriodicGhostParticle()) && p->getInvMass() > maxInvMass)
194  {
195  maxInvMass = p->getInvMass();
196  }
197  }
198  return maxInvMass;
199 }
200 
202 {
203 #ifdef MERCURY_USE_MPI
204  Mdouble maxInvMass = 0;
206  //Obtain the global value
207  MPIContainer::Instance().allReduce(invMassLocal, maxInvMass, MPI_MAX);
208  //return value
209  return 1.0 / maxInvMass;
210 #else
211  return 1.0 / getLargestInverseParticleMassLocal();
212 #endif
213 
214 }
215 
221  // if maxInteractionDistance_ has increased it's simple
222  if (interactionDistance>=maxInteractionDistance_) {
223  maxInteractionDistance_ = interactionDistance;
224  } else /*else we need to recompute*/ {
226  int j = getIndex();
227  for (int i=0; i<getHandler()->getSize(); ++i) {
228  const auto mixedSpecies = getHandler()->getMixedObject(i,j);
229  if (mixedSpecies) { //this check is necessary because the mixed species handler might not yet be built fully
231  mixedSpecies->getInteractionDistance());
232  }
233  }
234  }
235 }
236 
238  return (getIndex()==s->getIndex())?this:getHandler()->getMixedObject(getIndex(),s->getIndex());
239 }
Container to store all ParticleSpecies.
unsigned int getIndex() const
Returns the index of the object in the handler.
Definition: BaseObject.h:118
std::enable_if<!std::is_pointer< typename U::MixedSpeciesType >::value, typename U::MixedSpeciesType * >::type getMixedObject(const U *S, const U *T)
Mdouble maxInteractionDistance_
Returns the max distance between particles of this species and any other species below which adhesive...
static MPIContainer & Instance()
fetch the instance to be used for communication
Definition: MpiContainer.h:130
void setMaxInteractionDistance(Mdouble interactionDistance=0)
Sets maxInteractionDistance_.
BaseSpecies is the class from which all other species are derived.
Definition: BaseSpecies.h:49
unsigned int getSize() const
Gets the size of the particleHandler (including mpi and periodic particles)
Definition: BaseHandler.h:655
Logger< MERCURY_LOGLEVEL > logger("MercuryKernel")
double Mdouble
Definition: GeneralDefine.h:34
const std::function< double(double)> & getTemperatureDependentDensity() const
unsigned int getParticleDimensions() const
Returns the particle dimensionality.
Definition: DPMBase.cc:1427
void computeAllMasses(unsigned int indSpecies)
Computes the mass for all BaseParticle of the given species in this ParticleHandler.
const std::complex< Mdouble > i
Definition: ExtendedMath.h:50
std::function< double(double temperature)> temperatureDependentDensity_
void computeMass(BaseParticle *p) const
Compute Particle mass function, which required a reference to the Species vector. It computes the Par...
Mdouble getMassFromRadius(Mdouble radius) const
Mdouble getVolumeFromRadius(Mdouble radius) const
virtual void computeMass(const ParticleSpecies &s)
Computes the particle's (inverse) mass and inertia.
SpeciesHandler * getHandler() const
Returns the pointer to the handler to which this species belongs.
Definition: BaseSpecies.cc:99
std::string getBaseName() const
Used in Species::getName to obtain a unique name for each Species.
void write(std::ostream &os) const override
Sets the boolean constantRestitution_.
Definition: BaseSpecies.cc:131
const BaseSpecies * getMixedSpecies(const ParticleSpecies *s) const
const Mdouble pi
Definition: ExtendedMath.h:45
ParticleHandler particleHandler
An object of the class ParticleHandler, contains the pointers to all the particles created...
Definition: DPMBase.h:1329
void setDensity(Mdouble density)
Allows density_ to be changed.
ParticleSpecies()
The default constructor.
virtual void read(std::istream &is)=0
Definition: BaseObject.cc:81
void read(std::istream &is) override
Definition: BaseSpecies.cc:140
void setHandler(SpeciesHandler *handler)
Sets the pointer to the handler to which this species belongs.
Definition: BaseSpecies.cc:91
Mdouble getLargestInverseParticleMassLocal() const
Computes inverse mass of the lightest particle (by mass) belonging to this species. If MPI is used, this computation is done locally on each node.
Mdouble density_
The mass density.
Defines the basic properties that a interactable object can have.
Mdouble getDensity() const
Allows density_ to be accessed.
void write(std::ostream &os) const override
Writes the species properties to an output stream.
DPMBase * getDPMBase()
Gets the problem that is solved using this handler.
Definition: BaseHandler.h:725
Mdouble getSmallestParticleMass() const
Computes mass of the lightest particle (by mass) belonging to this species. This computation calls ge...
~ParticleSpecies()
The default destructor.
virtual void write(std::ostream &os) const =0
A purely virtual function which has an implementation which writes the name and the object id_ to the...
Definition: BaseObject.cc:91
void setTemperatureDependentDensity(const std::function< double(double)> &temperatureDependentDensity)
void read(std::istream &is) override
Reads the species properties from an input stream.