New pair-style ylz added to ASPHERE package

This commit is contained in:
mehdibghk
2022-10-13 13:45:09 +08:00
parent 77740c4f07
commit 0b17654bee
9 changed files with 894064 additions and 0 deletions

114
doc/src/pair_ylz.rst Executable file
View File

@ -0,0 +1,114 @@
.. index:: pair_style ylz
.. index:: pair_style ylz/gpu
.. index:: pair_style ylz/intel
.. index:: pair_style ylz/omp
pair_style ylc command
===========================
Accelerator Variants: *ylz/gpu*, *ylz/intel*, *ylz/omp*
Syntax
""""""
.. code-block:: LAMMPS
pair_style ylz cutoff
* cutoff = global cutoff for interactions (distance units)
Examples
""""""""
.. code-block:: LAMMPS
pair_style ylz 2.6
pair_coeff * * 1.0 1.0 4 3 0.0 2.6
Description
"""""""""""
The *ylz* (Yuan-Li-Zhang)
:ref:`(Yuan) <Yuan>` style computes anisotropic interactions between pairs of particles considering the relative particle orientations via the formulas
.. math::
U ( \mathbf{r}_{ij}, \mathbf{n}_i, \mathbf{n}_j ) =\left\{\begin{matrix} \mathbf{u}_R(r)+\left [ 1-\phi (\mathbf{r\hat{}}_{ij}, \mathbf{n}_i, \mathbf{n}_j ) \right ]\epsilon, ~~ r<\mathbf{r}_{min} \\ \mathbf{u}_A(r)\phi (\mathbf{r\hat{}}_{ij}, \mathbf{n}_i, \mathbf{n}_j ),~~ \mathbf{r}_{min}<r<\mathbf{r}_{c} \\ \end{matrix}\right.\\\\ \phi (\mathbf{r\hat{}}_{ij}, \mathbf{n}_i, \mathbf{n}_j )=1+\mu (a(\mathbf{r\hat{}}_{ij}, \mathbf{n}_i, \mathbf{n}_j )-1) \\\\ a(\mathbf{r\hat{}}_{ij}, \mathbf{n}_i, \mathbf{n}_j )=(\mathbf{n}_i\times\mathbf{r\hat{}}_{ij} )\cdot (\mathbf{n}_j\times\mathbf{r\hat{}}_{ij} )+sin\mathbf{\theta}_0(\mathbf{n}_i-\mathbf{n}_j)\cdot \mathbf{r\hat{}}_{ij}\\\\ \mathbf{u}_R(r)=\epsilon \left [ \left ( \frac{{r}_{min}}{r} \right )^{4}-2\left ( \frac{{r}_{min}}{r}\right )^{2} \right ] \\\\ \mathbf{u}_A(r)=-\epsilon\;cos^{2\zeta }\left ( \frac{\pi}{2}\frac{\left ( {r}-{r}_{min} \right )}{\left ( {r}_{c}-{r}_{min} \right )} \right ) \\
where :math:`r_{i}` and :math:`r_{j}` are the center position vectors of particles i and j, respectively, :math:`r_{ij}=r_{i}-r_{j}` is the inter-particle distance vector, :math:`r=\left|r_{ij} \right|` and :math:`{r\hat{}}_{ij}=\mathbf{r}_{ij}/r`. The unit vectors :math:`n_{i}` and :math:`n_{j}` represent the axes of symmetry of particles i and j, respectively. :math:`u_R` and :math:`u_A` are the repulsive and attractive potentials. :math:`\phi` is an angular function which depends on the relative orientation between pair particles. :math:`\mu` is the parameter related to bending rigidity, :math:`\theta_{0}` is the parameter related to the spontaneous curvature, and :math:`\epsilon` is the energy unit, respectively. The :math:`\zeta` controls the slope of the attractive branch and :math:`{r}_{c}`is the cutoff radius. :math:`r_{min}` is the distance which minimizes the potential energy :math:`u_{A}(r)`and :math:`r_{min}=2^{1/6}\sigma`, where :math:`\sigma` is the length unit.
Use of this pair style requires the NVE, NVT, or NPT fixes with the *asphere* extension (e.g. :doc:`fix nve/asphere <fix_nve_asphere>`) in order to integrate particle rotation. Additionally, :doc:`atom_style ellipsoid <atom_style>` should be used since it defines the rotational state of each particle.
The following coefficients must be defined for each pair of atoms types via the :doc:`pair_coeff <pair_coeff>` command as in the examples above, or in the data file or restart files read by the :doc:`read_data <read_data>` or :doc:`read_restart <read_restart>` commands, or by mixing as described below:
* :math:`\epsilon` = well depth (energy units)
* :math:`\sigma` = minimum effective particle radii (distance units)
* :math:`\zeta` = tune parameter for the slope of the attractive branch
* :math:`\mu` = parameter related to bending rigidity
* :math:`\sin(\theta _{0})` is the sine of parameter related to the spontaneous curvature
* cutoff (distance units)
The last coefficient is optional. If not specified, the global
cutoff specified in the pair_style command is used.
----------
.. include:: accel_styles.rst
----------
Mixing, shift, table, tail correction, restart, rRESPA info
"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
For atom type pairs I,J and I != J, the epsilon and sigma coefficients and cutoff distance for this pair style can be mixed. The default mix value is *geometric*\ . See the "pair_modify" command for details.
The :doc:`pair_modify <pair_modify>` table option is not relevant for this pair style.
This pair style does not support the :doc:`pair_modify <pair_modify>` tail option for adding long-range tail corrections to energy and pressure.
This pair style writes its information to :doc:`binary restart files <restart>`, so pair_style and pair_coeff commands do not need to be specified in an input script that reads a restart file.
This pair style can only be used via the *pair* keyword of the :doc:`run_style respa <run_style>` command. It does not support the
*inner*, *middle*, *outer* keywords.
----------
Restrictions
""""""""""""
The *ylz* style is part of the ASPHERE package. It is only enabled if LAMMPS was built with that package. See the :doc:`Build package <Build_package>` page for more info.
These pair styles require that atoms store torque and a quaternion to represent their orientation, as defined by the :doc:`atom_style <atom_style>`. It also require they store a per-type :doc:`shape <set>`. The particles cannot store a per-particle diameter.
This pair style requires that atoms be ellipsoids as defined by the
:doc:`atom_style ellipsoid <atom_style>` command.
Particles acted on by the potential can be finite-size aspherical or
spherical particles, or point particles. Spherical particles have all
3 of their shape parameters equal to each other. Point particles have
all 3 of their shape parameters equal to 0.0.
Related commands
""""""""""""""""
:doc:`pair_coeff <pair_coeff>`, :doc:`fix nve/asphere <fix_nve_asphere>`,
:doc:`compute temp/asphere <compute_temp_asphere>`, :doc:`pair_style resquared <pair_resquared>`, :doc:`pair_style gayberne <pair_resquared>`
Default
"""""""
none
----------
.. _Yuan:
**(Yuan)** Yuan, Huang, Li, Lykotrafitis, Zhang, Phys. Rev. E, 82, 011905(2010).

View File

@ -0,0 +1,55 @@
# flat membrane demo
variable r0 equal 0.97
variable d1 equal ${r0}
variable d2 equal sqrt(3.0)*${r0}
variable d3 equal 3.0*${r0}
variable ro equal 2./${d1}/${d2}/${d3}
variable T equal 0.23
variable LD equal 1.0
units lj
atom_style ellipsoid
boundary p p p
lattice custom ${ro} a1 ${d1} 0.0 0.0 a2 0.0 ${d2} 0.0 &
a3 0.0 0.0 ${d3} basis 0.0 0.0 0.0 basis 0.5 0.5 0.0
region box block 0 40 0 24 -20 20
create_box 1 box
region membrane block 0 40 0 24 -0.5 0.5
create_atoms 1 region membrane
group membrane region membrane
set type 1 mass 1.0
set type 1 shape 1 1 1
set group all quat 0 -1 0 90
#compute memb all temp/com
#compute rot all temp/asphere bias memb
velocity all create ${T} 87287 loop geom
pair_style ylz 2.6
pair_coeff * * 1.0 1.0 4 3 0.0 2.6
neighbor 1.0 bin
thermo_style custom step temp press pxx pyy
thermo 200
timestep 0.01
dump 1 all atom 10 dump_onlymembrane.lammpstrj
fix 1 all langevin ${T} ${T} ${LD} 48279
fix 2 all nve/asphere
run 3000

View File

@ -0,0 +1,161 @@
LAMMPS (29 Sep 2021 - Update 3)
# only membrane
variable r0 equal 0.97
variable d1 equal ${r0}
variable d1 equal 0.97
variable d2 equal sqrt(3.0)*${r0}
variable d2 equal sqrt(3.0)*0.97
variable d3 equal 3.0*${r0}
variable d3 equal 3.0*0.97
variable ro equal 2./${d1}/${d2}/${d3}
variable ro equal 2./0.97/${d2}/${d3}
variable ro equal 2./0.97/1.68008928334181/${d3}
variable ro equal 2./0.97/1.68008928334181/2.91
variable T equal 0.23
variable LD equal 1.0
units lj
atom_style ellipsoid
boundary p p p
lattice custom ${ro} a1 ${d1} 0.0 0.0 a2 0.0 ${d2} 0.0 a3 0.0 0.0 ${d3} basis 0.0 0.0 0.0 basis 0.5 0.5 0.0
lattice custom 0.421728460751825 a1 ${d1} 0.0 0.0 a2 0.0 ${d2} 0.0 a3 0.0 0.0 ${d3} basis 0.0 0.0 0.0 basis 0.5 0.5 0.0
lattice custom 0.421728460751825 a1 0.97 0.0 0.0 a2 0.0 ${d2} 0.0 a3 0.0 0.0 ${d3} basis 0.0 0.0 0.0 basis 0.5 0.5 0.0
lattice custom 0.421728460751825 a1 0.97 0.0 0.0 a2 0.0 1.68008928334181 0.0 a3 0.0 0.0 ${d3} basis 0.0 0.0 0.0 basis 0.5 0.5 0.0
lattice custom 0.421728460751825 a1 0.97 0.0 0.0 a2 0.0 1.68008928334181 0.0 a3 0.0 0.0 2.91 basis 0.0 0.0 0.0 basis 0.5 0.5 0.0
Lattice spacing in x,y,z = 0.97000000 1.6800893 2.9100000
region box block 0 40 0 24 -20 20
create_box 1 box
Created orthogonal box = (0.0000000 0.0000000 -58.200000) to (38.800000 40.322143 58.200000)
1 by 1 by 1 MPI processor grid
region membrane block 0 40 0 24 -0.5 0.5
create_atoms 1 region membrane
Created 1920 atoms
using lattice units in orthogonal box = (0.0000000 0.0000000 -58.200000) to (38.800000 40.322143 58.200000)
create_atoms CPU = 0.000 seconds
group membrane region membrane
1920 atoms in group membrane
set type 1 mass 1.0
Setting atom values ...
1920 settings made for mass
set type 1 shape 1 1 1
Setting atom values ...
1920 settings made for shape
set group all quat 0 -1 0 90
Setting atom values ...
1920 settings made for quat
compute memb all temp/com
compute rot all temp/asphere bias memb
velocity all create ${T} 87287 loop geom
velocity all create 0.23 87287 loop geom
pair_style ylz 2.6
pair_coeff * * 1.0 1.0 4 3 0.0 2.6
neighbor 1.0 bin
thermo_style custom step temp press pxx pyy
thermo 200
timestep 0.01
dump 1 all atom 10 dump_onlymembrane.lammpstrj
fix 1 all langevin ${T} ${T} ${LD} 48279
fix 1 all langevin 0.23 ${T} ${LD} 48279
fix 1 all langevin 0.23 0.23 ${LD} 48279
fix 1 all langevin 0.23 0.23 1 48279
fix 2 all nve/asphere
run 3000
CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE
Your simulation uses code contributions which should be cited:
- pair ylz command:
@Article{Yuan10,
author = {H. Yuan, C. Huang, J. Li, G. Lykotrafitis, and S. Zhang},
title = {One-particle-thick, solvent-free, coarse-grained model for biological and biomimetic fluid membranes},
journal = {Phys. Rev. E},
year = 2010,
volume = 82,
pages = {011905}
}
CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE
Neighbor list info ...
update every 1 steps, delay 10 steps, check yes
max neighbors/atom: 2000, page size: 100000
master list distance cutoff = 3.6
ghost atom cutoff = 3.6
binsize = 1.8, bins = 22 23 65
1 neighbor lists, perpetual/occasional/extra = 1 0 0
(1) pair ylz, perpetual
attributes: half, newton on
pair build: half/bin/atomonly/newton
stencil: half/bin/3d
bin: standard
Per MPI rank memory allocation (min/avg/max) = 6.097 | 6.097 | 6.097 Mbytes
Step Temp Press Pxx Pyy
0 0.23 -0.0073508785 -0.012283389 -0.012234574
200 0.20903886 -0.0010605951 -0.0011885957 -0.00198842
400 0.21898026 -0.00069250685 -0.0013217981 -0.00073225707
600 0.22689361 -0.00057919328 -0.00076880503 -0.0010242283
800 0.22983221 -0.00032145682 -0.00051928834 -0.00059337525
1000 0.23819392 -0.00027969126 -0.00088082301 -5.2666567e-05
1200 0.22053795 -0.00029571329 -0.0004446455 -0.00035529929
1400 0.22285021 -0.0002690371 -0.00068896571 -3.6258442e-05
1600 0.22687044 2.8599875e-05 -0.00032651798 0.0004056081
1800 0.23356905 -2.28742e-05 -0.00027073251 0.00025081131
2000 0.22499821 8.8230586e-06 -7.5750159e-05 0.0001988705
2200 0.23162995 -9.026855e-05 -0.00025832535 5.4904927e-05
2400 0.22920223 0.00016700455 3.5283125e-05 0.00034955857
2600 0.2260299 5.3095557e-05 0.00025691786 0.00013353467
2800 0.2296401 0.00043234854 0.00058344966 0.00063645193
3000 0.22564577 2.6423111e-05 8.9918406e-05 0.00022146229
Loop time of 5.08921 on 1 procs for 3000 steps with 1920 atoms
Performance: 509312.653 tau/day, 589.482 timesteps/s
99.7% CPU use with 1 MPI tasks x no OpenMP threads
MPI task timing breakdown:
Section | min time | avg time | max time |%varavg| %total
---------------------------------------------------------------
Pair | 4.2251 | 4.2251 | 4.2251 | 0.0 | 83.02
Neigh | 0.07599 | 0.07599 | 0.07599 | 0.0 | 1.49
Comm | 0.026195 | 0.026195 | 0.026195 | 0.0 | 0.51
Output | 0.21176 | 0.21176 | 0.21176 | 0.0 | 4.16
Modify | 0.53849 | 0.53849 | 0.53849 | 0.0 | 10.58
Other | | 0.01168 | | | 0.23
Nlocal: 1920.00 ave 1920 max 1920 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 772.000 ave 772 max 772 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 46804.0 ave 46804 max 46804 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 46804
Ave neighs/atom = 24.377083
Neighbor list builds = 99
Dangerous builds = 0
# notes-1: for npt control, t_start,p_start don't need to be the same as real staring value, moreover, it can cause problem.
# notes-2: drag=0.2 is effective for control pressure, pressure reach desired value too slow if no drag
# notes-3: pressure reach equilibrium much quicker than temperature
Total wall time: 0:00:05

View File

@ -0,0 +1,35 @@
# Vesicle demo
variable T equal 0.2
variable LD equal 1.0
units lj
atom_style ellipsoid
boundary p p p
read_data read_data.vesicle1026
compute ali all temp/com
compute rott all temp/asphere bias ali
velocity all create ${T} 87287 loop geom
pair_style ylz 2.6
pair_coeff * * 1.0 1.0 4 3 0.0 2.6
neighbor 1.0 bin
thermo_style custom step temp press pxx pyy
thermo 200
timestep 0.001
dump 1 all atom 10 onlymembrane2.lammpstrj
fix 1 all langevin ${T} ${T} ${LD} 48279
fix 2 all nve/asphere
run 3000

View File

@ -0,0 +1,124 @@
LAMMPS (29 Sep 2021 - Update 3)
variable T equal 0.2
variable LD equal 1.0
units lj
atom_style ellipsoid
boundary p p p
read_data read_data.vesicle1026
Reading data file ...
orthogonal box = (-35.000000 -35.000000 -35.000000) to (35.000000 35.000000 35.000000)
1 by 1 by 1 MPI processor grid
reading atoms ...
2938 atoms
2938 ellipsoids
read_data CPU = 0.008 seconds
compute ali all temp/com
compute rott all temp/asphere bias ali
velocity all create ${T} 87287 loop geom
velocity all create 0.2 87287 loop geom
pair_style ylz 2.6
pair_coeff * * 1.0 1.0 4 3 0.0 2.6
neighbor 1.0 bin
thermo_style custom step temp press pxx pyy
thermo 200
timestep 0.001
dump 1 all atom 10 onlymembrane2.lammpstrj
fix 1 all langevin ${T} ${T} ${LD} 48279
fix 1 all langevin 0.2 ${T} ${LD} 48279
fix 1 all langevin 0.2 0.2 ${LD} 48279
fix 1 all langevin 0.2 0.2 1 48279
fix 2 all nve/asphere
run 3000
CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE
Your simulation uses code contributions which should be cited:
- pair ylz command:
@Article{Yuan10,
author = {H. Yuan, C. Huang, J. Li, G. Lykotrafitis, and S. Zhang},
title = {One-particle-thick, solvent-free, coarse-grained model for biological and biomimetic fluid membranes},
journal = {Phys. Rev. E},
year = 2010,
volume = 82,
pages = {011905}
}
CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE-CITE
Neighbor list info ...
update every 1 steps, delay 10 steps, check yes
max neighbors/atom: 2000, page size: 100000
master list distance cutoff = 3.6
ghost atom cutoff = 3.6
binsize = 1.8, bins = 39 39 39
1 neighbor lists, perpetual/occasional/extra = 1 0 0
(1) pair ylz, perpetual
attributes: half, newton on
pair build: half/bin/atomonly/newton
stencil: half/bin/3d
bin: standard
Per MPI rank memory allocation (min/avg/max) = 6.203 | 6.203 | 6.203 Mbytes
Step Temp Press Pxx Pyy
0 0.2 -0.0054891414 -0.0052713616 -0.0053641136
200 0.12816247 -0.0051288861 -0.0048542514 -0.0049847561
400 0.1377632 -0.0048071582 -0.0045651263 -0.0048444087
600 0.14983781 -0.0045305725 -0.0043305994 -0.0046127777
800 0.16205271 -0.0041176346 -0.0040534483 -0.0041351779
1000 0.17462122 -0.0037000069 -0.0034938539 -0.0037915494
1200 0.18335448 -0.0032674318 -0.0032790248 -0.0031967931
1400 0.19195613 -0.0029332101 -0.0030823703 -0.0028287799
1600 0.19261762 -0.0025263447 -0.0025152249 -0.0026205398
1800 0.19758674 -0.0021087725 -0.001981333 -0.002309048
2000 0.19748896 -0.0017662369 -0.0019316344 -0.0016696035
2200 0.20196986 -0.0013363214 -0.0015581191 -0.0013384961
2400 0.20109248 -0.0009190831 -0.0010331417 -0.0010664316
2600 0.20228664 -0.00053590675 -0.00071808747 -0.00050218533
2800 0.20512955 -0.00030845899 -0.00016244901 -0.00047877516
3000 0.19855941 -7.9520073e-05 -0.00014969215 -5.4724226e-06
Loop time of 7.2222 on 1 procs for 3000 steps with 2938 atoms
Performance: 35889.329 tau/day, 415.386 timesteps/s
99.9% CPU use with 1 MPI tasks x no OpenMP threads
MPI task timing breakdown:
Section | min time | avg time | max time |%varavg| %total
---------------------------------------------------------------
Pair | 6.0158 | 6.0158 | 6.0158 | 0.0 | 83.30
Neigh | 0.034308 | 0.034308 | 0.034308 | 0.0 | 0.48
Comm | 0.0015149 | 0.0015149 | 0.0015149 | 0.0 | 0.02
Output | 0.31567 | 0.31567 | 0.31567 | 0.0 | 4.37
Modify | 0.83787 | 0.83787 | 0.83787 | 0.0 | 11.60
Other | | 0.01702 | | | 0.24
Nlocal: 2938.00 ave 2938 max 2938 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 0.00000 ave 0 max 0 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 73242.0 ave 73242 max 73242 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 73242
Ave neighs/atom = 24.929204
Neighbor list builds = 26
Dangerous builds = 0
# notes-1: for npt control, t_start,p_start don't need to be the same as real staring value, moreover, it can cause problem.
# notes-2: drag=0.2 is effective for control pressure, pressure reach desired value too slow if no drag
# notes-3: pressure reach equilibrium much quicker than temperature
Total wall time: 0:00:07

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

551
src/ASPHERE/pair_ylz.cpp Executable file
View File

@ -0,0 +1,551 @@
/* ----------------------------------------------------------------------
LAMMPS - Large-scale Atomic/Molecular Massively Parallel Simulator
http://www.lammps.org/, Sandia National Laboratories
Steve Plimpton, sjplimp@sandia.gov
Copyright (2003) Sandia Corporation. Under the terms of Contract
DE-AC04-94AL85000 with Sandia Corporation, the U.S. Government retains
certain rights in this software. This software is distributed under
the GNU General Public License.
See the README file in the top-level LAMMPS directory.
------------------------------------------------------------------------- */
/* ----------------------------------------------------------------------
Contributing author: Mehdi Baghaee (SUSTech)
------------------------------------------------------------------------- */
#include "pair_ylz.h"
#include <cmath>
#include "math_extra.h"
#include "atom.h"
#include "atom_vec_ellipsoid.h"
#include "comm.h"
#include "force.h"
#include "neighbor.h"
#include "neigh_list.h"
#include "citeme.h"
#include "memory.h"
#include "error.h"
using namespace LAMMPS_NS;
static const char cite_pair_ylz[] =
"pair ylz command:\n\n"
"@Article{Yuan10,\n"
" author = {H. Yuan, C. Huang, J. Li, G. Lykotrafitis, and S. Zhang},\n"
" title = {One-particle-thick, solvent-free, coarse-grained model for biological and biomimetic fluid membranes},\n"
" journal = {Phys. Rev. E},\n"
" year = 2010,\n"
" volume = 82,\n"
" pages = {011905}\n"
"}\n\n";
/* ---------------------------------------------------------------------- */
PairYLZ::PairYLZ(LAMMPS *lmp) : Pair(lmp)
{
if (lmp->citeme) lmp->citeme->add(cite_pair_ylz);
single_enable = 0;
writedata = 1;
}
/* ----------------------------------------------------------------------
free all arrays
------------------------------------------------------------------------- */
PairYLZ::~PairYLZ()
{
if (allocated) {
memory->destroy(setflag);
memory->destroy(cutsq);
memory->destroy(epsilon);
memory->destroy(sigma);
memory->destroy(cut);
memory->destroy(zeta);
memory->destroy(mu);
memory->destroy(beta);
}
}
/* ---------------------------------------------------------------------- */
void PairYLZ::compute(int eflag, int vflag)
{
int i,j,ii,jj,inum,jnum,itype,jtype;
double evdwl,one_eng,rsq,forcelj,factor_lj;
double fforce[3],ttor[3],rtor[3],r12[3];
double a1[3][3],a2[3][3];
int *ilist,*jlist,*numneigh,**firstneigh;
double *iquat,*jquat;
evdwl = 0.0;
ev_init(eflag , vflag);
AtomVecEllipsoid::Bonus *bonus = avec->bonus;
int *ellipsoid = atom->ellipsoid;
double **x = atom->x;
double **f = atom->f;
double **tor = atom->torque;
int *type = atom->type;
int nlocal = atom->nlocal;
double *special_lj = force->special_lj;
int newton_pair = force->newton_pair;
inum = list->inum;
ilist = list->ilist;
numneigh = list->numneigh;
firstneigh = list->firstneigh;
// loop over neighbors of my atoms
for (ii = 0; ii < inum; ii++) {
i = ilist[ii];
itype = type[i];
iquat = bonus[ellipsoid[i]].quat;
MathExtra::quat_to_mat_trans(iquat,a1);
jlist = firstneigh[i];
jnum = numneigh[i];
for (jj = 0; jj < jnum; jj++) {
j = jlist[jj];
factor_lj = special_lj[sbmask(j)];
j &= NEIGHMASK;
// r12 = center to center vector
r12[0] = x[j][0]-x[i][0];
r12[1] = x[j][1]-x[i][1];
r12[2] = x[j][2]-x[i][2];
rsq = MathExtra::dot3(r12,r12);
jtype = type[j];
// compute if less than cutoff
if (rsq < cutsq[itype][jtype]) {
jquat = bonus[ellipsoid[j]].quat;
MathExtra::quat_to_mat_trans(jquat,a2);
one_eng = ylz_analytic(i,j,a1,a2,r12,rsq,fforce,ttor,rtor);
fforce[0] *= factor_lj;
fforce[1] *= factor_lj;
fforce[2] *= factor_lj;
ttor[0] *= factor_lj;
ttor[1] *= factor_lj;
ttor[2] *= factor_lj;
f[i][0] += fforce[0];
f[i][1] += fforce[1];
f[i][2] += fforce[2];
tor[i][0] += ttor[0];
tor[i][1] += ttor[1];
tor[i][2] += ttor[2];
if (newton_pair || j < nlocal) {
rtor[0] *= factor_lj;
rtor[1] *= factor_lj;
rtor[2] *= factor_lj;
f[j][0] -= fforce[0];
f[j][1] -= fforce[1];
f[j][2] -= fforce[2];
tor[j][0] += rtor[0];
tor[j][1] += rtor[1];
tor[j][2] += rtor[2];
}
if (eflag) evdwl = factor_lj*one_eng;
if (evflag) ev_tally_xyz(i,j,nlocal,newton_pair,
evdwl,0.0,fforce[0],fforce[1],fforce[2],
-r12[0],-r12[1],-r12[2]);
}
}
}
if (vflag_fdotr) virial_fdotr_compute();
}
/* ----------------------------------------------------------------------
allocate all arrays
------------------------------------------------------------------------- */
void PairYLZ::allocate()
{
allocated = 1;
int n = atom->ntypes;
memory->create(setflag,n+1,n+1,"pair:setflag");
for (int i = 1; i <= n; i++)
for (int j = i; j <= n; j++)
setflag[i][j] = 0;
memory->create(cutsq,n+1,n+1,"pair:cutsq");
memory->create(epsilon,n+1,n+1,"pair:epsilon");
memory->create(sigma,n+1,n+1,"pair:sigma");
memory->create(cut,n+1,n+1,"pair:cut");
memory->create(zeta,n+1,n+1,"pair:zeta");
memory->create(mu,n+1,n+1,"pair:mu");
memory->create(beta,n+1,n+1,"pair:beta");
}
/* ----------------------------------------------------------------------
global settings
------------------------------------------------------------------------- */
void PairYLZ::settings(int narg, char **arg)
{
if (narg != 1) error->all(FLERR,"Illegal pair_style command");
cut_global = utils::numeric(FLERR,arg[0],false, lmp);
}
/* ----------------------------------------------------------------------
set coeffs for one or more type pairs
------------------------------------------------------------------------- */
void PairYLZ::coeff(int narg, char **arg)
{
if (narg < 8 || narg > 8)
error->all(FLERR,"Incorrect args for pair coefficients");
if (!allocated) allocate();
int ilo,ihi,jlo,jhi;
utils::bounds(FLERR, arg[0],1,atom->ntypes,ilo,ihi, error);
utils::bounds(FLERR, arg[1],1,atom->ntypes,jlo,jhi, error);
double epsilon_one = utils::numeric(FLERR,arg[2], false, lmp);
double sigma_one = utils::numeric(FLERR,arg[3], false, lmp);
double zeta_one = utils::numeric(FLERR,arg[4], false, lmp);
double mu_one = utils::numeric(FLERR,arg[5], false, lmp);
double beta_one = utils::numeric(FLERR,arg[6], false, lmp);
double cut_one = utils::numeric(FLERR,arg[7], false, lmp);
int count = 0;
for (int i = ilo; i <= ihi; i++) {
for (int j = MAX(jlo,i); j <= jhi; j++) {
epsilon[i][j] = epsilon_one;
sigma[i][j] = sigma_one;
cut[i][j] = cut_one;
zeta[i][j] = zeta_one;
mu[i][j] = mu_one;
beta[i][j] = beta_one;
setflag[i][j] = 1;
count++;
}
}
if (count == 0) error->all(FLERR,"Incorrect args for pair coefficients");
}
/* ----------------------------------------------------------------------
init specific to this pair style
------------------------------------------------------------------------- */
void PairYLZ::init_style()
{
avec = (AtomVecEllipsoid *) atom->style_match("ellipsoid");
if (!avec) error->all(FLERR,"Pair YLZ requires atom style ellipsoid");
neighbor->request(this,instance_me);
}
/* ----------------------------------------------------------------------
init for one type pair i,j and corresponding j,i
------------------------------------------------------------------------- */
double PairYLZ::init_one(int i, int j)
{
if (setflag[i][j] == 0) {
epsilon[i][j] = mix_energy(epsilon[i][i],epsilon[j][j],
sigma[i][i],sigma[j][j]);
sigma[i][j] = mix_distance(sigma[i][i],sigma[j][j]);
cut[i][j] = mix_distance(cut[i][i],cut[j][j]);
}
epsilon[j][i] = epsilon[i][j];
sigma[j][i] = sigma[i][j];
zeta[j][i] = zeta[i][j];
mu[j][i] = mu[i][j];
beta[j][i] = beta[i][j];
return cut[i][j];
}
/* ----------------------------------------------------------------------
proc 0 writes to restart file
------------------------------------------------------------------------- */
void PairYLZ::write_restart(FILE *fp)
{
write_restart_settings(fp);
int i,j;
for (i = 1; i <= atom->ntypes; i++) {
for (j = i; j <= atom->ntypes; j++) {
fwrite(&setflag[i][j],sizeof(int),1,fp);
if (setflag[i][j]) {
fwrite(&epsilon[i][j],sizeof(double),1,fp);
fwrite(&sigma[i][j],sizeof(double),1,fp);
fwrite(&cut[i][j],sizeof(double),1,fp);
fwrite(&zeta[i][j],sizeof(double),1,fp);
fwrite(&mu[i][j],sizeof(double),1,fp);
fwrite(&beta[i][j],sizeof(double),1,fp);
}
}
}
}
/* ----------------------------------------------------------------------
proc 0 reads from restart file, bcasts
------------------------------------------------------------------------- */
void PairYLZ::read_restart(FILE *fp)
{
read_restart_settings(fp);
allocate();
int i,j;
int me = comm->me;
for (i = 1; i <= atom->ntypes; i++) {
for (j = i; j <= atom->ntypes; j++) {
if (me == 0) utils::sfread(FLERR, &setflag[i][j],sizeof(int),1,fp, nullptr, error);
MPI_Bcast(&setflag[i][j],1,MPI_INT,0,world);
if (setflag[i][j]) {
if (me == 0) {
utils::sfread(FLERR, &epsilon[i][j],sizeof(double),1,fp, nullptr, error);
utils::sfread(FLERR, &sigma[i][j],sizeof(double),1,fp, nullptr, error);
utils::sfread(FLERR, &cut[i][j],sizeof(double),1,fp, nullptr, error);
utils::sfread(FLERR, &zeta[i][j],sizeof(double),1,fp, nullptr, error);
utils::sfread(FLERR, &mu[i][j],sizeof(double),1,fp, nullptr, error);
utils::sfread(FLERR, &beta[i][j],sizeof(double),1,fp, nullptr, error);
}
MPI_Bcast(&epsilon[i][j],1,MPI_DOUBLE,0,world);
MPI_Bcast(&sigma[i][j],1,MPI_DOUBLE,0,world);
MPI_Bcast(&cut[i][j],1,MPI_DOUBLE,0,world);
MPI_Bcast(&zeta[i][j],1,MPI_DOUBLE,0,world);
MPI_Bcast(&mu[i][j],1,MPI_DOUBLE,0,world);
MPI_Bcast(&beta[i][j],1,MPI_DOUBLE,0,world);
}
}
}
}
/* ----------------------------------------------------------------------
proc 0 writes to restart file
------------------------------------------------------------------------- */
void PairYLZ::write_restart_settings(FILE *fp)
{
//fwrite(&model_type,sizeof(int),1,fp);
fwrite(&cut_global,sizeof(double),1,fp);
fwrite(&offset_flag,sizeof(int),1,fp);
fwrite(&mix_flag,sizeof(int),1,fp);
}
/* ----------------------------------------------------------------------
proc 0 reads from restart file, bcasts
------------------------------------------------------------------------- */
void PairYLZ::read_restart_settings(FILE *fp)
{
int me = comm->me;
if (me == 0) {
// utils::sfread(FLERR, &model_type,sizeof(int),1,fp, nullptr, error);
utils::sfread(FLERR, &cut_global,sizeof(double),1,fp, nullptr, error);
utils::sfread(FLERR, &offset_flag,sizeof(int),1,fp, nullptr, error);
utils::sfread(FLERR, &mix_flag,sizeof(int),1,fp, nullptr, error);
}
//MPI_Bcast(&model_type,1,MPI_DOUBLE,0,world);
MPI_Bcast(&cut_global,1,MPI_DOUBLE,0,world);
MPI_Bcast(&offset_flag,1,MPI_INT,0,world);
MPI_Bcast(&mix_flag,1,MPI_INT,0,world);
}
/* ----------------------------------------------------------------------
proc 0 writes to data file
------------------------------------------------------------------------- */
void PairYLZ::write_data(FILE *fp)
{
for (int i = 1; i <= atom->ntypes; i++)
fprintf(fp,"%d %g %g %g %g %g %g\n",i,
epsilon[i][i],sigma[i][i],cut[i][i],zeta[i][i],mu[i][i], beta[i][i]);
}
/* ----------------------------------------------------------------------
proc 0 writes all pairs to data file
------------------------------------------------------------------------- */
void PairYLZ::write_data_all(FILE *fp)
{
for (int i = 1; i <= atom->ntypes; i++)
for (int j = i; j <= atom->ntypes; j++)
fprintf(fp,"%d %d %g %g %g %g %g %g\n",i,j,
epsilon[i][i],sigma[i][i],cut[i][j],zeta[i][j],mu[i][j], beta[i][j]);
}
/* ----------------------------------------------------------------------
compute analytic energy, force (fforce), and torque (ttor & rtor)
based on rotation matrices a
if newton is off, rtor is not calculated for ghost atoms
------------------------------------------------------------------------- */
double PairYLZ::ylz_analytic(const int i,const int j,double a1[3][3],
double a2[3][3], double *r12,
const double rsq, double *fforce,
double *ttor, double *rtor)
{
int *type = atom->type;
int newton_pair = force->newton_pair;
int nlocal = atom->nlocal;
double r12hat[3];
MathExtra::normalize3(r12,r12hat);
double r = sqrt(rsq);
double ni1[3],nj1[3],dphi_drhat[3],dUdrhat[3],dUdni1[3],dUdnj1[3],dphi_dni1[3],dphi_dnj1[3] ;
double t,t1,t2,t4,cos_t,U,uR,uA,dUdr,dUdphi;
double pi = 3.141592653589793, pow2_1by6 = 1.122462048309373;
double energy_well = epsilon[type[i]][type[j]];
double rmin = pow2_1by6*sigma[type[i]][type[j]];
double rcut = cut[type[i]][type[j]];
double zt = zeta[type[i]][type[j]];
double muu = mu[type[i]][type[j]];
double sint = beta[type[i]][type[j]];
ni1[0]=a1[0][0];
ni1[1]=a1[0][1];
ni1[2]=a1[0][2];
nj1[0]=a2[0][0];
nj1[1]=a2[0][1];
nj1[2]=a2[0][2];
double ninj = MathExtra::dot3(ni1,nj1);
double ni1rhat = MathExtra::dot3(ni1,r12hat);
double nj1rhat = MathExtra::dot3(nj1,r12hat);
double a = ninj + (sint-ni1rhat)*(sint+nj1rhat) - 2.0*sint*sint;
double phi = 1.0 + (a-1.0)*muu;
dphi_drhat[0] = muu*( (sint-ni1rhat)*nj1[0]-ni1[0]*(sint+nj1rhat) );
dphi_drhat[1] = muu*( (sint-ni1rhat)*nj1[1]-ni1[1]*(sint+nj1rhat) );
dphi_drhat[2] = muu*( (sint-ni1rhat)*nj1[2]-ni1[2]*(sint+nj1rhat) );
dphi_dni1[0] = muu*(nj1[0]-r12hat[0]*(sint+nj1rhat));
dphi_dni1[1] = muu*(nj1[1]-r12hat[1]*(sint+nj1rhat));
dphi_dni1[2] = muu*(nj1[2]-r12hat[2]*(sint+nj1rhat));
dphi_dnj1[0] = muu*(ni1[0]+r12hat[0]*(sint-ni1rhat));
dphi_dnj1[1] = muu*(ni1[1]+r12hat[1]*(sint-ni1rhat));
dphi_dnj1[2] = muu*(ni1[2]+r12hat[2]*(sint-ni1rhat));
if (r < rmin)
{
t = rmin/r;
t2=t*t;
t4=t2*t2;
uR = (t4 - 2.0*t2)*energy_well;
U = uR +(1.0 - phi)*energy_well;
dUdr = 4.0*(t2-t4)/r*energy_well;
dUdphi = -energy_well;
}
else
{
t = pi/2.0*(r-rmin)/(rcut-rmin);
cos_t = cos(t);
t1=cos_t;
for (int k = 1; k <= 2*zt-2; k++) {t1 *= cos_t;} // get cos()^(2zt-1)
uA = -energy_well*t1*cos_t;
U = uA*phi;
dUdr = 4.0*pi/(rcut-rmin)*(t1)*sin(t)*phi*energy_well;
dUdphi = uA;
}
dUdrhat[0] = dUdphi*dphi_drhat[0];
dUdrhat[1] = dUdphi*dphi_drhat[1];
dUdrhat[2] = dUdphi*dphi_drhat[2];
double dUdrhatrhat = MathExtra::dot3(dUdrhat,r12hat);
fforce[0] = dUdr*r12hat[0] + (dUdrhat[0]-dUdrhatrhat*r12hat[0])/r;
fforce[1] = dUdr*r12hat[1] + (dUdrhat[1]-dUdrhatrhat*r12hat[1])/r;
fforce[2] = dUdr*r12hat[2] + (dUdrhat[2]-dUdrhatrhat*r12hat[2])/r;
// torque i
dUdni1[0] = dUdphi*dphi_dni1[0];
dUdni1[1] = dUdphi*dphi_dni1[1];
dUdni1[2] = dUdphi*dphi_dni1[2];
MathExtra::cross3(dUdni1,ni1,ttor); //minus sign is replace by swapping ni1 and dUdni1
if (newton_pair || j < nlocal) {
dUdnj1[0] = dUdphi*dphi_dnj1[0];
dUdnj1[1] = dUdphi*dphi_dnj1[1];
dUdnj1[2] = dUdphi*dphi_dnj1[2];
MathExtra::cross3(dUdnj1,nj1,rtor); //minus sign is replace by swapping ni1 and dUdni1
}
// output energy, force, torque, only for the in_two_particles input file, for checking the model implementation
/*
fprintf(screen,"energy = %f \n",U);
fprintf(screen,"force_i = %f %f %f \n",fforce[0],fforce[1],fforce[2]);
fprintf(screen,"torque_i = %f %f %f \n",ttor[0],ttor[1],ttor[2]);
fprintf(screen,"torque_j = %f %f %f \n",rtor[0],rtor[1],rtor[2]);
*/
return U;
}

83
src/ASPHERE/pair_ylz.h Executable file
View File

@ -0,0 +1,83 @@
/* -*- c++ -*- ----------------------------------------------------------
LAMMPS - Large-scale Atomic/Molecular Massively Parallel Simulator
http://lammps.sandia.gov, Sandia National Laboratories
Steve Plimpton, sjplimp@sandia.gov
Copyright (2003) Sandia Corporation. Under the terms of Contract
DE-AC04-94AL85000 with Sandia Corporation, the U.S. Government retains
certain rights in this software. This software is distributed under
the GNU General Public License.
See the README file in the top-level LAMMPS directory.
------------------------------------------------------------------------- */
#ifdef PAIR_CLASS
PairStyle(ylz,PairYLZ);
#else
#ifndef LMP_PAIR_YLZ_H
#define LMP_PAIR_YLZ_H
#include "pair.h"
namespace LAMMPS_NS {
class PairYLZ : public Pair {
public:
PairYLZ(LAMMPS *lmp);
virtual ~PairYLZ();
virtual void compute(int, int);
virtual void settings(int, char **);
void coeff(int, char **);
virtual void init_style();
double init_one(int, int);
void write_restart(FILE *);
void read_restart(FILE *);
void write_restart_settings(FILE *);
void read_restart_settings(FILE *);
void write_data(FILE *);
void write_data_all(FILE *);
protected:
double cut_global;
double **epsilon,**sigma,**cut,**zeta,**mu,**beta; // model parameter values for atom-type pairs
class AtomVecEllipsoid *avec;
void allocate();
double ylz_analytic(const int i, const int j, double a1[3][3],
double a2[3][3], double *r12,
const double rsq, double *fforce, double *ttor,
double *rtor);
};
}
#endif
#endif
/* ERROR/WARNING messages:
E: Illegal ... command
Self-explanatory. Check the input script syntax and compare to the
documentation for the command. You can use -echo screen as a
command-line option when running LAMMPS to see the offending line.
E: Incorrect args for pair coefficients
Self-explanatory. Check the input script or data file.
E: Pair ylz requires atom style ellipsoid
Self-explanatory.
*/