Merge remote-tracking branch 'lammps-ro/master' into lammps-icms

Resolved Conflicts:
	doc/Manual.html
	doc/Manual.txt
This commit is contained in:
Axel Kohlmeyer
2015-03-18 07:26:15 -04:00
40 changed files with 3413 additions and 414 deletions

View File

@ -82,7 +82,7 @@ also leave off the "-fft fftw3" switch if you do not have the FFTW
library will be used. library will be used.
cd src cd src
Make.py -j 16 -p none molecule manybody kspace granular orig \ Make.py -j 16 -p none molecule manybody kspace granular rigid orig \
-cc mpi wrap=icc -fft fftw3 -a file mpi -cc mpi wrap=icc -fft fftw3 -a file mpi
---------------------------------------------------------------------- ----------------------------------------------------------------------

View File

@ -8,7 +8,7 @@ units lj
atom_style sphere atom_style sphere
boundary p p fs boundary p p fs
newton off newton off
communicate single vel yes comm_modify vel yes
read_data data.chute read_data data.chute

View File

@ -1,7 +1,7 @@
<HTML> <HTML>
<HEAD> <HEAD>
<TITLE>LAMMPS-ICMS Users Manual</TITLE> <TITLE>LAMMPS-ICMS Users Manual</TITLE>
<META NAME="docnumber" CONTENT="12 Mar 2015 version"> <META NAME="docnumber" CONTENT="14 Mar 2015 version">
<META NAME="author" CONTENT="http://lammps.sandia.gov - Sandia National Laboratories"> <META NAME="author" CONTENT="http://lammps.sandia.gov - Sandia National Laboratories">
<META NAME="copyright" CONTENT="Copyright (2003) Sandia Corporation. This software and manual is distributed under the GNU General Public License."> <META NAME="copyright" CONTENT="Copyright (2003) Sandia Corporation. This software and manual is distributed under the GNU General Public License.">
</HEAD> </HEAD>
@ -22,7 +22,7 @@
<CENTER><H3>LAMMPS-ICMS Documentation <CENTER><H3>LAMMPS-ICMS Documentation
</H3></CENTER> </H3></CENTER>
<CENTER><H4>12 Mar 2015 version <CENTER><H4>14 Mar 2015 version
</H4></CENTER> </H4></CENTER>
<H4>Version info: <H4>Version info:
</H4> </H4>
@ -260,17 +260,21 @@ it gives quick access to documentation for all LAMMPS commands.
<BR></UL> <BR></UL>
<LI><A HREF = "Section_python.html">Python interface</A> <LI><A HREF = "Section_python.html">Python interface</A>
<UL> 11.1 <A HREF = "Section_python.html#py_1">Building LAMMPS as a shared library</A> <UL> 11.1 <A HREF = "Section_python.html#py_1">Overview of running LAMMPS from Python</A>
<BR> <BR>
11.2 <A HREF = "Section_python.html#py_2">Installing the Python wrapper into Python</A> 11.2 <A HREF = "Section_python.html#py_2">Overview of using Python from a LAMMPS script</A>
<BR> <BR>
11.3 <A HREF = "Section_python.html#py_3">Extending Python with MPI to run in parallel</A> 11.3 <A HREF = "Section_python.html#py_3">Building LAMMPS as a shared library</A>
<BR> <BR>
11.4 <A HREF = "Section_python.html#py_4">Testing the Python-LAMMPS interface</A> 11.4 <A HREF = "Section_python.html#py_4">Installing the Python wrapper into Python</A>
<BR> <BR>
11.5 <A HREF = "Section_python.html#py_5">Using LAMMPS from Python</A> 11.5 <A HREF = "Section_python.html#py_5">Extending Python with MPI to run in parallel</A>
<BR> <BR>
11.6 <A HREF = "Section_python.html#py_6">Example Python scripts that use LAMMPS</A> 11.6 <A HREF = "Section_python.html#py_6">Testing the Python-LAMMPS interface</A>
<BR>
11.7 <A HREF = "py_7">Using LAMMPS from Python</A>
<BR>
11.8 <A HREF = "py_8">Example Python scripts that use LAMMPS</A>
<BR></UL> <BR></UL>
<LI><A HREF = "Section_errors.html">Errors</A> <LI><A HREF = "Section_errors.html">Errors</A>

View File

@ -1,7 +1,7 @@
<HEAD> <HEAD>
<TITLE>LAMMPS-ICMS Users Manual</TITLE> <TITLE>LAMMPS-ICMS Users Manual</TITLE>
<TITLE>LAMMPS Users Manual</TITLE> <TITLE>LAMMPS Users Manual</TITLE>
<META NAME="docnumber" CONTENT="12 Mar 2015 version"> <META NAME="docnumber" CONTENT="14 Mar 2015 version">
<META NAME="author" CONTENT="http://lammps.sandia.gov - Sandia National Laboratories"> <META NAME="author" CONTENT="http://lammps.sandia.gov - Sandia National Laboratories">
<META NAME="copyright" CONTENT="Copyright (2003) Sandia Corporation. This software and manual is distributed under the GNU General Public License."> <META NAME="copyright" CONTENT="Copyright (2003) Sandia Corporation. This software and manual is distributed under the GNU General Public License.">
</HEAD> </HEAD>
@ -19,7 +19,7 @@
<H1></H1> <H1></H1>
LAMMPS-ICMS Documentation :c,h3 LAMMPS-ICMS Documentation :c,h3
12 Mar 2015 version :c,h4 14 Mar 2015 version :c,h4
Version info: :h4 Version info: :h4
@ -175,12 +175,14 @@ it gives quick access to documentation for all LAMMPS commands.
10.14 "Variable options"_mod_14 :b 10.14 "Variable options"_mod_14 :b
10.15 "Submitting new features for inclusion in LAMMPS"_mod_15 :ule,b 10.15 "Submitting new features for inclusion in LAMMPS"_mod_15 :ule,b
"Python interface"_Section_python.html :l "Python interface"_Section_python.html :l
11.1 "Building LAMMPS as a shared library"_py_1 :ulb,b 11.1 "Overview of running LAMMPS from Python"_py_1 :ulb,b
11.2 "Installing the Python wrapper into Python"_py_2 :b 11.2 "Overview of using Python from a LAMMPS script"_py_2 :b
11.3 "Extending Python with MPI to run in parallel"_py_3 :b 11.3 "Building LAMMPS as a shared library"_py_3 :b
11.4 "Testing the Python-LAMMPS interface"_py_4 :b 11.4 "Installing the Python wrapper into Python"_py_4 :b
11.5 "Using LAMMPS from Python"_py_5 :b 11.5 "Extending Python with MPI to run in parallel"_py_5 :b
11.6 "Example Python scripts that use LAMMPS"_py_6 :ule,b 11.6 "Testing the Python-LAMMPS interface"_py_6 :b
11.7 "Using LAMMPS from Python"_py_7 :b
11.8 "Example Python scripts that use LAMMPS"_py_8 :ule,b
"Errors"_Section_errors.html :l "Errors"_Section_errors.html :l
12.1 "Common problems"_err_1 :ulb,b 12.1 "Common problems"_err_1 :ulb,b
12.2 "Reporting bugs"_err_2 :b 12.2 "Reporting bugs"_err_2 :b

View File

@ -86,11 +86,12 @@ file names or user-chosen ID strings.
</P> </P>
<P>Here is how each line in the input script is parsed by LAMMPS: <P>Here is how each line in the input script is parsed by LAMMPS:
</P> </P>
<P>(1) If the last printable character on the line is a "&" character <P>(1) If the last printable character on the line is a "&" character,
(with no surrounding quotes), the command is assumed to continue on the command is assumed to continue on the next line. The next line is
the next line. The next line is concatenated to the previous line by concatenated to the previous line by removing the "&" character and
removing the "&" character and newline. This allows long commands to line break. This allows long commands to be continued across two or
be continued across two or more lines. more lines. See the discussion of triple quotes in (6) for how to
continue a command across multiple line without using "&" characters.
</P> </P>
<P>(2) All characters from the first "#" character onward are treated as <P>(2) All characters from the first "#" character onward are treated as
comment and discarded. See an exception in (6). Note that a comment and discarded. See an exception in (6). Note that a
@ -136,9 +137,9 @@ variable X delete
contain nested $ characters for other variables to substitute for. contain nested $ characters for other variables to substitute for.
Thus you cannot do this: Thus you cannot do this:
</P> </P>
<PRE>variable a equal 2 <PRE>variable a equal 2
variable b2 equal 4 variable b2 equal 4
region 1 block ${b$a} 2 INF INF EDGE EDGE print "B2 = ${b$a}"
</PRE> </PRE>
<P>Nor can you specify this $($x-1.0) for an immediate variable, but <P>Nor can you specify this $($x-1.0) for an immediate variable, but
you could use $(v_x-1.0), since the latter is valid syntax for an you could use $(v_x-1.0), since the latter is valid syntax for an
@ -156,27 +157,38 @@ underscores, or punctuation characters.
line are arguments. line are arguments.
</P> </P>
<P>(6) If you want text with spaces to be treated as a single argument, <P>(6) If you want text with spaces to be treated as a single argument,
it can be enclosed in either double or single quotes. A long single it can be enclosed in either single or double or triple quotes. A
argument enclosed in quotes can even span multiple lines if the "&" long single argument enclosed in single or double quotes can span
character is used, as described above. E.g. multiple lines if the "&" character is used, as described above. When
the lines are concatenated together (and the "&" characters and line
breaks removed), the text will become a single line. If you want
multiple lines of an argument to retain their line breaks, the text
can be enclosed in triple quotes, in which case "&" characters are not
needed. For example:
</P> </P>
<PRE>print "Volume = $v" <PRE>print "Volume = $v"
print 'Volume = $v' print 'Volume = $v'
if "$<I>steps</I> > 1000" then quit
variable a string "red green blue & variable a string "red green blue &
purple orange cyan" purple orange cyan"
if "$<I>steps</I> > 1000" then quit print """
System volume = $v
System temperature = $t
"""
</PRE> </PRE>
<P>The quotes are removed when the single argument is stored internally. <P>In each case, the single, double, or triple quotes are removed when
the single argument they enclose is stored internally.
</P> </P>
<P>See the <A HREF = "dump_modify.html">dump modify format</A> or <A HREF = "print.html">print</A> or <P>See the <A HREF = "dump_modify.html">dump modify format</A>, <A HREF = "print.html">print</A>,
<A HREF = "if.html">if</A> commands for examples. A "#" or "$" character that is <A HREF = "if.html">if</A>, and <A HREF = "python.html">python</A> commands for examples.
between quotes will not be treated as a comment indicator in (2) or </P>
substituted for as a variable in (3). <P>A "#" or "$" character that is between quotes will not be treated as a
comment indicator in (2) or substituted for as a variable in (3).
</P> </P>
<P>IMPORTANT NOTE: If the argument is itself a command that requires a <P>IMPORTANT NOTE: If the argument is itself a command that requires a
quoted argument (e.g. using a <A HREF = "print.html">print</A> command as part of an quoted argument (e.g. using a <A HREF = "print.html">print</A> command as part of an
<A HREF = "if.html">if</A> or <A HREF = "run.html">run every</A> command), then the double and <A HREF = "if.html">if</A> or <A HREF = "run.html">run every</A> command), then single, double, or
single quotes can be nested in the usual manner. See the doc pages triple quotes can be nested in the usual manner. See the doc pages
for those commands for examples. Only one of level of nesting is for those commands for examples. Only one of level of nesting is
allowed, but that should be sufficient for most use cases. allowed, but that should be sufficient for most use cases.
</P> </P>
@ -407,12 +419,12 @@ g = GPU, i = USER-INTEL, k = KOKKOS, o = USER-OMP, t = OPT.
<TR ALIGN="center"><TD ><A HREF = "fix_nh.html">npt (co)</A></TD><TD ><A HREF = "fix_npt_asphere.html">npt/asphere (o)</A></TD><TD ><A HREF = "fix_npt_sphere.html">npt/sphere (o)</A></TD><TD ><A HREF = "fix_nve.html">nve (cko)</A></TD><TD ><A HREF = "fix_nve_asphere.html">nve/asphere</A></TD><TD ><A HREF = "fix_nve_asphere_noforce.html">nve/asphere/noforce</A></TD><TD ><A HREF = "fix_nve_body.html">nve/body</A></TD><TD ><A HREF = "fix_nve_limit.html">nve/limit</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "fix_nh.html">npt (co)</A></TD><TD ><A HREF = "fix_npt_asphere.html">npt/asphere (o)</A></TD><TD ><A HREF = "fix_npt_sphere.html">npt/sphere (o)</A></TD><TD ><A HREF = "fix_nve.html">nve (cko)</A></TD><TD ><A HREF = "fix_nve_asphere.html">nve/asphere</A></TD><TD ><A HREF = "fix_nve_asphere_noforce.html">nve/asphere/noforce</A></TD><TD ><A HREF = "fix_nve_body.html">nve/body</A></TD><TD ><A HREF = "fix_nve_limit.html">nve/limit</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "fix_nve_line.html">nve/line</A></TD><TD ><A HREF = "fix_nve_noforce.html">nve/noforce</A></TD><TD ><A HREF = "fix_nve_sphere.html">nve/sphere (o)</A></TD><TD ><A HREF = "fix_nve_tri.html">nve/tri</A></TD><TD ><A HREF = "fix_nh.html">nvt (co)</A></TD><TD ><A HREF = "fix_nvt_asphere.html">nvt/asphere (o)</A></TD><TD ><A HREF = "fix_nvt_sllod.html">nvt/sllod (o)</A></TD><TD ><A HREF = "fix_nvt_sphere.html">nvt/sphere (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "fix_nve_line.html">nve/line</A></TD><TD ><A HREF = "fix_nve_noforce.html">nve/noforce</A></TD><TD ><A HREF = "fix_nve_sphere.html">nve/sphere (o)</A></TD><TD ><A HREF = "fix_nve_tri.html">nve/tri</A></TD><TD ><A HREF = "fix_nh.html">nvt (co)</A></TD><TD ><A HREF = "fix_nvt_asphere.html">nvt/asphere (o)</A></TD><TD ><A HREF = "fix_nvt_sllod.html">nvt/sllod (o)</A></TD><TD ><A HREF = "fix_nvt_sphere.html">nvt/sphere (o)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "fix_oneway.html">oneway</A></TD><TD ><A HREF = "fix_orient_fcc.html">orient/fcc</A></TD><TD ><A HREF = "fix_planeforce.html">planeforce</A></TD><TD ><A HREF = "fix_poems.html">poems</A></TD><TD ><A HREF = "fix_pour.html">pour</A></TD><TD ><A HREF = "fix_press_berendsen.html">press/berendsen</A></TD><TD ><A HREF = "fix_print.html">print</A></TD><TD ><A HREF = "fix_property_atom.html">property/atom</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "fix_oneway.html">oneway</A></TD><TD ><A HREF = "fix_orient_fcc.html">orient/fcc</A></TD><TD ><A HREF = "fix_planeforce.html">planeforce</A></TD><TD ><A HREF = "fix_poems.html">poems</A></TD><TD ><A HREF = "fix_pour.html">pour</A></TD><TD ><A HREF = "fix_press_berendsen.html">press/berendsen</A></TD><TD ><A HREF = "fix_print.html">print</A></TD><TD ><A HREF = "fix_property_atom.html">property/atom</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "fix_qeq_comb.html">qeq/comb (o)</A></TD><TD ><A HREF = "fix_qeq.html">qeq/dynamic</A></TD><TD ><A HREF = "fix_qeq.html">qeq/point</A></TD><TD ><A HREF = "fix_qeq.html">qeq/shielded</A></TD><TD ><A HREF = "fix_qeq.html">qeq/slater</A></TD><TD ><A HREF = "fix_shake.html">rattle</A></TD><TD ><A HREF = "fix_reax_bonds.html">reax/bonds</A></TD><TD ><A HREF = "fix_recenter.html">recenter</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "fix_qeq_comb.html">qeq/comb (o)</A></TD><TD ><A HREF = "fix_qeq.html">qeq/dynamic</A></TD><TD ><A HREF = "fix_qeq.html">qeq/point</A></TD><TD ><A HREF = "fix_qeq.html">qeq/shielded</A></TD><TD ><A HREF = "fix_qeq.html">qeq/slater</A></TD><TD ><A HREF = "fix_reax_bonds.html">reax/bonds</A></TD><TD ><A HREF = "fix_recenter.html">recenter</A></TD><TD ><A HREF = "fix_restrain.html">restrain</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "fix_restrain.html">restrain</A></TD><TD ><A HREF = "fix_rigid.html">rigid (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/nph (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/npt (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/nve (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/nvt (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/small (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/small/nph</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "fix_rigid.html">rigid (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/nph (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/npt (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/nve (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/nvt (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/small (o)</A></TD><TD ><A HREF = "fix_rigid.html">rigid/small/nph</A></TD><TD ><A HREF = "fix_rigid.html">rigid/small/npt</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "fix_rigid.html">rigid/small/npt</A></TD><TD ><A HREF = "fix_rigid.html">rigid/small/nve</A></TD><TD ><A HREF = "fix_rigid.html">rigid/small/nvt</A></TD><TD ><A HREF = "fix_setforce.html">setforce (c)</A></TD><TD ><A HREF = "fix_shake.html">shake (c)</A></TD><TD ><A HREF = "fix_spring.html">spring</A></TD><TD ><A HREF = "fix_spring_rg.html">spring/rg</A></TD><TD ><A HREF = "fix_spring_self.html">spring/self</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "fix_rigid.html">rigid/small/nve</A></TD><TD ><A HREF = "fix_rigid.html">rigid/small/nvt</A></TD><TD ><A HREF = "fix_setforce.html">setforce (c)</A></TD><TD ><A HREF = "fix_shake.html">shake (c)</A></TD><TD ><A HREF = "fix_spring.html">spring</A></TD><TD ><A HREF = "fix_spring_rg.html">spring/rg</A></TD><TD ><A HREF = "fix_spring_self.html">spring/self</A></TD><TD ><A HREF = "fix_srd.html">srd</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "fix_srd.html">srd</A></TD><TD ><A HREF = "fix_store_force.html">store/force</A></TD><TD ><A HREF = "fix_store_state.html">store/state</A></TD><TD ><A HREF = "fix_temp_berendsen.html">temp/berendsen (c)</A></TD><TD ><A HREF = "fix_temp_csvr.html">temp/csvr</A></TD><TD ><A HREF = "fix_temp_rescale.html">temp/rescale (c)</A></TD><TD ><A HREF = "fix_tfmc.html">tfmc</A></TD><TD ><A HREF = "fix_thermal_conductivity.html">thermal/conductivity</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "fix_store_force.html">store/force</A></TD><TD ><A HREF = "fix_store_state.html">store/state</A></TD><TD ><A HREF = "fix_temp_berendsen.html">temp/berendsen (c)</A></TD><TD ><A HREF = "fix_temp_csvr.html">temp/csvr</A></TD><TD ><A HREF = "fix_temp_rescale.html">temp/rescale (c)</A></TD><TD ><A HREF = "fix_tfmc.html">tfmc</A></TD><TD ><A HREF = "fix_thermal_conductivity.html">thermal/conductivity</A></TD><TD ><A HREF = "fix_tmd.html">tmd</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "fix_tmd.html">tmd</A></TD><TD ><A HREF = "fix_ttm.html">ttm</A></TD><TD ><A HREF = "fix_tune_kspace.html">tune/kspace</A></TD><TD ><A HREF = "fix_vector.html">vector</A></TD><TD ><A HREF = "fix_viscosity.html">viscosity</A></TD><TD ><A HREF = "fix_viscous.html">viscous (c)</A></TD><TD ><A HREF = "fix_wall.html">wall/colloid</A></TD><TD ><A HREF = "fix_wall_gran.html">wall/gran</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "fix_ttm.html">ttm</A></TD><TD ><A HREF = "fix_tune_kspace.html">tune/kspace</A></TD><TD ><A HREF = "fix_vector.html">vector</A></TD><TD ><A HREF = "fix_viscosity.html">viscosity</A></TD><TD ><A HREF = "fix_viscous.html">viscous (c)</A></TD><TD ><A HREF = "fix_wall.html">wall/colloid</A></TD><TD ><A HREF = "fix_wall_gran.html">wall/gran</A></TD><TD ><A HREF = "fix_wall.html">wall/harmonic</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "fix_wall.html">wall/harmonic</A></TD><TD ><A HREF = "fix_wall.html">wall/lj1043</A></TD><TD ><A HREF = "fix_wall.html">wall/lj126</A></TD><TD ><A HREF = "fix_wall.html">wall/lj93</A></TD><TD ><A HREF = "fix_wall_piston.html">wall/piston</A></TD><TD ><A HREF = "fix_wall_reflect.html">wall/reflect</A></TD><TD ><A HREF = "fix_wall_region.html">wall/region</A></TD><TD ><A HREF = "fix_wall_srd.html">wall/srd</A> <TR ALIGN="center"><TD ><A HREF = "fix_wall.html">wall/lj1043</A></TD><TD ><A HREF = "fix_wall.html">wall/lj126</A></TD><TD ><A HREF = "fix_wall.html">wall/lj93</A></TD><TD ><A HREF = "fix_wall_piston.html">wall/piston</A></TD><TD ><A HREF = "fix_wall_reflect.html">wall/reflect</A></TD><TD ><A HREF = "fix_wall_region.html">wall/region</A></TD><TD ><A HREF = "fix_wall_srd.html">wall/srd</A>
</TD></TR></TABLE></DIV> </TD></TR></TABLE></DIV>
<P>These are additional fix styles in USER packages, which can be used if <P>These are additional fix styles in USER packages, which can be used if
@ -449,9 +461,9 @@ KOKKOS, o = USER-OMP, t = OPT.
<TR ALIGN="center"><TD ><A HREF = "compute_msd_chunk.html">msd/chunk</A></TD><TD ><A HREF = "compute_msd_nongauss.html">msd/nongauss</A></TD><TD ><A HREF = "compute_pair.html">pair</A></TD><TD ><A HREF = "compute_pair_local.html">pair/local</A></TD><TD ><A HREF = "compute_pe.html">pe (c)</A></TD><TD ><A HREF = "compute_pe_atom.html">pe/atom</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "compute_msd_chunk.html">msd/chunk</A></TD><TD ><A HREF = "compute_msd_nongauss.html">msd/nongauss</A></TD><TD ><A HREF = "compute_pair.html">pair</A></TD><TD ><A HREF = "compute_pair_local.html">pair/local</A></TD><TD ><A HREF = "compute_pe.html">pe (c)</A></TD><TD ><A HREF = "compute_pe_atom.html">pe/atom</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "compute_plasticity_atom.html">plasticity/atom</A></TD><TD ><A HREF = "compute_pressure.html">pressure (c)</A></TD><TD ><A HREF = "compute_property_atom.html">property/atom</A></TD><TD ><A HREF = "compute_property_local.html">property/local</A></TD><TD ><A HREF = "compute_property_chunk.html">property/chunk</A></TD><TD ><A HREF = "compute_rdf.html">rdf</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "compute_plasticity_atom.html">plasticity/atom</A></TD><TD ><A HREF = "compute_pressure.html">pressure (c)</A></TD><TD ><A HREF = "compute_property_atom.html">property/atom</A></TD><TD ><A HREF = "compute_property_local.html">property/local</A></TD><TD ><A HREF = "compute_property_chunk.html">property/chunk</A></TD><TD ><A HREF = "compute_rdf.html">rdf</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "compute_reduce.html">reduce</A></TD><TD ><A HREF = "compute_reduce.html">reduce/region</A></TD><TD ><A HREF = "compute_slice.html">slice</A></TD><TD ><A HREF = "compute_sna.html">sna/atom</A></TD><TD ><A HREF = "compute_sna.html">snad/atom</A></TD><TD ><A HREF = "compute_sna.html">snav/atom</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "compute_reduce.html">reduce</A></TD><TD ><A HREF = "compute_reduce.html">reduce/region</A></TD><TD ><A HREF = "compute_slice.html">slice</A></TD><TD ><A HREF = "compute_sna.html">sna/atom</A></TD><TD ><A HREF = "compute_sna.html">snad/atom</A></TD><TD ><A HREF = "compute_sna.html">snav/atom</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "compute_stress_atom.html">stress/atom</A></TD><TD ><A HREF = "compute_temp.html">temp (c)</A></TD><TD ><A HREF = "compute_temp_asphere.html">temp/asphere</A></TD><TD ><A HREF = "compute_temp_com.html">temp/com</A></TD><TD ><A HREF = "compute_temp_chunk.html">temp/chunk</A></TD><TD ><A HREF = "compute_temp_cs.html">temp/cs</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "compute_stress_atom.html">stress/atom</A></TD><TD ><A HREF = "compute_temp.html">temp (c)</A></TD><TD ><A HREF = "compute_temp_asphere.html">temp/asphere</A></TD><TD ><A HREF = "compute_temp_com.html">temp/com</A></TD><TD ><A HREF = "compute_temp_chunk.html">temp/chunk</A></TD><TD ><A HREF = "compute_temp_deform.html">temp/deform</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "compute_temp_deform.html">temp/deform</A></TD><TD ><A HREF = "compute_temp_partial.html">temp/partial (c)</A></TD><TD ><A HREF = "compute_temp_profile.html">temp/profile</A></TD><TD ><A HREF = "compute_temp_ramp.html">temp/ramp</A></TD><TD ><A HREF = "compute_temp_region.html">temp/region</A></TD><TD ><A HREF = "compute_temp_sphere.html">temp/sphere</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "compute_temp_partial.html">temp/partial (c)</A></TD><TD ><A HREF = "compute_temp_profile.html">temp/profile</A></TD><TD ><A HREF = "compute_temp_ramp.html">temp/ramp</A></TD><TD ><A HREF = "compute_temp_region.html">temp/region</A></TD><TD ><A HREF = "compute_temp_sphere.html">temp/sphere</A></TD><TD ><A HREF = "compute_ti.html">ti</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "compute_ti.html">ti</A></TD><TD ><A HREF = "compute_torque_chunk.html">torque/chunk</A></TD><TD ><A HREF = "compute_vacf.html">vacf</A></TD><TD ><A HREF = "compute_vcm_chunk.html">vcm/chunk</A></TD><TD ><A HREF = "compute_voronoi_atom.html">voronoi/atom</A> <TR ALIGN="center"><TD ><A HREF = "compute_torque_chunk.html">torque/chunk</A></TD><TD ><A HREF = "compute_vacf.html">vacf</A></TD><TD ><A HREF = "compute_vcm_chunk.html">vcm/chunk</A></TD><TD ><A HREF = "compute_voronoi_atom.html">voronoi/atom</A>
</TD></TR></TABLE></DIV> </TD></TR></TABLE></DIV>
<P>These are additional compute styles in USER packages, which can be <P>These are additional compute styles in USER packages, which can be
@ -478,31 +490,30 @@ KOKKOS, o = USER-OMP, t = OPT.
<DIV ALIGN=center><TABLE BORDER=1 > <DIV ALIGN=center><TABLE BORDER=1 >
<TR ALIGN="center"><TD ><A HREF = "pair_none.html">none</A></TD><TD ><A HREF = "pair_hybrid.html">hybrid</A></TD><TD ><A HREF = "pair_hybrid.html">hybrid/overlay</A></TD><TD ><A HREF = "pair_adp.html">adp (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_none.html">none</A></TD><TD ><A HREF = "pair_hybrid.html">hybrid</A></TD><TD ><A HREF = "pair_hybrid.html">hybrid/overlay</A></TD><TD ><A HREF = "pair_adp.html">adp (o)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_airebo.html">airebo (o)</A></TD><TD ><A HREF = "pair_beck.html">beck (go)</A></TD><TD ><A HREF = "pair_body.html">body</A></TD><TD ><A HREF = "pair_bop.html">bop</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_airebo.html">airebo (o)</A></TD><TD ><A HREF = "pair_beck.html">beck (go)</A></TD><TD ><A HREF = "pair_body.html">body</A></TD><TD ><A HREF = "pair_bop.html">bop</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_born.html">born (go)</A></TD><TD ><A HREF = "pair_born.html">born/coul/long (cgo)</A></TD><TD ><A HREF = "pair_cs.html">born/coul/long/cs</A></TD><TD ><A HREF = "pair_born.html">born/coul/msm (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_born.html">born (go)</A></TD><TD ><A HREF = "pair_born.html">born/coul/long (cgo)</A></TD><TD ><A HREF = "pair_born.html">born/coul/msm (o)</A></TD><TD ><A HREF = "pair_born.html">born/coul/wolf (go)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_born.html">born/coul/wolf (go)</A></TD><TD ><A HREF = "pair_brownian.html">brownian (o)</A></TD><TD ><A HREF = "pair_brownian.html">brownian/poly (o)</A></TD><TD ><A HREF = "pair_buck.html">buck (cgko)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_brownian.html">brownian (o)</A></TD><TD ><A HREF = "pair_brownian.html">brownian/poly (o)</A></TD><TD ><A HREF = "pair_buck.html">buck (cgko)</A></TD><TD ><A HREF = "pair_buck.html">buck/coul/cut (cgo)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_buck.html">buck/coul/cut (cgo)</A></TD><TD ><A HREF = "pair_buck.html">buck/coul/long (cgo)</A></TD><TD ><A HREF = "pair_cs.html">buck/coul/long/cs</A></TD><TD ><A HREF = "pair_buck.html">buck/coul/msm (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_buck.html">buck/coul/long (cgo)</A></TD><TD ><A HREF = "pair_buck.html">buck/coul/msm (o)</A></TD><TD ><A HREF = "pair_buck_long.html">buck/long/coul/long (o)</A></TD><TD ><A HREF = "pair_colloid.html">colloid (go)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_buck_long.html">buck/long/coul/long (o)</A></TD><TD ><A HREF = "pair_colloid.html">colloid (go)</A></TD><TD ><A HREF = "pair_comb.html">comb (o)</A></TD><TD ><A HREF = "pair_comb.html">comb3</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_comb.html">comb (o)</A></TD><TD ><A HREF = "pair_comb.html">comb3</A></TD><TD ><A HREF = "pair_coul.html">coul/cut (gko)</A></TD><TD ><A HREF = "pair_coul.html">coul/debye (go)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_coul.html">coul/cut (gko)</A></TD><TD ><A HREF = "pair_coul.html">coul/debye (go)</A></TD><TD ><A HREF = "pair_coul.html">coul/dsf (gko)</A></TD><TD ><A HREF = "pair_coul.html">coul/long (go)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_coul.html">coul/dsf (gko)</A></TD><TD ><A HREF = "pair_coul.html">coul/long (go)</A></TD><TD ><A HREF = "pair_coul.html">coul/msm</A></TD><TD ><A HREF = "pair_coul.html">coul/streitz</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_coul.html">coul/msm</A></TD><TD ><A HREF = "pair_coul.html">coul/streitz</A></TD><TD ><A HREF = "pair_coul.html">coul/wolf (ko)</A></TD><TD ><A HREF = "pair_dpd.html">dpd (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_coul.html">coul/wolf (ko)</A></TD><TD ><A HREF = "pair_dpd.html">dpd (o)</A></TD><TD ><A HREF = "pair_dpd.html">dpd/tstat (o)</A></TD><TD ><A HREF = "pair_dsmc.html">dsmc</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_dpd.html">dpd/tstat (o)</A></TD><TD ><A HREF = "pair_dsmc.html">dsmc</A></TD><TD ><A HREF = "pair_eam.html">eam (cgkot)</A></TD><TD ><A HREF = "pair_eam.html">eam/alloy (cgot)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_eam.html">eam (cgkot)</A></TD><TD ><A HREF = "pair_eam.html">eam/alloy (cgot)</A></TD><TD ><A HREF = "pair_eam.html">eam/fs (cgot)</A></TD><TD ><A HREF = "pair_eim.html">eim (o)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_eam.html">eam/fs (cgot)</A></TD><TD ><A HREF = "pair_eim.html">eim (o)</A></TD><TD ><A HREF = "pair_gauss.html">gauss (go)</A></TD><TD ><A HREF = "pair_gayberne.html">gayberne (gio)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_gauss.html">gauss (go)</A></TD><TD ><A HREF = "pair_gayberne.html">gayberne (gio)</A></TD><TD ><A HREF = "pair_gran.html">gran/hertz/history (o)</A></TD><TD ><A HREF = "pair_gran.html">gran/hooke (co)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_gran.html">gran/hertz/history (o)</A></TD><TD ><A HREF = "pair_gran.html">gran/hooke (co)</A></TD><TD ><A HREF = "pair_gran.html">gran/hooke/history (o)</A></TD><TD ><A HREF = "pair_hbond_dreiding.html">hbond/dreiding/lj (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_gran.html">gran/hooke/history (o)</A></TD><TD ><A HREF = "pair_hbond_dreiding.html">hbond/dreiding/lj (o)</A></TD><TD ><A HREF = "pair_hbond_dreiding.html">hbond/dreiding/morse (o)</A></TD><TD ><A HREF = "pair_kim.html">kim</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_hbond_dreiding.html">hbond/dreiding/morse (o)</A></TD><TD ><A HREF = "pair_kim.html">kim</A></TD><TD ><A HREF = "pair_lcbop.html">lcbop</A></TD><TD ><A HREF = "pair_line_lj.html">line/lj (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_lcbop.html">lcbop</A></TD><TD ><A HREF = "pair_line_lj.html">line/lj (o)</A></TD><TD ><A HREF = "pair_charmm.html">lj/charmm/coul/charmm (co)</A></TD><TD ><A HREF = "pair_charmm.html">lj/charmm/coul/charmm/implicit (co)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_charmm.html">lj/charmm/coul/charmm (co)</A></TD><TD ><A HREF = "pair_charmm.html">lj/charmm/coul/charmm/implicit (co)</A></TD><TD ><A HREF = "pair_charmm.html">lj/charmm/coul/long (cgio)</A></TD><TD ><A HREF = "pair_charmm.html">lj/charmm/coul/msm</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_charmm.html">lj/charmm/coul/long (cgio)</A></TD><TD ><A HREF = "pair_charmm.html">lj/charmm/coul/msm</A></TD><TD ><A HREF = "pair_class2.html">lj/class2 (cgo)</A></TD><TD ><A HREF = "pair_class2.html">lj/class2/coul/cut (co)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_class2.html">lj/class2 (cgo)</A></TD><TD ><A HREF = "pair_class2.html">lj/class2/coul/cut (co)</A></TD><TD ><A HREF = "pair_class2.html">lj/class2/coul/long (cgo)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut (cgikot)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_class2.html">lj/class2/coul/long (cgo)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut (cgikot)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/coul/cut (cgko)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/coul/debye (cgo)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_lj.html">lj/cut/coul/cut (cgko)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/coul/debye (cgo)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/coul/dsf (go)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/coul/long (cgikot)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_lj.html">lj/cut/coul/dsf (go)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/coul/long (cgikot)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/coul/msm (go)</A></TD><TD ><A HREF = "pair_dipole.html">lj/cut/dipole/cut (go)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_lj.html">lj/cut/coul/msm (go)</A></TD><TD ><A HREF = "pair_dipole.html">lj/cut/dipole/cut (go)</A></TD><TD ><A HREF = "pair_dipole.html">lj/cut/dipole/long</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/tip4p/cut (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_dipole.html">lj/cut/dipole/long</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/tip4p/cut (o)</A></TD><TD ><A HREF = "pair_lj.html">lj/cut/tip4p/long (ot)</A></TD><TD ><A HREF = "pair_lj_expand.html">lj/expand (cgo)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_lj.html">lj/cut/tip4p/long (ot)</A></TD><TD ><A HREF = "pair_lj_expand.html">lj/expand (cgo)</A></TD><TD ><A HREF = "pair_gromacs.html">lj/gromacs (cgo)</A></TD><TD ><A HREF = "pair_gromacs.html">lj/gromacs/coul/gromacs (co)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_gromacs.html">lj/gromacs (cgo)</A></TD><TD ><A HREF = "pair_gromacs.html">lj/gromacs/coul/gromacs (co)</A></TD><TD ><A HREF = "pair_lj_long.html">lj/long/coul/long (o)</A></TD><TD ><A HREF = "pair_dipole.html">lj/long/dipole/long</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_lj_long.html">lj/long/coul/long (o)</A></TD><TD ><A HREF = "pair_dipole.html">lj/long/dipole/long</A></TD><TD ><A HREF = "pair_lj_long.html">lj/long/tip4p/long</A></TD><TD ><A HREF = "pair_lj_smooth.html">lj/smooth (co)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_lj_long.html">lj/long/tip4p/long</A></TD><TD ><A HREF = "pair_lj_smooth.html">lj/smooth (co)</A></TD><TD ><A HREF = "pair_lj_smooth_linear.html">lj/smooth/linear (o)</A></TD><TD ><A HREF = "pair_lj96.html">lj96/cut (cgo)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_lj_smooth_linear.html">lj/smooth/linear (o)</A></TD><TD ><A HREF = "pair_lj96.html">lj96/cut (cgo)</A></TD><TD ><A HREF = "pair_lubricate.html">lubricate (o)</A></TD><TD ><A HREF = "pair_lubricate.html">lubricate/poly (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_lubricate.html">lubricate (o)</A></TD><TD ><A HREF = "pair_lubricate.html">lubricate/poly (o)</A></TD><TD ><A HREF = "pair_lubricateU.html">lubricateU</A></TD><TD ><A HREF = "pair_lubricateU.html">lubricateU/poly</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_lubricateU.html">lubricateU</A></TD><TD ><A HREF = "pair_lubricateU.html">lubricateU/poly</A></TD><TD ><A HREF = "pair_meam.html">meam (o)</A></TD><TD ><A HREF = "pair_mie.html">mie/cut (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_meam.html">meam (o)</A></TD><TD ><A HREF = "pair_mie.html">mie/cut (o)</A></TD><TD ><A HREF = "pair_morse.html">morse (cgot)</A></TD><TD ><A HREF = "pair_nb3b_harmonic.html">nb3b/harmonic (o)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_morse.html">morse (cgot)</A></TD><TD ><A HREF = "pair_nb3b_harmonic.html">nb3b/harmonic (o)</A></TD><TD ><A HREF = "pair_nm.html">nm/cut (o)</A></TD><TD ><A HREF = "pair_nm.html">nm/cut/coul/cut (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_nm.html">nm/cut (o)</A></TD><TD ><A HREF = "pair_nm.html">nm/cut/coul/cut (o)</A></TD><TD ><A HREF = "pair_nm.html">nm/cut/coul/long (o)</A></TD><TD ><A HREF = "pair_peri.html">peri/eps</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_nm.html">nm/cut/coul/long (o)</A></TD><TD ><A HREF = "pair_peri.html">peri/eps</A></TD><TD ><A HREF = "pair_peri.html">peri/lps (o)</A></TD><TD ><A HREF = "pair_peri.html">peri/pmb (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_peri.html">peri/lps (o)</A></TD><TD ><A HREF = "pair_peri.html">peri/pmb (o)</A></TD><TD ><A HREF = "pair_peri.html">peri/ves</A></TD><TD ><A HREF = "pair_reax.html">reax</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_peri.html">peri/ves</A></TD><TD ><A HREF = "pair_reax.html">reax</A></TD><TD ><A HREF = "pair_airebo.html">rebo (o)</A></TD><TD ><A HREF = "pair_resquared.html">resquared (go)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_airebo.html">rebo (o)</A></TD><TD ><A HREF = "pair_resquared.html">resquared (go)</A></TD><TD ><A HREF = "pair_snap.html">snap</A></TD><TD ><A HREF = "pair_soft.html">soft (go)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_snap.html">snap</A></TD><TD ><A HREF = "pair_soft.html">soft (go)</A></TD><TD ><A HREF = "pair_sw.html">sw (cgio)</A></TD><TD ><A HREF = "pair_table.html">table (gko)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_sw.html">sw (cgo)</A></TD><TD ><A HREF = "pair_table.html">table (gko)</A></TD><TD ><A HREF = "pair_tersoff.html">tersoff (co)</A></TD><TD ><A HREF = "pair_tersoff_mod.html">tersoff/mod (o)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_tersoff.html">tersoff (co)</A></TD><TD ><A HREF = "pair_tersoff_mod.html">tersoff/mod (o)</A></TD><TD ><A HREF = "pair_tersoff_zbl.html">tersoff/zbl (o)</A></TD><TD ><A HREF = "pair_coul.html">tip4p/cut (o)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_tersoff_zbl.html">tersoff/zbl (o)</A></TD><TD ><A HREF = "pair_coul.html">tip4p/cut (o)</A></TD><TD ><A HREF = "pair_coul.html">tip4p/long (o)</A></TD><TD ><A HREF = "pair_tri_lj.html">tri/lj (o)</A></TD></TR>
<TR ALIGN="center"><TD ><A HREF = "pair_coul.html">tip4p/long (o)</A></TD><TD ><A HREF = "pair_tri_lj.html">tri/lj (o)</A></TD><TD ><A HREF = "pair_yukawa.html">yukawa (go)</A></TD><TD ><A HREF = "pair_yukawa_colloid.html">yukawa/colloid (go)</A></TD></TR> <TR ALIGN="center"><TD ><A HREF = "pair_yukawa.html">yukawa (go)</A></TD><TD ><A HREF = "pair_yukawa_colloid.html">yukawa/colloid (go)</A></TD><TD ><A HREF = "pair_zbl.html">zbl (o)</A>
<TR ALIGN="center"><TD ><A HREF = "pair_zbl.html">zbl (o)</A>
</TD></TR></TABLE></DIV> </TD></TR></TABLE></DIV>
<P>These are additional pair styles in USER packages, which can be used <P>These are additional pair styles in USER packages, which can be used

View File

@ -82,11 +82,12 @@ file names or user-chosen ID strings.
Here is how each line in the input script is parsed by LAMMPS: Here is how each line in the input script is parsed by LAMMPS:
(1) If the last printable character on the line is a "&" character (1) If the last printable character on the line is a "&" character,
(with no surrounding quotes), the command is assumed to continue on the command is assumed to continue on the next line. The next line is
the next line. The next line is concatenated to the previous line by concatenated to the previous line by removing the "&" character and
removing the "&" character and newline. This allows long commands to line break. This allows long commands to be continued across two or
be continued across two or more lines. more lines. See the discussion of triple quotes in (6) for how to
continue a command across multiple line without using "&" characters.
(2) All characters from the first "#" character onward are treated as (2) All characters from the first "#" character onward are treated as
comment and discarded. See an exception in (6). Note that a comment and discarded. See an exception in (6). Note that a
@ -132,9 +133,9 @@ Note that neither the curly-bracket or immediate form of variables can
contain nested $ characters for other variables to substitute for. contain nested $ characters for other variables to substitute for.
Thus you cannot do this: Thus you cannot do this:
variable a equal 2 variable a equal 2
variable b2 equal 4 variable b2 equal 4
region 1 block $\{b$a\} 2 INF INF EDGE EDGE :pre print "B2 = $\{b$a\}" :pre
Nor can you specify this $($x-1.0) for an immediate variable, but Nor can you specify this $($x-1.0) for an immediate variable, but
you could use $(v_x-1.0), since the latter is valid syntax for an you could use $(v_x-1.0), since the latter is valid syntax for an
@ -152,27 +153,38 @@ underscores, or punctuation characters.
line are arguments. line are arguments.
(6) If you want text with spaces to be treated as a single argument, (6) If you want text with spaces to be treated as a single argument,
it can be enclosed in either double or single quotes. A long single it can be enclosed in either single or double or triple quotes. A
argument enclosed in quotes can even span multiple lines if the "&" long single argument enclosed in single or double quotes can span
character is used, as described above. E.g. multiple lines if the "&" character is used, as described above. When
the lines are concatenated together (and the "&" characters and line
breaks removed), the text will become a single line. If you want
multiple lines of an argument to retain their line breaks, the text
can be enclosed in triple quotes, in which case "&" characters are not
needed. For example:
print "Volume = $v" print "Volume = $v"
print 'Volume = $v' print 'Volume = $v'
if "${steps} > 1000" then quit
variable a string "red green blue & variable a string "red green blue &
purple orange cyan" purple orange cyan"
if "${steps} > 1000" then quit :pre print """
System volume = $v
System temperature = $t
""" :pre
The quotes are removed when the single argument is stored internally. In each case, the single, double, or triple quotes are removed when
the single argument they enclose is stored internally.
See the "dump modify format"_dump_modify.html or "print"_print.html or See the "dump modify format"_dump_modify.html, "print"_print.html,
"if"_if.html commands for examples. A "#" or "$" character that is "if"_if.html, and "python"_python.html commands for examples.
between quotes will not be treated as a comment indicator in (2) or
substituted for as a variable in (3). A "#" or "$" character that is between quotes will not be treated as a
comment indicator in (2) or substituted for as a variable in (3).
IMPORTANT NOTE: If the argument is itself a command that requires a IMPORTANT NOTE: If the argument is itself a command that requires a
quoted argument (e.g. using a "print"_print.html command as part of an quoted argument (e.g. using a "print"_print.html command as part of an
"if"_if.html or "run every"_run.html command), then the double and "if"_if.html or "run every"_run.html command), then single, double, or
single quotes can be nested in the usual manner. See the doc pages triple quotes can be nested in the usual manner. See the doc pages
for those commands for examples. Only one of level of nesting is for those commands for examples. Only one of level of nesting is
allowed, but that should be sufficient for most use cases. allowed, but that should be sufficient for most use cases.
@ -535,7 +547,6 @@ g = GPU, i = USER-INTEL, k = KOKKOS, o = USER-OMP, t = OPT.
"qeq/point"_fix_qeq.html, "qeq/point"_fix_qeq.html,
"qeq/shielded"_fix_qeq.html, "qeq/shielded"_fix_qeq.html,
"qeq/slater"_fix_qeq.html, "qeq/slater"_fix_qeq.html,
"rattle"_fix_shake.html,
"reax/bonds"_fix_reax_bonds.html, "reax/bonds"_fix_reax_bonds.html,
"recenter"_fix_recenter.html, "recenter"_fix_recenter.html,
"restrain"_fix_restrain.html, "restrain"_fix_restrain.html,
@ -681,7 +692,6 @@ KOKKOS, o = USER-OMP, t = OPT.
"temp/asphere"_compute_temp_asphere.html, "temp/asphere"_compute_temp_asphere.html,
"temp/com"_compute_temp_com.html, "temp/com"_compute_temp_com.html,
"temp/chunk"_compute_temp_chunk.html, "temp/chunk"_compute_temp_chunk.html,
"temp/cs"_compute_temp_cs.html,
"temp/deform"_compute_temp_deform.html, "temp/deform"_compute_temp_deform.html,
"temp/partial (c)"_compute_temp_partial.html, "temp/partial (c)"_compute_temp_partial.html,
"temp/profile"_compute_temp_profile.html, "temp/profile"_compute_temp_profile.html,
@ -733,7 +743,6 @@ KOKKOS, o = USER-OMP, t = OPT.
"bop"_pair_bop.html, "bop"_pair_bop.html,
"born (go)"_pair_born.html, "born (go)"_pair_born.html,
"born/coul/long (cgo)"_pair_born.html, "born/coul/long (cgo)"_pair_born.html,
"born/coul/long/cs"_pair_cs.html,
"born/coul/msm (o)"_pair_born.html, "born/coul/msm (o)"_pair_born.html,
"born/coul/wolf (go)"_pair_born.html, "born/coul/wolf (go)"_pair_born.html,
"brownian (o)"_pair_brownian.html, "brownian (o)"_pair_brownian.html,
@ -741,7 +750,6 @@ KOKKOS, o = USER-OMP, t = OPT.
"buck (cgko)"_pair_buck.html, "buck (cgko)"_pair_buck.html,
"buck/coul/cut (cgo)"_pair_buck.html, "buck/coul/cut (cgo)"_pair_buck.html,
"buck/coul/long (cgo)"_pair_buck.html, "buck/coul/long (cgo)"_pair_buck.html,
"buck/coul/long/cs"_pair_cs.html,
"buck/coul/msm (o)"_pair_buck.html, "buck/coul/msm (o)"_pair_buck.html,
"buck/long/coul/long (o)"_pair_buck_long.html, "buck/long/coul/long (o)"_pair_buck_long.html,
"colloid (go)"_pair_colloid.html, "colloid (go)"_pair_colloid.html,
@ -817,7 +825,7 @@ KOKKOS, o = USER-OMP, t = OPT.
"resquared (go)"_pair_resquared.html, "resquared (go)"_pair_resquared.html,
"snap"_pair_snap.html, "snap"_pair_snap.html,
"soft (go)"_pair_soft.html, "soft (go)"_pair_soft.html,
"sw (cgio)"_pair_sw.html, "sw (cgo)"_pair_sw.html,
"table (gko)"_pair_table.html, "table (gko)"_pair_table.html,
"tersoff (co)"_pair_tersoff.html, "tersoff (co)"_pair_tersoff.html,
"tersoff/mod (o)"_pair_tersoff_mod.html, "tersoff/mod (o)"_pair_tersoff_mod.html,

View File

@ -63,6 +63,7 @@ packages, more details are provided.
<TR ALIGN="center"><TD >OPT</TD><TD > optimized pair styles</TD><TD > Fischer & Richie & Natoli (2)</TD><TD > <A HREF = "accelerate_opt.html">Section accelerate</A></TD><TD > -</TD><TD > -</TD></TR> <TR ALIGN="center"><TD >OPT</TD><TD > optimized pair styles</TD><TD > Fischer & Richie & Natoli (2)</TD><TD > <A HREF = "accelerate_opt.html">Section accelerate</A></TD><TD > -</TD><TD > -</TD></TR>
<TR ALIGN="center"><TD >PERI</TD><TD > Peridynamics models</TD><TD > Mike Parks (Sandia)</TD><TD > <A HREF = "pair_peri.html">pair_style peri</A></TD><TD > peri</TD><TD > -</TD></TR> <TR ALIGN="center"><TD >PERI</TD><TD > Peridynamics models</TD><TD > Mike Parks (Sandia)</TD><TD > <A HREF = "pair_peri.html">pair_style peri</A></TD><TD > peri</TD><TD > -</TD></TR>
<TR ALIGN="center"><TD >POEMS</TD><TD > coupled rigid body motion</TD><TD > Rudra Mukherjee (JPL)</TD><TD > <A HREF = "fix_poems.html">fix poems</A></TD><TD > rigid</TD><TD > lib/poems</TD></TR> <TR ALIGN="center"><TD >POEMS</TD><TD > coupled rigid body motion</TD><TD > Rudra Mukherjee (JPL)</TD><TD > <A HREF = "fix_poems.html">fix poems</A></TD><TD > rigid</TD><TD > lib/poems</TD></TR>
<TR ALIGN="center"><TD >PYTHON</TD><TD > embed Python code in an input script</TD><TD > -</TD><TD > <A HREF = "python.html">python</A></TD><TD > python</TD><TD > lib/python</TD></TR>
<TR ALIGN="center"><TD >REAX</TD><TD > ReaxFF potential</TD><TD > Aidan Thompson (Sandia)</TD><TD > <A HREF = "pair_reax.html">pair_style reax</A></TD><TD > reax</TD><TD > lib/reax</TD></TR> <TR ALIGN="center"><TD >REAX</TD><TD > ReaxFF potential</TD><TD > Aidan Thompson (Sandia)</TD><TD > <A HREF = "pair_reax.html">pair_style reax</A></TD><TD > reax</TD><TD > lib/reax</TD></TR>
<TR ALIGN="center"><TD >REPLICA</TD><TD > multi-replica methods</TD><TD > -</TD><TD > <A HREF = "Section_howto.html#howto_5">Section_howto 6.5</A></TD><TD > tad</TD><TD > -</TD></TR> <TR ALIGN="center"><TD >REPLICA</TD><TD > multi-replica methods</TD><TD > -</TD><TD > <A HREF = "Section_howto.html#howto_5">Section_howto 6.5</A></TD><TD > tad</TD><TD > -</TD></TR>
<TR ALIGN="center"><TD >RIGID</TD><TD > rigid bodies</TD><TD > -</TD><TD > <A HREF = "fix_rigid.html">fix rigid</A></TD><TD > rigid</TD><TD > -</TD></TR> <TR ALIGN="center"><TD >RIGID</TD><TD > rigid bodies</TD><TD > -</TD><TD > <A HREF = "fix_rigid.html">fix rigid</A></TD><TD > rigid</TD><TD > -</TD></TR>

View File

@ -58,6 +58,7 @@ MOLECULE, molecular system force fields, -, "Section_howto 6.3"_Section_howto.ht
OPT, optimized pair styles, Fischer & Richie & Natoli (2), "Section accelerate"_accelerate_opt.html, -, - OPT, optimized pair styles, Fischer & Richie & Natoli (2), "Section accelerate"_accelerate_opt.html, -, -
PERI, Peridynamics models, Mike Parks (Sandia), "pair_style peri"_pair_peri.html, peri, - PERI, Peridynamics models, Mike Parks (Sandia), "pair_style peri"_pair_peri.html, peri, -
POEMS, coupled rigid body motion, Rudra Mukherjee (JPL), "fix poems"_fix_poems.html, rigid, lib/poems POEMS, coupled rigid body motion, Rudra Mukherjee (JPL), "fix poems"_fix_poems.html, rigid, lib/poems
PYTHON, embed Python code in an input script, -, "python"_python.html, python, lib/python
REAX, ReaxFF potential, Aidan Thompson (Sandia), "pair_style reax"_pair_reax.html, reax, lib/reax REAX, ReaxFF potential, Aidan Thompson (Sandia), "pair_style reax"_pair_reax.html, reax, lib/reax
REPLICA, multi-replica methods, -, "Section_howto 6.5"_Section_howto.html#howto_5, tad, - REPLICA, multi-replica methods, -, "Section_howto 6.5"_Section_howto.html#howto_5, tad, -
RIGID, rigid bodies, -, "fix rigid"_fix_rigid.html, rigid, - RIGID, rigid bodies, -, "fix rigid"_fix_rigid.html, rigid, -

View File

@ -11,61 +11,98 @@
<H3>11. Python interface to LAMMPS <H3>11. Python interface to LAMMPS
</H3> </H3>
<P>This section describes how to build and use LAMMPS via a Python <P>LAMMPS can work together with Python in two ways. First, Python can
interface. wrap LAMMPS through the <A HREF = "Section_howto.html#howto_19">LAMMPS library
interface</A>, so that a Python script can
create one or more instances of LAMMPS and launch one or more
simulations. In Python lingo, this is "extending" Python with LAMMPS.
</P> </P>
<UL><LI>11.1 <A HREF = "#py_1">Building LAMMPS as a shared library</A> <P>Second, LAMMPS can use the Python interpreter, so that a LAMMPS input
<LI>11.2 <A HREF = "#py_2">Installing the Python wrapper into Python</A> script can invoke Python code, and pass information back-and-forth
<LI>11.3 <A HREF = "#py_3">Extending Python with MPI to run in parallel</A> between the input script and Python functions you write. The Python
<LI>11.4 <A HREF = "#py_4">Testing the Python-LAMMPS interface</A> code can also callback to LAMMPS to query or change its attributes.
<LI>11.5 <A HREF = "#py_5">Using LAMMPS from Python</A> In Python lingo, this is "embedding" Python in LAMMPS.
<LI>11.6 <A HREF = "#py_6">Example Python scripts that use LAMMPS</A> </P>
<P>This section describes how to do both.
</P>
<UL><LI>11.1 <A HREF = "#py_1">Overview of running LAMMPS from Python</A>
<LI>11.2 <A HREF = "#py_2">Overview of using Python from a LAMMPS script</A>
<LI>11.3 <A HREF = "#py_3">Building LAMMPS as a shared library</A>
<LI>11.4 <A HREF = "#py_4">Installing the Python wrapper into Python</A>
<LI>11.5 <A HREF = "#py_5">Extending Python with MPI to run in parallel</A>
<LI>11.6 <A HREF = "#py_6">Testing the Python-LAMMPS interface</A>
<LI>11.7 <A HREF = "#py_7">Using LAMMPS from Python</A>
<LI>11.8 <A HREF = "#py_8">Example Python scripts that use LAMMPS</A>
</UL> </UL>
<P>The LAMMPS distribution includes the file python/lammps.py which wraps <P>If you are not familiar with it, <A HREF = "http://www.python.org">Python</A> is a
the library interface to LAMMPS. This file makes it is possible to powerful scripting and programming language which can essentially do
run LAMMPS, invoke LAMMPS commands or give it an input script, extract anything that faster, lower-level languages like C or C++ can do, but
LAMMPS results, an modify internal LAMMPS variables, either from a typically with much fewer lines of code. When used in embedded mode,
Python script or interactively from a Python prompt. You can do the Python can perform operations that the simplistic LAMMPS input script
former in serial or parallel. Running Python interactively in syntax cannot. Python can be also be used as a "glue" language to
parallel does not generally work, unless you have a package installed drive a program through its library interface, or to hook multiple
that extends your Python to enable multiple instances of Python to pieces of software together, such as a simulation package plus a
read what you type. visualization package, or to run a coupled multiscale or multiphysics
model.
</P> </P>
<P><A HREF = "http://www.python.org">Python</A> is a powerful scripting and programming <P>See <A HREF = "Section_howto.html#howto_10">Section_howto 10</A> of the manual and
language which can be used to wrap software like LAMMPS and other the couple directory of the distribution for more ideas about coupling
packages. It can be used to glue multiple pieces of software LAMMPS to other codes. See <A HREF = "Section_howto.html#howto_19">Section_howto
together, e.g. to run a coupled or multiscale model. See <A HREF = "Section_howto.html#howto_10">Section 19</A> for a description of the LAMMPS
section</A> of the manual and the couple library interface provided in src/library.cpp and src/library.h, and
directory of the distribution for more ideas about coupling LAMMPS to how to extend it for your needs. As described below, that interface
other codes. See <A HREF = "Section_start.html#start_5">Section_start 4</A> about is what is exposed to Python either when calling LAMMPS from Python or
how to build LAMMPS as a library, and <A HREF = "Section_howto.html#howto_19">Section_howto when calling Python from a LAMMPS input script and then calling back
19</A> for a description of the library to LAMMPS from Python code. The library interface is designed to be
interface provided in src/library.cpp and src/library.h and how to easy to add functions to. Thus the Python interface to LAMMPS is also
extend it for your needs. As described below, that interface is what easy to extend as well.
is exposed to Python. It is designed to be easy to add functions to.
This can easily extend the Python inteface as well. See details
below.
</P> </P>
<P>By using the Python interface, LAMMPS can also be coupled with a GUI <P>If you create interesting Python scripts that run LAMMPS or
or other visualization tools that display graphs or animations in real interesting Python functions that can be called from a LAMMPS input
time as LAMMPS runs. Examples of such scripts are inlcluded in the script, that you think would be useful to other users, please <A HREF = "http://lammps.sandia.gov/authors.html">email
python directory. them to the developers</A>. We can
include them in the LAMMPS distribution.
</P> </P>
<P>Two advantages of using Python are how concise the language is, and <HR>
that it can be run interactively, enabling rapid development and
debugging of programs. If you use it to mostly invoke costly <HR>
operations within LAMMPS, such as running a simulation for a
<A NAME = "py_1"></A><H4>11.1 Overview of running LAMMPS from Python
</H4>
<P>The LAMMPS distribution includes a python directory with all you need
to run LAMMPS from Python. The python/lammps.py file wraps the LAMMPS
library interface, with one wrapper function per LAMMPS library
function. This file makes it is possible to do the following either
from a Python script, or interactively from a Python prompt: create
one or more instances of LAMMPS, invoke LAMMPS commands or give it an
input script, run LAMMPS incrementally, extract LAMMPS results, an
modify internal LAMMPS variables. From a Python script you can do
this in serial or parallel. Running Python interactively in parallel
does not generally work, unless you have a version of Python that
extends standard Python to enable multiple instances of Python to read
what you type.
</P>
<P>To do all of this, you must first build LAMMPS as a shared library,
then insure that your Python can find the python/lammps.py file and
the shared library. These steps are explained in subsequent sections
11.3 and 11.4. Sections 11.5 and 11.6 discuss using MPI from a
parallel Python program and how to test that you are ready to use
LAMMPS from Python. Section 11.7 lists all the functions in the
current LAMMPS library interface and how to call them from Python.
</P>
<P>Section 11.8 gives some examples of coupling LAMMPS to other tools via
Python. For example, LAMMPS can easily be coupled to a GUI or other
visualization tools that display graphs or animations in real time as
LAMMPS runs. Examples of such scripts are inlcluded in the python
directory.
</P>
<P>Two advantages of using Python to run LAMMPS are how concise the
language is, and that it can be run interactively, enabling rapid
development and debugging of programs. If you use it to mostly invoke
costly operations within LAMMPS, such as running a simulation for a
reasonable number of timesteps, then the overhead cost of invoking reasonable number of timesteps, then the overhead cost of invoking
LAMMPS thru Python will be negligible. LAMMPS thru Python will be negligible.
</P> </P>
<P>Before using LAMMPS from a Python script, you need to do two things.
You need to build LAMMPS as a dynamic shared library, so it can be
loaded by Python. And you need to tell Python how to find the library
and the Python wrapper file python/lammps.py. Both these steps are
discussed below. If you wish to run LAMMPS in parallel from Python,
you also need to extend your Python with MPI. This is also discussed
below.
</P>
<P>The Python wrapper for LAMMPS uses the amazing and magical (to me) <P>The Python wrapper for LAMMPS uses the amazing and magical (to me)
"ctypes" package in Python, which auto-generates the interface code "ctypes" package in Python, which auto-generates the interface code
needed between Python and a set of C interface routines for a library. needed between Python and a set of C interface routines for a library.
@ -75,16 +112,82 @@ check which version of Python you have installed, by simply typing
</P> </P>
<HR> <HR>
<A NAME = "py_2"></A><H4>11.2 Overview of using Python from a LAMMPS script
</H4>
<P>IMPORTANT NOTE: It is not currently possible to use the
<A HREF = "python.html">python</A> command described in this section with Python 3,
only with Python 2. The C API changed from Python 2 to 3 and the
LAMMPS code is not compatible with both.
</P>
<P>LAMMPS has a <A HREF = "python.html">python</A> command which can be used in an
input script to define and execute a Python function that you write
the code for. The Python function can also be assigned to a LAMMPS
python-style variable via the <A HREF = "variable.html">variable</A> command. Each
time the variable is evaluated, either in the LAMMPS input script
itself, or by another LAMMPS command that uses the variable, this will
trigger the Python function to be invoked.
</P>
<P>The Python code for the function can be included directly in the input
script or in an auxiliary file. The function can have arguments which
are mapped to LAMMPS variables (also defined in the input script) and
it can return a value to a LAMMPS variable. This is thus a mechanism
for your input script to pass information to a piece of Python code,
ask Python to execute the code, and return information to your input
script.
</P>
<P>Note that a Python function can be arbitrarily complex. It can import
other Python modules, instantiate Python classes, call other Python
functions, etc. The Python code that you provide can contain more
code than the single function. It can contain other functions or
Python classes, as well as global variables or other mechanisms for
storing state between calls from LAMMPS to the function.
</P>
<P>The Python function you provide can consist of "pure" Python code that
only performs operations provided by standard Python. However, the
Python function can also "call back" to LAMMPS through its
Python-wrapped library interface, in the manner described in the
previous section 11.1. This means it can issue LAMMPS input script
commands or query and set internal LAMMPS state. As an example, this
can be useful in an input script to create a more complex loop with
branching logic, than can be created using the simple looping and
brancing logic enabled by the <A HREF = "next_html">next</A> and <A HREF = "if.html">if</A>
commands.
</P>
<P>See the <A HREF = "python.html">python</A> doc page and the <A HREF = "variable.html">variable</A>
doc page for its python-style variables for more info, including
examples of Python code you can write for both pure Python operations
and callbacks to LAMMPS.
</P>
<P>To run pure Python code from LAMMPS, you only need to build LAMMPS
with the PYTHON package installed:
</P>
<P>make yes-python
make machine
</P>
<P>Note that this will link LAMMPS with the Python library on your
system, which typically requires several auxiliary system libraries to
also be linked. The list of these libraries and the paths to find
them are specified in the lib/python/Makefile.lammps file. You need
to insure that file contains the correct information for your version
of Python and your machine to successfully build LAMMPS. See the
lib/python/README file for more info.
</P>
<P>If you want to write Python code with callbacks to LAMMPS, then you
must also follow the steps overviewed in the preceeding section (11.1)
for running LAMMPS from Python. I.e. you must build LAMMPS as a
shared library and insure that Python can find the python/lammps.py
file and the shared library.
</P>
<HR> <HR>
<A NAME = "py_1"></A><H4>11.1 Building LAMMPS as a shared library <A NAME = "py_3"></A><H4>11.3 Building LAMMPS as a shared library
</H4> </H4>
<P>Instructions on how to build LAMMPS as a shared library are given in <P>Instructions on how to build LAMMPS as a shared library are given in
<A HREF = "Section_start.html#start_5">Section_start 5</A>. A shared library is one <A HREF = "Section_start.html#start_5">Section_start 5</A>. A shared library is one
that is dynamically loadable, which is what Python requires. On Linux that is dynamically loadable, which is what Python requires to wrap
this is a library file that ends in ".so", not ".a". LAMMPS. On Linux this is a library file that ends in ".so", not ".a".
</P> </P>
<P>From the src directory, type <P>>From the src directory, type
</P> </P>
<PRE>make foo mode=shlib <PRE>make foo mode=shlib
</PRE> </PRE>
@ -102,7 +205,7 @@ system.
</P> </P>
<HR> <HR>
<A NAME = "py_2"></A><H4>11.2 Installing the Python wrapper into Python <A NAME = "py_4"></A><H4>11.4 Installing the Python wrapper into Python
</H4> </H4>
<P>For Python to invoke LAMMPS, there are 2 files it needs to know about: <P>For Python to invoke LAMMPS, there are 2 files it needs to know about:
</P> </P>
@ -170,7 +273,7 @@ environment variable as described above.
</P> </P>
<HR> <HR>
<A NAME = "py_3"></A><H4>11.3 Extending Python with MPI to run in parallel <A NAME = "py_5"></A><H4>11.5 Extending Python with MPI to run in parallel
</H4> </H4>
<P>If you wish to run LAMMPS in parallel from Python, you need to extend <P>If you wish to run LAMMPS in parallel from Python, you need to extend
your Python with an interface to MPI. This also allows you to your Python with an interface to MPI. This also allows you to
@ -197,11 +300,12 @@ believe) creates a new alternate executable (in place of "python"
itself) as a result. itself) as a result.
</P> </P>
<P>In principle any of these Python/MPI packages should work to invoke <P>In principle any of these Python/MPI packages should work to invoke
LAMMPS in parallel and MPI calls themselves from a Python script which LAMMPS in parallel and to make MPI calls themselves from a Python
is itself running in parallel. However, when I downloaded and looked script which is itself running in parallel. However, when I
at a few of them, their documentation was incomplete and I had trouble downloaded and looked at a few of them, their documentation was
with their installation. It's not clear if some of the packages are incomplete and I had trouble with their installation. It's not clear
still being actively developed and supported. if some of the packages are still being actively developed and
supported.
</P> </P>
<P>The one I recommend, since I have successfully used it with LAMMPS, is <P>The one I recommend, since I have successfully used it with LAMMPS, is
Pypar. Pypar requires the ubiquitous <A HREF = "http://numpy.scipy.org">Numpy Pypar. Pypar requires the ubiquitous <A HREF = "http://numpy.scipy.org">Numpy
@ -261,7 +365,7 @@ the right one.
</P> </P>
<HR> <HR>
<A NAME = "py_4"></A><H4>11.4 Testing the Python-LAMMPS interface <A NAME = "py_6"></A><H4>11.6 Testing the Python-LAMMPS interface
</H4> </H4>
<P>To test if LAMMPS is callable from Python, launch Python interactively <P>To test if LAMMPS is callable from Python, launch Python interactively
and type: and type:
@ -375,22 +479,24 @@ Python on a single processor, not in parallel.
<HR> <HR>
<A NAME = "py_5"></A><H4>11.5 Using LAMMPS from Python <A NAME = "py_7"></A><H4>11.7 Using LAMMPS from Python
</H4> </H4>
<P>The Python interface to LAMMPS consists of a Python "lammps" module, <P>As described above, the Python interface to LAMMPS consists of a
the source code for which is in python/lammps.py, which creates a Python "lammps" module, the source code for which is in
"lammps" object, with a set of methods that can be invoked on that python/lammps.py, which creates a "lammps" object, with a set of
object. The sample Python code below assumes you have first imported methods that can be invoked on that object. The sample Python code
the "lammps" module in your Python script, as follows: below assumes you have first imported the "lammps" module in your
Python script, as follows:
</P> </P>
<PRE>from lammps import lammps <PRE>from lammps import lammps
</PRE> </PRE>
<P>These are the methods defined by the lammps module. If you look <P>These are the methods defined by the lammps module. If you look at
at the file src/library.cpp you will see that they correspond the files src/library.cpp and src/library.h you will see that they
one-to-one with calls you can make to the LAMMPS library from a C++ or correspond one-to-one with calls you can make to the LAMMPS library
C or Fortran program. from a C++ or C or Fortran program.
</P> </P>
<PRE>lmp = lammps() # create a LAMMPS object using the default liblammps.so library <PRE>lmp = lammps() # create a LAMMPS object using the default liblammps.so library
lmp = lammps(ptr=lmpptr) # ditto, but use lmpptr as previously created LAMMPS object
lmp = lammps("g++") # create a LAMMPS object using the liblammps_g++.so library lmp = lammps("g++") # create a LAMMPS object using the liblammps_g++.so library
lmp = lammps("",list) # ditto, with command-line args, e.g. list = ["-echo","screen"] lmp = lammps("",list) # ditto, with command-line args, e.g. list = ["-echo","screen"]
lmp = lammps("g++",list) lmp = lammps("g++",list)
@ -449,6 +555,33 @@ processors. If someone figures out how to do this with one or more of
the Python wrappers for MPI, like Pypar, please let us know and we the Python wrappers for MPI, like Pypar, please let us know and we
will amend these doc pages. will amend these doc pages.
</P> </P>
<P>The lines
</P>
<PRE>from lammps import lammps
lmp = lammps()
</PRE>
<P>create an instance of LAMMPS, wrapped in a Python class by the lammps
Python module, and return an instance of the Python class as lmp. It
is used to make all subequent calls to the LAMMPS library.
</P>
<P>Additional arguments can be used to tell Python the name of the shared
library to load or to pass arguments to the LAMMPS instance, the same
as if LAMMPS were launched from a command-line prompt.
</P>
<P>If the ptr argument is set like this:
</P>
<PRE>lmp = lammps(ptr=lmpptr)
</PRE>
<P>then lmpptr must be an argument passed to Python via the LAMMPS
<A HREF = "python.html">python</A> command, when it is used to define a Python
function that is invoked by the LAMMPS input script. This mode of
using Python with LAMMPS is described above in 11.2. The variable
lmpptr refers to the instance of LAMMPS that called the embedded
Python interpreter. Using it as an argument to lammps() allows the
returned Python class instance "lmp" to make calls to that instance of
LAMMPS. See the <A HREF = "python.html">python</A> command doc page for examples
using this syntax.
</P>
<P>Note that you can create multiple LAMMPS objects in your Python <P>Note that you can create multiple LAMMPS objects in your Python
script, and coordinate and run multiple simulations, e.g. script, and coordinate and run multiple simulations, e.g.
</P> </P>
@ -578,7 +711,7 @@ Python script. Isn't ctypes amazing?
<HR> <HR>
<A NAME = "py_6"></A><H4>11.6 Example Python scripts that use LAMMPS <A NAME = "py_8"></A><H4>11.8 Example Python scripts that use LAMMPS
</H4> </H4>
<P>These are the Python scripts included as demos in the python/examples <P>These are the Python scripts included as demos in the python/examples
directory of the LAMMPS distribution, to illustrate the kinds of directory of the LAMMPS distribution, to illustrate the kinds of

View File

@ -8,61 +8,97 @@
11. Python interface to LAMMPS :h3 11. Python interface to LAMMPS :h3
This section describes how to build and use LAMMPS via a Python LAMMPS can work together with Python in two ways. First, Python can
interface. wrap LAMMPS through the "LAMMPS library
interface"_Section_howto.html#howto_19, so that a Python script can
create one or more instances of LAMMPS and launch one or more
simulations. In Python lingo, this is "extending" Python with LAMMPS.
11.1 "Building LAMMPS as a shared library"_#py_1 Second, LAMMPS can use the Python interpreter, so that a LAMMPS input
11.2 "Installing the Python wrapper into Python"_#py_2 script can invoke Python code, and pass information back-and-forth
11.3 "Extending Python with MPI to run in parallel"_#py_3 between the input script and Python functions you write. The Python
11.4 "Testing the Python-LAMMPS interface"_#py_4 code can also callback to LAMMPS to query or change its attributes.
11.5 "Using LAMMPS from Python"_#py_5 In Python lingo, this is "embedding" Python in LAMMPS.
11.6 "Example Python scripts that use LAMMPS"_#py_6 :ul
The LAMMPS distribution includes the file python/lammps.py which wraps This section describes how to do both.
the library interface to LAMMPS. This file makes it is possible to
run LAMMPS, invoke LAMMPS commands or give it an input script, extract
LAMMPS results, an modify internal LAMMPS variables, either from a
Python script or interactively from a Python prompt. You can do the
former in serial or parallel. Running Python interactively in
parallel does not generally work, unless you have a package installed
that extends your Python to enable multiple instances of Python to
read what you type.
"Python"_http://www.python.org is a powerful scripting and programming 11.1 "Overview of running LAMMPS from Python"_#py_1
language which can be used to wrap software like LAMMPS and other 11.2 "Overview of using Python from a LAMMPS script"_#py_2
packages. It can be used to glue multiple pieces of software 11.3 "Building LAMMPS as a shared library"_#py_3
together, e.g. to run a coupled or multiscale model. See "Section 11.4 "Installing the Python wrapper into Python"_#py_4
section"_Section_howto.html#howto_10 of the manual and the couple 11.5 "Extending Python with MPI to run in parallel"_#py_5
directory of the distribution for more ideas about coupling LAMMPS to 11.6 "Testing the Python-LAMMPS interface"_#py_6
other codes. See "Section_start 4"_Section_start.html#start_5 about 11.7 "Using LAMMPS from Python"_#py_7
how to build LAMMPS as a library, and "Section_howto 11.8 "Example Python scripts that use LAMMPS"_#py_8 :ul
19"_Section_howto.html#howto_19 for a description of the library
interface provided in src/library.cpp and src/library.h and how to
extend it for your needs. As described below, that interface is what
is exposed to Python. It is designed to be easy to add functions to.
This can easily extend the Python inteface as well. See details
below.
By using the Python interface, LAMMPS can also be coupled with a GUI If you are not familiar with it, "Python"_http://www.python.org is a
or other visualization tools that display graphs or animations in real powerful scripting and programming language which can essentially do
time as LAMMPS runs. Examples of such scripts are inlcluded in the anything that faster, lower-level languages like C or C++ can do, but
python directory. typically with much fewer lines of code. When used in embedded mode,
Python can perform operations that the simplistic LAMMPS input script
syntax cannot. Python can be also be used as a "glue" language to
drive a program through its library interface, or to hook multiple
pieces of software together, such as a simulation package plus a
visualization package, or to run a coupled multiscale or multiphysics
model.
Two advantages of using Python are how concise the language is, and See "Section_howto 10"_Section_howto.html#howto_10 of the manual and
that it can be run interactively, enabling rapid development and the couple directory of the distribution for more ideas about coupling
debugging of programs. If you use it to mostly invoke costly LAMMPS to other codes. See "Section_howto
operations within LAMMPS, such as running a simulation for a 19"_Section_howto.html#howto_19 for a description of the LAMMPS
library interface provided in src/library.cpp and src/library.h, and
how to extend it for your needs. As described below, that interface
is what is exposed to Python either when calling LAMMPS from Python or
when calling Python from a LAMMPS input script and then calling back
to LAMMPS from Python code. The library interface is designed to be
easy to add functions to. Thus the Python interface to LAMMPS is also
easy to extend as well.
If you create interesting Python scripts that run LAMMPS or
interesting Python functions that can be called from a LAMMPS input
script, that you think would be useful to other users, please "email
them to the developers"_http://lammps.sandia.gov/authors.html. We can
include them in the LAMMPS distribution.
:line
:line
11.1 Overview of running LAMMPS from Python :link(py_1),h4
The LAMMPS distribution includes a python directory with all you need
to run LAMMPS from Python. The python/lammps.py file wraps the LAMMPS
library interface, with one wrapper function per LAMMPS library
function. This file makes it is possible to do the following either
from a Python script, or interactively from a Python prompt: create
one or more instances of LAMMPS, invoke LAMMPS commands or give it an
input script, run LAMMPS incrementally, extract LAMMPS results, an
modify internal LAMMPS variables. From a Python script you can do
this in serial or parallel. Running Python interactively in parallel
does not generally work, unless you have a version of Python that
extends standard Python to enable multiple instances of Python to read
what you type.
To do all of this, you must first build LAMMPS as a shared library,
then insure that your Python can find the python/lammps.py file and
the shared library. These steps are explained in subsequent sections
11.3 and 11.4. Sections 11.5 and 11.6 discuss using MPI from a
parallel Python program and how to test that you are ready to use
LAMMPS from Python. Section 11.7 lists all the functions in the
current LAMMPS library interface and how to call them from Python.
Section 11.8 gives some examples of coupling LAMMPS to other tools via
Python. For example, LAMMPS can easily be coupled to a GUI or other
visualization tools that display graphs or animations in real time as
LAMMPS runs. Examples of such scripts are inlcluded in the python
directory.
Two advantages of using Python to run LAMMPS are how concise the
language is, and that it can be run interactively, enabling rapid
development and debugging of programs. If you use it to mostly invoke
costly operations within LAMMPS, such as running a simulation for a
reasonable number of timesteps, then the overhead cost of invoking reasonable number of timesteps, then the overhead cost of invoking
LAMMPS thru Python will be negligible. LAMMPS thru Python will be negligible.
Before using LAMMPS from a Python script, you need to do two things.
You need to build LAMMPS as a dynamic shared library, so it can be
loaded by Python. And you need to tell Python how to find the library
and the Python wrapper file python/lammps.py. Both these steps are
discussed below. If you wish to run LAMMPS in parallel from Python,
you also need to extend your Python with MPI. This is also discussed
below.
The Python wrapper for LAMMPS uses the amazing and magical (to me) The Python wrapper for LAMMPS uses the amazing and magical (to me)
"ctypes" package in Python, which auto-generates the interface code "ctypes" package in Python, which auto-generates the interface code
needed between Python and a set of C interface routines for a library. needed between Python and a set of C interface routines for a library.
@ -71,16 +107,83 @@ check which version of Python you have installed, by simply typing
"python" at a shell prompt. "python" at a shell prompt.
:line :line
11.2 Overview of using Python from a LAMMPS script :link(py_2),h4
IMPORTANT NOTE: It is not currently possible to use the
"python"_python.html command described in this section with Python 3,
only with Python 2. The C API changed from Python 2 to 3 and the
LAMMPS code is not compatible with both.
LAMMPS has a "python"_python.html command which can be used in an
input script to define and execute a Python function that you write
the code for. The Python function can also be assigned to a LAMMPS
python-style variable via the "variable"_variable.html command. Each
time the variable is evaluated, either in the LAMMPS input script
itself, or by another LAMMPS command that uses the variable, this will
trigger the Python function to be invoked.
The Python code for the function can be included directly in the input
script or in an auxiliary file. The function can have arguments which
are mapped to LAMMPS variables (also defined in the input script) and
it can return a value to a LAMMPS variable. This is thus a mechanism
for your input script to pass information to a piece of Python code,
ask Python to execute the code, and return information to your input
script.
Note that a Python function can be arbitrarily complex. It can import
other Python modules, instantiate Python classes, call other Python
functions, etc. The Python code that you provide can contain more
code than the single function. It can contain other functions or
Python classes, as well as global variables or other mechanisms for
storing state between calls from LAMMPS to the function.
The Python function you provide can consist of "pure" Python code that
only performs operations provided by standard Python. However, the
Python function can also "call back" to LAMMPS through its
Python-wrapped library interface, in the manner described in the
previous section 11.1. This means it can issue LAMMPS input script
commands or query and set internal LAMMPS state. As an example, this
can be useful in an input script to create a more complex loop with
branching logic, than can be created using the simple looping and
brancing logic enabled by the "next"_next_html and "if"_if.html
commands.
See the "python"_python.html doc page and the "variable"_variable.html
doc page for its python-style variables for more info, including
examples of Python code you can write for both pure Python operations
and callbacks to LAMMPS.
To run pure Python code from LAMMPS, you only need to build LAMMPS
with the PYTHON package installed:
make yes-python
make machine
Note that this will link LAMMPS with the Python library on your
system, which typically requires several auxiliary system libraries to
also be linked. The list of these libraries and the paths to find
them are specified in the lib/python/Makefile.lammps file. You need
to insure that file contains the correct information for your version
of Python and your machine to successfully build LAMMPS. See the
lib/python/README file for more info.
If you want to write Python code with callbacks to LAMMPS, then you
must also follow the steps overviewed in the preceeding section (11.1)
for running LAMMPS from Python. I.e. you must build LAMMPS as a
shared library and insure that Python can find the python/lammps.py
file and the shared library.
:line :line
11.1 Building LAMMPS as a shared library :link(py_1),h4 11.3 Building LAMMPS as a shared library :link(py_3),h4
Instructions on how to build LAMMPS as a shared library are given in Instructions on how to build LAMMPS as a shared library are given in
"Section_start 5"_Section_start.html#start_5. A shared library is one "Section_start 5"_Section_start.html#start_5. A shared library is one
that is dynamically loadable, which is what Python requires. On Linux that is dynamically loadable, which is what Python requires to wrap
this is a library file that ends in ".so", not ".a". LAMMPS. On Linux this is a library file that ends in ".so", not ".a".
From the src directory, type >From the src directory, type
make foo mode=shlib :pre make foo mode=shlib :pre
@ -98,7 +201,7 @@ system.
:line :line
11.2 Installing the Python wrapper into Python :link(py_2),h4 11.4 Installing the Python wrapper into Python :link(py_4),h4
For Python to invoke LAMMPS, there are 2 files it needs to know about: For Python to invoke LAMMPS, there are 2 files it needs to know about:
@ -166,7 +269,7 @@ environment variable as described above.
:line :line
11.3 Extending Python with MPI to run in parallel :link(py_3),h4 11.5 Extending Python with MPI to run in parallel :link(py_5),h4
If you wish to run LAMMPS in parallel from Python, you need to extend If you wish to run LAMMPS in parallel from Python, you need to extend
your Python with an interface to MPI. This also allows you to your Python with an interface to MPI. This also allows you to
@ -193,11 +296,12 @@ believe) creates a new alternate executable (in place of "python"
itself) as a result. itself) as a result.
In principle any of these Python/MPI packages should work to invoke In principle any of these Python/MPI packages should work to invoke
LAMMPS in parallel and MPI calls themselves from a Python script which LAMMPS in parallel and to make MPI calls themselves from a Python
is itself running in parallel. However, when I downloaded and looked script which is itself running in parallel. However, when I
at a few of them, their documentation was incomplete and I had trouble downloaded and looked at a few of them, their documentation was
with their installation. It's not clear if some of the packages are incomplete and I had trouble with their installation. It's not clear
still being actively developed and supported. if some of the packages are still being actively developed and
supported.
The one I recommend, since I have successfully used it with LAMMPS, is The one I recommend, since I have successfully used it with LAMMPS, is
Pypar. Pypar requires the ubiquitous "Numpy Pypar. Pypar requires the ubiquitous "Numpy
@ -257,7 +361,7 @@ the right one.
:line :line
11.4 Testing the Python-LAMMPS interface :link(py_4),h4 11.6 Testing the Python-LAMMPS interface :link(py_6),h4
To test if LAMMPS is callable from Python, launch Python interactively To test if LAMMPS is callable from Python, launch Python interactively
and type: and type:
@ -370,22 +474,24 @@ Python on a single processor, not in parallel.
:line :line
:line :line
11.5 Using LAMMPS from Python :link(py_5),h4 11.7 Using LAMMPS from Python :link(py_7),h4
The Python interface to LAMMPS consists of a Python "lammps" module, As described above, the Python interface to LAMMPS consists of a
the source code for which is in python/lammps.py, which creates a Python "lammps" module, the source code for which is in
"lammps" object, with a set of methods that can be invoked on that python/lammps.py, which creates a "lammps" object, with a set of
object. The sample Python code below assumes you have first imported methods that can be invoked on that object. The sample Python code
the "lammps" module in your Python script, as follows: below assumes you have first imported the "lammps" module in your
Python script, as follows:
from lammps import lammps :pre from lammps import lammps :pre
These are the methods defined by the lammps module. If you look These are the methods defined by the lammps module. If you look at
at the file src/library.cpp you will see that they correspond the files src/library.cpp and src/library.h you will see that they
one-to-one with calls you can make to the LAMMPS library from a C++ or correspond one-to-one with calls you can make to the LAMMPS library
C or Fortran program. from a C++ or C or Fortran program.
lmp = lammps() # create a LAMMPS object using the default liblammps.so library lmp = lammps() # create a LAMMPS object using the default liblammps.so library
lmp = lammps(ptr=lmpptr) # ditto, but use lmpptr as previously created LAMMPS object
lmp = lammps("g++") # create a LAMMPS object using the liblammps_g++.so library lmp = lammps("g++") # create a LAMMPS object using the liblammps_g++.so library
lmp = lammps("",list) # ditto, with command-line args, e.g. list = \["-echo","screen"\] lmp = lammps("",list) # ditto, with command-line args, e.g. list = \["-echo","screen"\]
lmp = lammps("g++",list) :pre lmp = lammps("g++",list) :pre
@ -444,6 +550,33 @@ processors. If someone figures out how to do this with one or more of
the Python wrappers for MPI, like Pypar, please let us know and we the Python wrappers for MPI, like Pypar, please let us know and we
will amend these doc pages. will amend these doc pages.
The lines
from lammps import lammps
lmp = lammps() :pre
create an instance of LAMMPS, wrapped in a Python class by the lammps
Python module, and return an instance of the Python class as lmp. It
is used to make all subequent calls to the LAMMPS library.
Additional arguments can be used to tell Python the name of the shared
library to load or to pass arguments to the LAMMPS instance, the same
as if LAMMPS were launched from a command-line prompt.
If the ptr argument is set like this:
lmp = lammps(ptr=lmpptr) :pre
then lmpptr must be an argument passed to Python via the LAMMPS
"python"_python.html command, when it is used to define a Python
function that is invoked by the LAMMPS input script. This mode of
using Python with LAMMPS is described above in 11.2. The variable
lmpptr refers to the instance of LAMMPS that called the embedded
Python interpreter. Using it as an argument to lammps() allows the
returned Python class instance "lmp" to make calls to that instance of
LAMMPS. See the "python"_python.html command doc page for examples
using this syntax.
Note that you can create multiple LAMMPS objects in your Python Note that you can create multiple LAMMPS objects in your Python
script, and coordinate and run multiple simulations, e.g. script, and coordinate and run multiple simulations, e.g.
@ -572,7 +705,7 @@ Python script. Isn't ctypes amazing? :l,ule
:line :line
:line :line
11.6 Example Python scripts that use LAMMPS :link(py_6),h4 11.8 Example Python scripts that use LAMMPS :link(py_8),h4
These are the Python scripts included as demos in the python/examples These are the Python scripts included as demos in the python/examples
directory of the LAMMPS distribution, to illustrate the kinds of directory of the LAMMPS distribution, to illustrate the kinds of

View File

@ -171,7 +171,7 @@ all good starting points if you find you need to change them for your
machine. Put any file you edit into the src/MAKE/MINE directory and machine. Put any file you edit into the src/MAKE/MINE directory and
it will be never be touched by any LAMMPS updates. it will be never be touched by any LAMMPS updates.
</P> </P>
<P>From within the src directory, type "make" or "gmake". You should see <P>>From within the src directory, type "make" or "gmake". You should see
a list of available choices from src/MAKE and all of its a list of available choices from src/MAKE and all of its
sub-directories. If one of those has the options you want or is the sub-directories. If one of those has the options you want or is the
machine you want, you can type a command like: machine you want, you can type a command like:
@ -772,20 +772,30 @@ options.
<A NAME = "start_3_3"></A><B><I>Packages that require extra libraries:</I></B> <A NAME = "start_3_3"></A><B><I>Packages that require extra libraries:</I></B>
<P>A few of the standard and user packages require additional auxiliary <P>A few of the standard and user packages require additional auxiliary
libraries. They must be compiled first, before LAMMPS is built. If libraries. Most of them are provided with LAMMPS, in which case they
you get a LAMMPS build error about a missing library, this is likely must be compiled first, before LAMMPS is built if you wish to include
the reason. See the <A HREF = "Section_packages.html">Section_packages</A> doc page that package. If you get a LAMMPS build error about a missing
for a list of packages that have auxiliary libraries. library, this is likely the reason. See the
<A HREF = "Section_packages.html">Section_packages</A> doc page for a list of
packages that have these kinds of auxiliary libraries.
</P> </P>
<P>The lib directory in the distribution has sub-directories with package <P>The lib directory in the distribution has sub-directories with package
names that correspond to the needed auxiliary libs, e.g. lib/reax. names that correspond to the needed auxiliary libs, e.g. lib/reax.
Each sub-directory has a README file that gives more details. Code Each sub-directory has a README file that gives more details. Code
for most of the auxiliary libraries is included in that directory. for most of the auxiliary libraries is included in that directory.
Examples are the USER-ATC and MEAM packages. A few of the Examples are the USER-ATC and MEAM packages.
sub-directories do not include code, but do include instructions and </P>
sometimes scripts that automate the process of downloading the <P>A few of the lib sub-directories do not include code, but do include
auxiliary library and installing it so LAMMPS can link to it. instructions and sometimes scripts that automate the process of
Examples are the KIM and VORONOI and USER-MOLFILE packages. downloading the auxiliary library and installing it so LAMMPS can link
to it. Examples are the KIM and VORONOI and USER-MOLFILE packages.
</P>
<P>The lib/python directory (for the PYTHON package) contains only a
choice of Makefile.lammps.* files. This is because no auxiliary code
or libraries are needed, only the Python library and other system libs
that already available on your system. However, the Makefile.lammps
file is needed to tell the LAMMPS build which libs to use and where to
find them.
</P> </P>
<P>For libraries with provided code, the sub-directory README file <P>For libraries with provided code, the sub-directory README file
(e.g. lib/reax/README) has instructions on how to build that library. (e.g. lib/reax/README) has instructions on how to build that library.

View File

@ -165,7 +165,7 @@ all good starting points if you find you need to change them for your
machine. Put any file you edit into the src/MAKE/MINE directory and machine. Put any file you edit into the src/MAKE/MINE directory and
it will be never be touched by any LAMMPS updates. it will be never be touched by any LAMMPS updates.
From within the src directory, type "make" or "gmake". You should see >From within the src directory, type "make" or "gmake". You should see
a list of available choices from src/MAKE and all of its a list of available choices from src/MAKE and all of its
sub-directories. If one of those has the options you want or is the sub-directories. If one of those has the options you want or is the
machine you want, you can type a command like: machine you want, you can type a command like:
@ -766,20 +766,30 @@ options.
[{Packages that require extra libraries:}] :link(start_3_3) [{Packages that require extra libraries:}] :link(start_3_3)
A few of the standard and user packages require additional auxiliary A few of the standard and user packages require additional auxiliary
libraries. They must be compiled first, before LAMMPS is built. If libraries. Most of them are provided with LAMMPS, in which case they
you get a LAMMPS build error about a missing library, this is likely must be compiled first, before LAMMPS is built if you wish to include
the reason. See the "Section_packages"_Section_packages.html doc page that package. If you get a LAMMPS build error about a missing
for a list of packages that have auxiliary libraries. library, this is likely the reason. See the
"Section_packages"_Section_packages.html doc page for a list of
packages that have these kinds of auxiliary libraries.
The lib directory in the distribution has sub-directories with package The lib directory in the distribution has sub-directories with package
names that correspond to the needed auxiliary libs, e.g. lib/reax. names that correspond to the needed auxiliary libs, e.g. lib/reax.
Each sub-directory has a README file that gives more details. Code Each sub-directory has a README file that gives more details. Code
for most of the auxiliary libraries is included in that directory. for most of the auxiliary libraries is included in that directory.
Examples are the USER-ATC and MEAM packages. A few of the Examples are the USER-ATC and MEAM packages.
sub-directories do not include code, but do include instructions and
sometimes scripts that automate the process of downloading the A few of the lib sub-directories do not include code, but do include
auxiliary library and installing it so LAMMPS can link to it. instructions and sometimes scripts that automate the process of
Examples are the KIM and VORONOI and USER-MOLFILE packages. downloading the auxiliary library and installing it so LAMMPS can link
to it. Examples are the KIM and VORONOI and USER-MOLFILE packages.
The lib/python directory (for the PYTHON package) contains only a
choice of Makefile.lammps.* files. This is because no auxiliary code
or libraries are needed, only the Python library and other system libs
that already available on your system. However, the Makefile.lammps
file is needed to tell the LAMMPS build which libs to use and where to
find them.
For libraries with provided code, the sub-directory README file For libraries with provided code, the sub-directory README file
(e.g. lib/reax/README) has instructions on how to build that library. (e.g. lib/reax/README) has instructions on how to build that library.

View File

@ -13,8 +13,8 @@
</H3> </H3>
<P><B>Syntax:</B> <P><B>Syntax:</B>
</P> </P>
<P>print string keyword value:pre <PRE>print string keyword value
</P> </PRE>
<UL><LI>string = text string to print, which may contain variables <UL><LI>string = text string to print, which may contain variables
<LI>zero or more keyword/value pairs may be appended <LI>zero or more keyword/value pairs may be appended
@ -32,14 +32,20 @@
<PRE>print "Done with equilibration" file info.dat <PRE>print "Done with equilibration" file info.dat
print Vol=$v append info.dat screen no print Vol=$v append info.dat screen no
print "The system volume is now $v" print "The system volume is now $v"
print 'The system volume is now $v' print 'The system volume is now $v'
print """
System volume = $v
System temperature = $t
"""
</PRE> </PRE>
<P><B>Description:</B> <P><B>Description:</B>
</P> </P>
<P>Print a text string to the screen and logfile. One line of output is <P>Print a text string to the screen and logfile. The text string must
generated. The text string must be a single argument, so it should be be a single argument, so if it is one line but more than one word, it
enclosed in double quotes if it is more than one word. If it contains should be enclosed in single or double quotes. To generate multiple
variables, they will be evaluated and their current values printed. lines of output, the string can be enclosed in triple quotes, as in
the last example above. If the text string contains variables, they
will be evaluated and their current values printed.
</P> </P>
<P>If the <I>file</I> or <I>append</I> keyword is used, a filename is specified to <P>If the <I>file</I> or <I>append</I> keyword is used, a filename is specified to
which the output will be written. If <I>file</I> is used, then the which the output will be written. If <I>file</I> is used, then the

View File

@ -10,7 +10,7 @@ print command :h3
[Syntax:] [Syntax:]
print string keyword value:pre print string keyword value :pre
string = text string to print, which may contain variables :ulb,l string = text string to print, which may contain variables :ulb,l
zero or more keyword/value pairs may be appended :l zero or more keyword/value pairs may be appended :l
@ -25,14 +25,20 @@ keyword = {file} or {append} or {screen} :l
print "Done with equilibration" file info.dat print "Done with equilibration" file info.dat
print Vol=$v append info.dat screen no print Vol=$v append info.dat screen no
print "The system volume is now $v" print "The system volume is now $v"
print 'The system volume is now $v' :pre print 'The system volume is now $v'
print """
System volume = $v
System temperature = $t
""" :pre
[Description:] [Description:]
Print a text string to the screen and logfile. One line of output is Print a text string to the screen and logfile. The text string must
generated. The text string must be a single argument, so it should be be a single argument, so if it is one line but more than one word, it
enclosed in double quotes if it is more than one word. If it contains should be enclosed in single or double quotes. To generate multiple
variables, they will be evaluated and their current values printed. lines of output, the string can be enclosed in triple quotes, as in
the last example above. If the text string contains variables, they
will be evaluated and their current values printed.
If the {file} or {append} keyword is used, a filename is specified to If the {file} or {append} keyword is used, a filename is specified to
which the output will be written. If {file} is used, then the which the output will be written. If {file} is used, then the
@ -69,4 +75,3 @@ thermodynamic properties, global values calculated by a
[Default:] [Default:]
The option defaults are no file output and screen = yes. The option defaults are no file output and screen = yes.

490
doc/python.html Normal file
View File

@ -0,0 +1,490 @@
<HTML>
<CENTER><A HREF = "http://lammps.sandia.gov">LAMMPS WWW Site</A> - <A HREF = "Manual.html">LAMMPS Documentation</A> - <A HREF = "Section_commands.html#comm">LAMMPS Commands</A>
</CENTER>
<HR>
<H3>python command
</H3>
<P><B>Syntax:</B>
</P>
<PRE>python func keyword args ...
</PRE>
<UL><LI>func = name of Python function
<LI>one or more keyword/args pairs must be appended
<PRE>keyword = <I>invoke</I> or <I>input</I> or <I>return</I> or <I>format</I> or <I>file</I> or <I>here</I> or <I>exists</I>
<I>invoke</I> arg = none = invoke the previously defined Python function
<I>input</I> args = N i1 i2 ... iN
N = # of inputs to function
i1,...,iN = value, SELF, or LAMMPS variable name
value = integer number, floating point number, or string
SELF = reference to LAMMPS itself which can be accessed by Python function
variable = v_name, where name = name of LAMMPS variable, e.g. v_abc
<I>return</I> arg = varReturn
varReturn = v_name = LAMMPS variable name which return value of function will be assigned to
<I>format</I> arg = fstring with M characters
M = N if no return value, where N = # of inputs
M = N+1 if there is a return value
fstring = each character (i,f,s,p) corresponds in order to an input or return value
'i' = integer, 'f' = floating point, 's' = string, 'p' = SELF
<I>file</I> arg = filename
filename = file of Python code, which defines func
<I>here</I> arg = inline
inline = one or more lines of Python code which defines func
must be a single argument, typically enclosed between triple quotes
<I>exists</I> arg = none = Python code has been loaded by previous python command
</PRE>
</UL>
<P><B>Examples:</B>
</P>
<PRE>python pForce input 2 v_x 20.0 return v_f format fff file force.py
python pForce invoke
</PRE>
<PRE>python factorial input 1 myN return v_fac format ii here """
def factorial(n):
if n == 1: return n
return n * factorial(n-1)
"""
</PRE>
<PRE>python loop input 1 SELF return v_value format -f here """
def loop(lmpptr,N,cut0):
from lammps import lammps
lmp = lammps(ptr=lmpptr)
</PRE>
<PRE> # loop N times, increasing cutoff each time
</PRE>
<PRE> for i in range(N):
cut = cut0 + i*0.1
lmp.set_variable("cut",cut) # set a variable in LAMMPS
lmp.command("pair_style lj/cut $<I>cut</I>") # LAMMPS commands
lmp.command("pair_coeff * * 1.0 1.0")
lmp.command("run 100")
"""
</PRE>
<P><B>Description:</B>
</P>
<P>IMPORTANT NOTE: It is not currently possible to use the
<A HREF = "python.html">python</A> command described in this section with Python 3,
only with Python 2. The C API changed from Python 2 to 3 and the
LAMMPS code is not compatible with both.
</P>
<P>Define a Python function or execute a previously defined function.
Arguments, including LAMMPS variables, can be passed to the function
from the LAMMPS input script and a value returned by the Python
function to a LAMMPS variable. The Python code for the function can
be included directly in the input script or in a separate Python file.
The function can be standard Python code or it can make "callbacks" to
LAMMPS through its library interface to query or set internal values
within LAMMPS. This is a powerful mechanism for performing complex
operations in a LAMMPS input script that are not possible with the
simple input script and variable syntax which LAMMPS defines. Thus
your input script can operate more like a true programming language.
</P>
<P>Use of this command requires building LAMMPS with the PYTHON package
which links to the Python library so that the Python interpreter is
embedded in LAMMPS. More details about this process are given below.
</P>
<P>There are two ways to invoke a Python function once it has been
defined. One is using the <I>invoke</I> keyword. The other is to assign
the function to a <A HREF = "variable.html">python-style variable</A> defined in
your input script. Whenever the variable is evaluated, it will
execute the Python function to assign a value to the variable. Note
that variables can be evaluated in many different ways within LAMMPS.
They can be substituted for directly in an input script. Or they can
be passed to various commands as arguments, so that the variable is
evaluated during a simulation run.
</P>
<P>A broader overview of how Python can be used with LAMMPS is
given in <A HREF = "Section_python.html">Section python</A>. There is an
examples/python directory which illustrates use of the python
command.
</P>
<HR>
<P>The <I>func</I> setting specifies the name of the Python function. The
code for the function is defined using the <I>file</I> or <I>here</I> keywords
as explained below.
</P>
<P>If the <I>invoke</I> keyword is used, no other keywords can be used, and a
previous python command must have defined the Python function
referenced by this command. This invokes the Python function with the
previously defined arguments and return value processed as explained
below. You can invoke the function as many times as you wish in your
input script.
</P>
<P>The <I>input</I> keyword defines how many arguments <I>N</I> the Python function
expects. If it takes no arguments, then the <I>input</I> keyword should
not be used. Each argument can be specified directly as a value,
e.g. 6 or 3.14159 or abc (a string of characters). The type of each
argument is specified by the <I>format</I> keyword as explained below, so
that Python will know how to interpret the value. If the word SELF is
used for an argument it has a special meaning. A pointer is passed to
the Python function which it converts into a reference to LAMMPS
itself. This enables the function to call back to LAMMPS through its
library interface as explained below. This allows the Python function
to query or set values internal to LAMMPS which can affect the
subsequent execution of the input script. A LAMMPS variable can also
be used as an argument, specified as v_name, where "name" is the name
of the variable. Any style of LAMMPS variable can be used, as defined
by the <A HREF = "variable.html">variable</A> command. Each time the Python
function is invoked, the LAMMPS variable is evaluated and its value is
passed to the Python function.
</P>
<P>The <I>return</I> keyword is only needed if the Python function returns a
value. The specified <I>varReturn</I> must be of the form v_name, where
"name" is the name of a python-style LAMMPS variable, defined by the
<A HREF = "variable.html">variable</A> command. The Python function can return a
numeric or string value, as specified by the <I>format</I> keyword.
</P>
<P>As explained on the <A HREF = "variable.html">variable</A> doc page, the definition
of a python-style variable associates a Python function name with the
variable. This must match the <I>func</I> setting for this command. For
exampe these two commands would be self-consistent:
</P>
<PRE>variable foo python myMultiply
python myMultiply return v_foo format f file funcs.py
</PRE>
<P>The two commands can appear in either order in the input script so
long as both are specified before the Python function is invoked for
the first time.
</P>
<P>The <I>format</I> keyword must be used if the <I>input</I> or <I>return</I> keyword
is used. It defines an <I>fstring</I> with M characters, where M = sum of
number of inputs and outputs. The order of characters corresponds to
the N inputs, followed by the return value (if it exists). Each
character must be one of the following: "i" for integer, "f" for
floating point, "s" for string, or "p" for SELF. Each character
defines the type of the corresponding input or output value of the
Python function and affects the type conversion that is performed
internally as data is passed back and forth between LAMMPS and Python.
Note that it is permissible to use a <A HREF = "variable.html">python-style
variable</A> in a LAMMPS command that allows for an
equal-style variable as an argument, but only if the output of the
Python function is flagged as a numeric value ("i" or "f") via the
<I>format</I> keyword.
</P>
<P>Either the <I>file</I>, <I>here</I>, or <I>exists</I> keyword must be used, but only
one of them. These keywords specify what Python code to load into the
Python interpreter. The <I>file</I> keyword gives the name of a file,
which should end with a ".py" suffix, which contains Python code. The
code will be immediately loaded into and run in the "main" module of
the Python interpreter. Note that Python code which contains a
function definition does not "execute" the function when it is run; it
simply defines the function so that it can be invoked later.
</P>
<P>The <I>here</I> keyword does the same thing, except that the Python code
follows as a single argument to the <I>here</I> keyword. This can be done
using triple quotes as delimiters, as in the examples above. This
allows Python code to be listed verbatim in your input script, with
proper indentation, blank lines, and comments, as desired. See
<A HREF = "Section_commands.html#cmd_2">Section 3.2</A>, for an explanation of how
triple quotes can be used as part of input script syntax.
</P>
<P>The <I>exists</I> keyword takes no argument. It means that Python code
containing the required Python function defined by the <I>func</I> setting,
is assumed to have been previously loaded by another python command.
</P>
<P>Note that the Python code that is loaded and run must contain a
function with the specified <I>func</I> name. To operate properly when
later invoked, the the function code must match the <I>input</I> and
<I>return</I> and <I>format</I> keywords specified by the python command.
Otherwise Python will generate an error.
</P>
<HR>
<P>This section describes how Python code can be written to work with
LAMMPS.
</P>
<P>Whether you load Python code from a file or directly from your input
script, via the <I>file</I> and <I>here</I> keywords, the code can be identical.
It must be indented properly as Python requires. It can contain
comments or blank lines. If the code is in your input script, it
cannot however contain triple-quoted Python strings, since that will
conflict with the triple-quote parsing that the LAMMPS input script
performs.
</P>
<P>All the Python code you specify via one or more python commands is
loaded into the Python "main" module, i.e. __main__. The code can
define global variables or statements that are outside of function
definitions. It can contain multiple functions, only one of which
matches the <I>func</I> setting in the python command. This means you can
use the <I>file</I> keyword once to load several functions, and the
<I>exists</I> keyword thereafter in subsequent python commands to access
the other functions previously loaded.
</P>
<P>A Python function you define (or more generally, the code you load)
can import other Python modules or classes, it can make calls to other
system functions or functions you define, and it can access or modify
global variables (in the "main" module) which will persist between
successive function calls. The latter can be useful, for example, to
prevent a function from being invoke multiple times per timestep by
different commands in a LAMMPS input script that access the returned
python-style variable associated with the function. For example,
consider this function loaded with two global variables defined
outside the function:
</P>
<PRE>nsteplast = -1
nvaluelast = 0
</PRE>
<PRE>def expensive(nstep):
global nsteplast,nvaluelast
if nstep == nsteplast: return nvaluelast
nsteplast = nstep
# perform complicated calculation
nvalue = ...
nvaluelast = nvalue
return nvalue
</PRE>
<P>Nsteplast stores the previous timestep the function was invoked
(passed as an argument to the function). Nvaluelast stores the return
value computed on the last function invocation. If the function is
invoked again on the same timestep, the previous value is simply
returned, without re-computing it. The "global" statement inside the
Python function allows it to overwrite the global variables.
</P>
<P>Note that if you load Python code multiple times (via multiple python
commands), you can overwrite previously loaded variables and functions
if you are not careful. E.g. if the code above were loaded twice, the
global variables would be re-initialized, which might not be what you
want. Likewise, if a function with the same name exists in two chunks
of Python code you load, the function loaded second will override the
function loaded first.
</P>
<P>It's important to realize that if you are running LAMMPS in parallel,
each MPI task will load the Python interpreter and execute a local
copy of the Python function(s) you define. There is no connection
between the Python interpreters running on different processors.
This implies three important things.
</P>
<P>First, if you put a print statement in your Python function, you will
see P copies of the output, when running on P processors. If the
prints occur at (nearly) the same time, the P copies of the output may
be mixed together. Welcome to the world of parallel programming and
debugging.
</P>
<P>Second, if your Python code loads modules that are not pre-loaded by
the Python library, then it will load the module from disk. This may
be a bottleneck if 1000s of processors try to load a module at the
same time. On some large supercomputers, loading of modules from disk
by Python may be disabled. In this case you would need to pre-build a
Python library that has the required modules pre-loaded and link
LAMMPS with that library.
</P>
<P>Third, if your Python code calls back to LAMMPS (discussed in the
next section) and causes LAMMPS to perform an MPI operation requires
global communication (e.g. via MPI_Allreduce), such as computing the
global temperature of the system, then you must insure all your Python
functions (running independently on different processors) call back to
LAMMPS. Otherwise the code may hang.
</P>
<HR>
<P>Your Python function can "call back" to LAMMPS through its
library interface, if you use the SELF input to pass Python
a pointer to LAMMPS. The mechanism for doing this in your
Python function is as follows:
</P>
<PRE>def foo(lmpptr,...):
from lammps import lammps
lmp = lammps(ptr=lmpptr)
lmp.command('print "Hello from inside Python"')
...
</PRE>
<P>The function definition must include a variable (lmpptr in this case)
which corresponds to SELF in the python command. The first line of
the function imports the Python module lammps.py in the python dir of
the distribution. The second line creates a Python object "lmp" which
wraps the instance of LAMMPS that called the function. The
"ptr=lmpptr" argument is what makes that happen. The thrid line
invokes the command() function in the LAMMPS library interface. It
takes a single string argument which is a LAMMPS input script command
for LAMMPS to execute, the same as if it appeared in your input
script. In this case, LAMMPS should output
</P>
<PRE>Hello from inside Python
</PRE>
<P>to the screen and log file. Note that since the LAMMPS print command
itself takes a string in quotes as its argument, the Python string
must be delimited with a different style of quotes.
</P>
<P><A HREF = "Section_python.html#py_7">Section 11.7</A> describes the syntax for how
Python wraps the various functions included in the LAMMPS library
interface.
</P>
<P>A more interesting example is in the examples/python/in.python script
which loads and runs the following function from examples/python/funcs.py:
</P>
<PRE>def loop(N,cut0,thresh,lmpptr):
print "LOOP ARGS",N,cut0,thresh,lmpptr
from lammps import lammps
lmp = lammps(ptr=lmpptr)
natoms = lmp.get_natoms()
</PRE>
<PRE> for i in range(N):
cut = cut0 + i*0.1
</PRE>
<PRE> lmp.set_variable("cut",cut) # set a variable in LAMMPS
lmp.command("pair_style lj/cut $<I>cut</I>") # LAMMPS command
#lmp.command("pair_style lj/cut %d" % cut) # LAMMPS command option
</PRE>
<PRE> lmp.command("pair_coeff * * 1.0 1.0") # ditto
lmp.command("run 10") # ditto
pe = lmp.extract_compute("thermo_pe",0,0) # extract total PE from LAMMPS
print "PE",pe/natoms,thresh
if pe/natoms < thresh: return
</PRE>
<P>with these input script commands:
</P>
<PRE>python loop input 4 10 1.0 -4.0 SELF format iffp file funcs.py
python loop invoke
</PRE>
<P>This has the effect of looping over a series of 10 short runs (10
timesteps each) where the pair style cutoff is increased from a value
of 1.0 in distance units, in increments of 0.1. The looping stops
when the per-atom potential energy falls below a threshhold of -4.0 in
energy units. More generally, Python can be used to implement a loop
with complex logic, much more so than can be created using the LAMMPS
<A HREF = "jump.html">jump</A> and <A HREF = "if.html">if</A> commands.
</P>
<P>Several LAMMPS library functions are called from the loop function.
Get_natoms() returns the number of atoms in the simulation, so that it
can be used to normalize the potential energy that is returned by
extract_compute() for the "thermo_pe" compute that is defined by
default for LAMMPS thermodynamic output. Set_variable() sets the
value of a string variable defined in LAMMPS. This library function
is a useful way for a Python function to return multiple values to
LAMMPS, more than the single value that can be passed back via a
return statement. This cutoff value in the "cut" variable is then
substituted (by LAMMPS) in the pair_style command that is executed
next. Alternatively, the "LAMMPS command option" line could be used
in place of the 2 preceeding lines, to have Python insert the value
into the LAMMPS command string.
</P>
<P>IMPORTANT NOTE: When using the callback mechanism just described,
recognize that there are some operations you should not attempt
because LAMMPS cannot execute them correctly. If the Python function
is invoked between runs in the LAMMPS input script, then it should be
OK to invoke any LAMMPS input script command via the library interface
command() or file() functions, so long as the command would work if it
were executed in the LAMMPS input script directly at the same point.
</P>
<P>However, a Python function can also be invoked during a run, whenever
an associated LAMMPS variable it is assigned to is evaluted. If the
variable is an input argument to another LAMMPS command (e.g. <A HREF = "fix_setforce.html">fix
setforce</A>), then the Python function will be invoked
inside the class for that command, in one of its methods that is
invoked in the middle of a timestep. You cannot execute arbitrary
input script commands from the Python function (again, via the
command() or file() functions) at that point in the run and expect it
to work. Other library functions such as those that invoke computes
or other variables may have hidden side effects as well. In these
cases, LAMMPS has no simple way to check that something illogical is
being attempted.
</P>
<HR>
<P>If you run Python code directly on your workstation, either
interactively or by using Python to launch a Python script stored in a
file, and your code has an error, you will typically see informative
error messages. That is not the case when you run Python code from
LAMMPS using an embedded Python interpreter. The code will typically
fail silently. LAMMPS will catch some errors but cannot tell you
where in the Python code the problem occurred. For example, if the
Python code cannot be loaded and run because it has syntax or other
logic errors, you may get an error from Python pointing to the
offending line, or you may get one of these generic errors from
LAMMPS:
</P>
<PRE>Could not process Python file
Could not process Python string
</PRE>
<P>When the Python function is invoked, if it does not return properly,
you will typically get this generic error from LAMMPS:
</P>
<PRE>Python function evaluation failed
</PRE>
<P>Here are three suggestions for debugging your Python code while
running it under LAMMPS.
</P>
<P>First, don't run it under LAMMPS, at least to start with! Debug it
using plain Python. Load and invoke your function, pass it arguments,
check return values, etc.
</P>
<P>Second, add Python print statements to the function to check how far
it gets and intermediate values it calculates. See the discussion
above about printing from Python when running in parallel.
</P>
<P>Third, use Python exception handling. For example, say this statement
in your Python function is failing, because you have not initialized the
variable foo:
</P>
<PRE>foo += 1
</PRE>
<P>If you put one (or more) statements inside a "try" statement,
like this:
</P>
<PRE>import exceptions
print "Inside simple function"
try:
foo += 1 # one or more statements here
except Exception, e:
print "FOO error:",e
</PRE>
<P>then you will get this message printed to the screen:
</P>
<PRE>FOO error: local variable 'foo' referenced before assignment
</PRE>
<P>If there is no error in the try statements, then nothing is printed.
Either way the function continues on (unless you put a return or
sys.exit() in the except clause).
</P>
<HR>
<P><B>Restrictions:</B>
</P>
<P>This command is part of the PYTHON package. It is only enabled if
LAMMPS was built with that package. See the <A HREF = "Section_start.html#start_3">Making
LAMMPS</A> section for more info.
</P>
<P>Building LAMMPS with the PYTHON package will link LAMMPS with the
Python library on your system. Settings to enable this are in the
lib/python/Makefile.lammps file. See the lib/python/README file for
information on those settings.
</P>
<P>If you use Python code which calls back to LAMMPS, via the SELF input
argument explained above, there is an extra step required when
building LAMMPS. LAMMPS must also be built as a shared library and
your Python function must be able to to load the Python module in
python/lammps.py that wraps the LAMMPS library interface. These are
the same steps required to use Python by itself to wrap LAMMPS.
Details on these steps are explained in <A HREF = "Section.python.html">Section
python</A>. Note that it is important that the
stand-alone LAMMPS executable and the LAMMPS shared library be
consistent (built from the same source code files) in order for this
to work. If the two have been built at different times using
different source files, problems may occur.
</P>
<P>As described above, you can use the python command to invoke a Python
function which calls back to LAMMPS through its Python-wrapped library
interface. However you cannot do the opposite. I.e. you cannot call
LAMMPS from Python and invoke the python command to "callback" to
Python and execute a Python function. LAMMPS will generate an error
if you try to do that. Note that we think there actually should be a
way to do that, but haven't yet been able to figure out how to do it
successfully.
</P>
<P><B>Related commands:</B>
</P>
<P><A HREF = "shell.html">shell</A>, <A HREF = "variable.html">variable</A>
</P>
<P><B>Default:</B> none
</P>
</HTML>

482
doc/python.txt Normal file
View File

@ -0,0 +1,482 @@
"LAMMPS WWW Site"_lws - "LAMMPS Documentation"_ld - "LAMMPS Commands"_lc :c
:link(lws,http://lammps.sandia.gov)
:link(ld,Manual.html)
:link(lc,Section_commands.html#comm)
:line
python command :h3
[Syntax:]
python func keyword args ... :pre
func = name of Python function :ulb,l
one or more keyword/args pairs must be appended :l
keyword = {invoke} or {input} or {return} or {format} or {file} or {here} or {exists}
{invoke} arg = none = invoke the previously defined Python function
{input} args = N i1 i2 ... iN
N = # of inputs to function
i1,...,iN = value, SELF, or LAMMPS variable name
value = integer number, floating point number, or string
SELF = reference to LAMMPS itself which can be accessed by Python function
variable = v_name, where name = name of LAMMPS variable, e.g. v_abc
{return} arg = varReturn
varReturn = v_name = LAMMPS variable name which return value of function will be assigned to
{format} arg = fstring with M characters
M = N if no return value, where N = # of inputs
M = N+1 if there is a return value
fstring = each character (i,f,s,p) corresponds in order to an input or return value
'i' = integer, 'f' = floating point, 's' = string, 'p' = SELF
{file} arg = filename
filename = file of Python code, which defines func
{here} arg = inline
inline = one or more lines of Python code which defines func
must be a single argument, typically enclosed between triple quotes
{exists} arg = none = Python code has been loaded by previous python command :pre
:ule
[Examples:]
python pForce input 2 v_x 20.0 return v_f format fff file force.py
python pForce invoke :pre
python factorial input 1 myN return v_fac format ii here """
def factorial(n):
if n == 1: return n
return n * factorial(n-1)
""" :pre
python loop input 1 SELF return v_value format -f here """
def loop(lmpptr,N,cut0):
from lammps import lammps
lmp = lammps(ptr=lmpptr) :pre
# loop N times, increasing cutoff each time :pre
for i in range(N):
cut = cut0 + i*0.1
lmp.set_variable("cut",cut) # set a variable in LAMMPS
lmp.command("pair_style lj/cut ${cut}") # LAMMPS commands
lmp.command("pair_coeff * * 1.0 1.0")
lmp.command("run 100")
""" :pre
[Description:]
IMPORTANT NOTE: It is not currently possible to use the
"python"_python.html command described in this section with Python 3,
only with Python 2. The C API changed from Python 2 to 3 and the
LAMMPS code is not compatible with both.
Define a Python function or execute a previously defined function.
Arguments, including LAMMPS variables, can be passed to the function
from the LAMMPS input script and a value returned by the Python
function to a LAMMPS variable. The Python code for the function can
be included directly in the input script or in a separate Python file.
The function can be standard Python code or it can make "callbacks" to
LAMMPS through its library interface to query or set internal values
within LAMMPS. This is a powerful mechanism for performing complex
operations in a LAMMPS input script that are not possible with the
simple input script and variable syntax which LAMMPS defines. Thus
your input script can operate more like a true programming language.
Use of this command requires building LAMMPS with the PYTHON package
which links to the Python library so that the Python interpreter is
embedded in LAMMPS. More details about this process are given below.
There are two ways to invoke a Python function once it has been
defined. One is using the {invoke} keyword. The other is to assign
the function to a "python-style variable"_variable.html defined in
your input script. Whenever the variable is evaluated, it will
execute the Python function to assign a value to the variable. Note
that variables can be evaluated in many different ways within LAMMPS.
They can be substituted for directly in an input script. Or they can
be passed to various commands as arguments, so that the variable is
evaluated during a simulation run.
A broader overview of how Python can be used with LAMMPS is
given in "Section python"_Section_python.html. There is an
examples/python directory which illustrates use of the python
command.
:line
The {func} setting specifies the name of the Python function. The
code for the function is defined using the {file} or {here} keywords
as explained below.
If the {invoke} keyword is used, no other keywords can be used, and a
previous python command must have defined the Python function
referenced by this command. This invokes the Python function with the
previously defined arguments and return value processed as explained
below. You can invoke the function as many times as you wish in your
input script.
The {input} keyword defines how many arguments {N} the Python function
expects. If it takes no arguments, then the {input} keyword should
not be used. Each argument can be specified directly as a value,
e.g. 6 or 3.14159 or abc (a string of characters). The type of each
argument is specified by the {format} keyword as explained below, so
that Python will know how to interpret the value. If the word SELF is
used for an argument it has a special meaning. A pointer is passed to
the Python function which it converts into a reference to LAMMPS
itself. This enables the function to call back to LAMMPS through its
library interface as explained below. This allows the Python function
to query or set values internal to LAMMPS which can affect the
subsequent execution of the input script. A LAMMPS variable can also
be used as an argument, specified as v_name, where "name" is the name
of the variable. Any style of LAMMPS variable can be used, as defined
by the "variable"_variable.html command. Each time the Python
function is invoked, the LAMMPS variable is evaluated and its value is
passed to the Python function.
The {return} keyword is only needed if the Python function returns a
value. The specified {varReturn} must be of the form v_name, where
"name" is the name of a python-style LAMMPS variable, defined by the
"variable"_variable.html command. The Python function can return a
numeric or string value, as specified by the {format} keyword.
As explained on the "variable"_variable.html doc page, the definition
of a python-style variable associates a Python function name with the
variable. This must match the {func} setting for this command. For
exampe these two commands would be self-consistent:
variable foo python myMultiply
python myMultiply return v_foo format f file funcs.py :pre
The two commands can appear in either order in the input script so
long as both are specified before the Python function is invoked for
the first time.
The {format} keyword must be used if the {input} or {return} keyword
is used. It defines an {fstring} with M characters, where M = sum of
number of inputs and outputs. The order of characters corresponds to
the N inputs, followed by the return value (if it exists). Each
character must be one of the following: "i" for integer, "f" for
floating point, "s" for string, or "p" for SELF. Each character
defines the type of the corresponding input or output value of the
Python function and affects the type conversion that is performed
internally as data is passed back and forth between LAMMPS and Python.
Note that it is permissible to use a "python-style
variable"_variable.html in a LAMMPS command that allows for an
equal-style variable as an argument, but only if the output of the
Python function is flagged as a numeric value ("i" or "f") via the
{format} keyword.
Either the {file}, {here}, or {exists} keyword must be used, but only
one of them. These keywords specify what Python code to load into the
Python interpreter. The {file} keyword gives the name of a file,
which should end with a ".py" suffix, which contains Python code. The
code will be immediately loaded into and run in the "main" module of
the Python interpreter. Note that Python code which contains a
function definition does not "execute" the function when it is run; it
simply defines the function so that it can be invoked later.
The {here} keyword does the same thing, except that the Python code
follows as a single argument to the {here} keyword. This can be done
using triple quotes as delimiters, as in the examples above. This
allows Python code to be listed verbatim in your input script, with
proper indentation, blank lines, and comments, as desired. See
"Section 3.2"_Section_commands.html#cmd_2, for an explanation of how
triple quotes can be used as part of input script syntax.
The {exists} keyword takes no argument. It means that Python code
containing the required Python function defined by the {func} setting,
is assumed to have been previously loaded by another python command.
Note that the Python code that is loaded and run must contain a
function with the specified {func} name. To operate properly when
later invoked, the the function code must match the {input} and
{return} and {format} keywords specified by the python command.
Otherwise Python will generate an error.
:line
This section describes how Python code can be written to work with
LAMMPS.
Whether you load Python code from a file or directly from your input
script, via the {file} and {here} keywords, the code can be identical.
It must be indented properly as Python requires. It can contain
comments or blank lines. If the code is in your input script, it
cannot however contain triple-quoted Python strings, since that will
conflict with the triple-quote parsing that the LAMMPS input script
performs.
All the Python code you specify via one or more python commands is
loaded into the Python "main" module, i.e. __main__. The code can
define global variables or statements that are outside of function
definitions. It can contain multiple functions, only one of which
matches the {func} setting in the python command. This means you can
use the {file} keyword once to load several functions, and the
{exists} keyword thereafter in subsequent python commands to access
the other functions previously loaded.
A Python function you define (or more generally, the code you load)
can import other Python modules or classes, it can make calls to other
system functions or functions you define, and it can access or modify
global variables (in the "main" module) which will persist between
successive function calls. The latter can be useful, for example, to
prevent a function from being invoke multiple times per timestep by
different commands in a LAMMPS input script that access the returned
python-style variable associated with the function. For example,
consider this function loaded with two global variables defined
outside the function:
nsteplast = -1
nvaluelast = 0 :pre
def expensive(nstep):
global nsteplast,nvaluelast
if nstep == nsteplast: return nvaluelast
nsteplast = nstep
# perform complicated calculation
nvalue = ...
nvaluelast = nvalue
return nvalue :pre
Nsteplast stores the previous timestep the function was invoked
(passed as an argument to the function). Nvaluelast stores the return
value computed on the last function invocation. If the function is
invoked again on the same timestep, the previous value is simply
returned, without re-computing it. The "global" statement inside the
Python function allows it to overwrite the global variables.
Note that if you load Python code multiple times (via multiple python
commands), you can overwrite previously loaded variables and functions
if you are not careful. E.g. if the code above were loaded twice, the
global variables would be re-initialized, which might not be what you
want. Likewise, if a function with the same name exists in two chunks
of Python code you load, the function loaded second will override the
function loaded first.
It's important to realize that if you are running LAMMPS in parallel,
each MPI task will load the Python interpreter and execute a local
copy of the Python function(s) you define. There is no connection
between the Python interpreters running on different processors.
This implies three important things.
First, if you put a print statement in your Python function, you will
see P copies of the output, when running on P processors. If the
prints occur at (nearly) the same time, the P copies of the output may
be mixed together. Welcome to the world of parallel programming and
debugging.
Second, if your Python code loads modules that are not pre-loaded by
the Python library, then it will load the module from disk. This may
be a bottleneck if 1000s of processors try to load a module at the
same time. On some large supercomputers, loading of modules from disk
by Python may be disabled. In this case you would need to pre-build a
Python library that has the required modules pre-loaded and link
LAMMPS with that library.
Third, if your Python code calls back to LAMMPS (discussed in the
next section) and causes LAMMPS to perform an MPI operation requires
global communication (e.g. via MPI_Allreduce), such as computing the
global temperature of the system, then you must insure all your Python
functions (running independently on different processors) call back to
LAMMPS. Otherwise the code may hang.
:line
Your Python function can "call back" to LAMMPS through its
library interface, if you use the SELF input to pass Python
a pointer to LAMMPS. The mechanism for doing this in your
Python function is as follows:
def foo(lmpptr,...):
from lammps import lammps
lmp = lammps(ptr=lmpptr)
lmp.command('print "Hello from inside Python"')
... :pre
The function definition must include a variable (lmpptr in this case)
which corresponds to SELF in the python command. The first line of
the function imports the Python module lammps.py in the python dir of
the distribution. The second line creates a Python object "lmp" which
wraps the instance of LAMMPS that called the function. The
"ptr=lmpptr" argument is what makes that happen. The thrid line
invokes the command() function in the LAMMPS library interface. It
takes a single string argument which is a LAMMPS input script command
for LAMMPS to execute, the same as if it appeared in your input
script. In this case, LAMMPS should output
Hello from inside Python :pre
to the screen and log file. Note that since the LAMMPS print command
itself takes a string in quotes as its argument, the Python string
must be delimited with a different style of quotes.
"Section 11.7"_Section_python.html#py_7 describes the syntax for how
Python wraps the various functions included in the LAMMPS library
interface.
A more interesting example is in the examples/python/in.python script
which loads and runs the following function from examples/python/funcs.py:
def loop(N,cut0,thresh,lmpptr):
print "LOOP ARGS",N,cut0,thresh,lmpptr
from lammps import lammps
lmp = lammps(ptr=lmpptr)
natoms = lmp.get_natoms() :pre
for i in range(N):
cut = cut0 + i*0.1 :pre
lmp.set_variable("cut",cut) # set a variable in LAMMPS
lmp.command("pair_style lj/cut ${cut}") # LAMMPS command
#lmp.command("pair_style lj/cut %d" % cut) # LAMMPS command option :pre
lmp.command("pair_coeff * * 1.0 1.0") # ditto
lmp.command("run 10") # ditto
pe = lmp.extract_compute("thermo_pe",0,0) # extract total PE from LAMMPS
print "PE",pe/natoms,thresh
if pe/natoms < thresh: return :pre
with these input script commands:
python loop input 4 10 1.0 -4.0 SELF format iffp file funcs.py
python loop invoke :pre
This has the effect of looping over a series of 10 short runs (10
timesteps each) where the pair style cutoff is increased from a value
of 1.0 in distance units, in increments of 0.1. The looping stops
when the per-atom potential energy falls below a threshhold of -4.0 in
energy units. More generally, Python can be used to implement a loop
with complex logic, much more so than can be created using the LAMMPS
"jump"_jump.html and "if"_if.html commands.
Several LAMMPS library functions are called from the loop function.
Get_natoms() returns the number of atoms in the simulation, so that it
can be used to normalize the potential energy that is returned by
extract_compute() for the "thermo_pe" compute that is defined by
default for LAMMPS thermodynamic output. Set_variable() sets the
value of a string variable defined in LAMMPS. This library function
is a useful way for a Python function to return multiple values to
LAMMPS, more than the single value that can be passed back via a
return statement. This cutoff value in the "cut" variable is then
substituted (by LAMMPS) in the pair_style command that is executed
next. Alternatively, the "LAMMPS command option" line could be used
in place of the 2 preceeding lines, to have Python insert the value
into the LAMMPS command string.
IMPORTANT NOTE: When using the callback mechanism just described,
recognize that there are some operations you should not attempt
because LAMMPS cannot execute them correctly. If the Python function
is invoked between runs in the LAMMPS input script, then it should be
OK to invoke any LAMMPS input script command via the library interface
command() or file() functions, so long as the command would work if it
were executed in the LAMMPS input script directly at the same point.
However, a Python function can also be invoked during a run, whenever
an associated LAMMPS variable it is assigned to is evaluted. If the
variable is an input argument to another LAMMPS command (e.g. "fix
setforce"_fix_setforce.html), then the Python function will be invoked
inside the class for that command, in one of its methods that is
invoked in the middle of a timestep. You cannot execute arbitrary
input script commands from the Python function (again, via the
command() or file() functions) at that point in the run and expect it
to work. Other library functions such as those that invoke computes
or other variables may have hidden side effects as well. In these
cases, LAMMPS has no simple way to check that something illogical is
being attempted.
:line
If you run Python code directly on your workstation, either
interactively or by using Python to launch a Python script stored in a
file, and your code has an error, you will typically see informative
error messages. That is not the case when you run Python code from
LAMMPS using an embedded Python interpreter. The code will typically
fail silently. LAMMPS will catch some errors but cannot tell you
where in the Python code the problem occurred. For example, if the
Python code cannot be loaded and run because it has syntax or other
logic errors, you may get an error from Python pointing to the
offending line, or you may get one of these generic errors from
LAMMPS:
Could not process Python file
Could not process Python string :pre
When the Python function is invoked, if it does not return properly,
you will typically get this generic error from LAMMPS:
Python function evaluation failed :pre
Here are three suggestions for debugging your Python code while
running it under LAMMPS.
First, don't run it under LAMMPS, at least to start with! Debug it
using plain Python. Load and invoke your function, pass it arguments,
check return values, etc.
Second, add Python print statements to the function to check how far
it gets and intermediate values it calculates. See the discussion
above about printing from Python when running in parallel.
Third, use Python exception handling. For example, say this statement
in your Python function is failing, because you have not initialized the
variable foo:
foo += 1 :pre
If you put one (or more) statements inside a "try" statement,
like this:
import exceptions
print "Inside simple function"
try:
foo += 1 # one or more statements here
except Exception, e:
print "FOO error:",e :pre
then you will get this message printed to the screen:
FOO error: local variable 'foo' referenced before assignment :pre
If there is no error in the try statements, then nothing is printed.
Either way the function continues on (unless you put a return or
sys.exit() in the except clause).
:line
[Restrictions:]
This command is part of the PYTHON package. It is only enabled if
LAMMPS was built with that package. See the "Making
LAMMPS"_Section_start.html#start_3 section for more info.
Building LAMMPS with the PYTHON package will link LAMMPS with the
Python library on your system. Settings to enable this are in the
lib/python/Makefile.lammps file. See the lib/python/README file for
information on those settings.
If you use Python code which calls back to LAMMPS, via the SELF input
argument explained above, there is an extra step required when
building LAMMPS. LAMMPS must also be built as a shared library and
your Python function must be able to to load the Python module in
python/lammps.py that wraps the LAMMPS library interface. These are
the same steps required to use Python by itself to wrap LAMMPS.
Details on these steps are explained in "Section
python"_Section.python.html. Note that it is important that the
stand-alone LAMMPS executable and the LAMMPS shared library be
consistent (built from the same source code files) in order for this
to work. If the two have been built at different times using
different source files, problems may occur.
As described above, you can use the python command to invoke a Python
function which calls back to LAMMPS through its Python-wrapped library
interface. However you cannot do the opposite. I.e. you cannot call
LAMMPS from Python and invoke the python command to "callback" to
Python and execute a Python function. LAMMPS will generate an error
if you try to do that. Note that we think there actually should be a
way to do that, but haven't yet been able to figure out how to do it
successfully.
[Related commands:]
"shell"_shell.html, "variable"_variable.html
[Default:] none

View File

@ -17,7 +17,8 @@
</PRE> </PRE>
<UL><LI>name = name of variable to define <UL><LI>name = name of variable to define
<LI>style = <I>delete</I> or <I>index</I> or <I>loop</I> or <I>world</I> or <I>universe</I> or <I>uloop</I> or <I>string</I> or <I>format</I> or <I>getenv</I> or <I>file</I> or <I>atomfile</I> or <I>equal</I> or <I>atom</I> <LI>style = <I>delete</I> or <I>index</I> or <I>loop</I> or <I>world</I> or <I>universe</I> or
<I>uloop</I> or <I>string</I> or <I>format</I> or <I>getenv</I> or <I>file</I> or <I>atomfile</I> or <I>python</I> or <I>equal</I> or <I>atom</I>
<PRE> <I>delete</I> = no args <PRE> <I>delete</I> = no args
<I>index</I> args = one or more strings <I>index</I> args = one or more strings
@ -45,6 +46,7 @@
<I>getenv</I> arg = one string <I>getenv</I> arg = one string
<I>file</I> arg = filename <I>file</I> arg = filename
<I>atomfile</I> arg = filename <I>atomfile</I> arg = filename
<I>python</I> arg = function
<I>equal</I> or <I>atom</I> args = one formula containing numbers, thermo keywords, math operations, group functions, atom values and vectors, compute/fix/variable references <I>equal</I> or <I>atom</I> args = one formula containing numbers, thermo keywords, math operations, group functions, atom values and vectors, compute/fix/variable references
numbers = 0.0, 100, -5.4, 2.8e-4, etc numbers = 0.0, 100, -5.4, 2.8e-4, etc
constants = PI constants = PI
@ -87,6 +89,7 @@ variable b equal xcm(mol1,x)/2.0
variable b equal c_myTemp variable b equal c_myTemp
variable b atom x*y/vol variable b atom x*y/vol
variable foo string myfile variable foo string myfile
variable myPy python increase
variable f file values.txt variable f file values.txt
variable temp world 300.0 310.0 320.0 ${Tfinal} variable temp world 300.0 310.0 320.0 ${Tfinal}
variable x universe 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 variable x universe 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
@ -116,7 +119,9 @@ command) or used as input to an averaging fix (see the <A HREF = "fix_ave_spatia
ave/spatial</A> and <A HREF = "fix_ave_atom.html">fix ave/atom</A> ave/spatial</A> and <A HREF = "fix_ave_atom.html">fix ave/atom</A>
commands). Variables of style <I>atomfile</I> can be used anywhere in an commands). Variables of style <I>atomfile</I> can be used anywhere in an
input script that atom-style variables are used; they get their input script that atom-style variables are used; they get their
per-atom values from a file rather than from a formula. per-atom values from a file rather than from a formula. Variables can
be hooked to Python functions using code you provide, so that the
variable gets its value from the evaluation of the Python code.
</P> </P>
<P>IMPORTANT NOTE: As discussed in <A HREF = "Section_commands.html#cmd_2">Section <P>IMPORTANT NOTE: As discussed in <A HREF = "Section_commands.html#cmd_2">Section
3.2</A> of the manual, an input script can 3.2</A> of the manual, an input script can
@ -138,11 +143,31 @@ different values when it is evaluated at different times during a
simulation. simulation.
</P> </P>
<P>IMPORTANT NOTE: When the input script line is encountered that defines <P>IMPORTANT NOTE: When the input script line is encountered that defines
a variable of style <I>equal</I> or <I>atom</I> that contains a formula, the a variable of style <I>equal</I> or <I>atom</I> or <I>python</I> that contains a
formula is NOT immediately evaluated and the result stored. See the formula or Python code, the formula is NOT immediately evaluated and
discussion below about "Immediate Evaluation of Variables" if you want the result stored. See the discussion below about "Immediate
to do this. This is also true of the <I>format</I> style variable Evaluation of Variables" if you want to do this. This is also true of
since it evaluates another variable when it is invoked. the <I>format</I> style variable since it evaluates another variable when
it is invoked.
</P>
<P>IMPORTANT NOTE: Variables of style <I>equal</I> and <I>atom</I> can be used as
inputs to various other LAMMPS commands which evaluate their formulas
as needed, e.g. at different timesteps during a <A HREF = "run.html">run</A>.
Variables of style <I>python</I> can be used in place of an equal-style
variable so long as the associated Python function, as defined by the
<A HREF = "python.html">python</A> command, returns a numeric value. Thus any
command that states it can use an equal-style variable as an argument,
can also use such a python-style variable. This means that when the
LAMMPS command evaluates the variable, the Python function will be
executed.
</P>
<P>When the input script line is encountered that defines
a variable of style <I>equal</I> or <I>atom</I> or <I>python</I> that contains a
formula or Python code, the formula is NOT immediately evaluated and
the result stored. See the discussion below about "Immediate
Evaluation of Variables" if you want to do this. This is also true of
the <I>format</I> style variable since it evaluates another variable when
it is invoked.
</P> </P>
<P>IMPORTANT NOTE: When a variable command is encountered in the input <P>IMPORTANT NOTE: When a variable command is encountered in the input
script and the variable name has already been specified, the command script and the variable name has already been specified, the command
@ -155,12 +180,12 @@ means that using the <A HREF = "Section_start.html#start_7">command-line switch<
script. script.
</P> </P>
<P>There are two exceptions to this rule. First, variables of style <P>There are two exceptions to this rule. First, variables of style
<I>string</I>, <I>getenv</I>, <I>equal</I> and <I>atom</I> ARE redefined each time the <I>string</I>, <I>getenv</I>, <I>equal</I>, <I>atom</I>, and <I>python</I> ARE redefined each
command is encountered. This allows these style of variables to be time the command is encountered. This allows these style of variables
redefined multiple times in an input script. In a loop, this means to be redefined multiple times in an input script. In a loop, this
the formula associated with an <I>equal</I> or <I>atom</I> style variable can means the formula associated with an <I>equal</I> or <I>atom</I> style variable
change if it contains a substitution for another variable, e.g. $x or can change if it contains a substitution for another variable, e.g. $x
v_x. or v_x.
</P> </P>
<P>Second, as described below, if a variable is iterated on to the end of <P>Second, as described below, if a variable is iterated on to the end of
its list of strings via the <A HREF = "next.html">next</A> command, it is removed its list of strings via the <A HREF = "next.html">next</A> command, it is removed
@ -202,13 +227,15 @@ variable a delete
</PRE> </PRE>
<HR> <HR>
<P>This section describes how various variable styles are defined and <P>This section describes how all the various variable styles are defined
what they store. Many of the styles store one or more strings. Note and what they store. Except for the <I>equal</I> and <I>atom</I> styles,
that a single string can contain spaces (multiple words), if it is which are explaine in the next section.
enclosed in quotes in the variable command. When the variable is </P>
substituted for in another input script command, its returned string <P>Many of the styles store one or more strings. Note that a single
will then be interpreted as multiple arguments in the expanded string can contain spaces (multiple words), if it is enclosed in
command. quotes in the variable command. When the variable is substituted for
in another input script command, its returned string will then be
interpreted as multiple arguments in the expanded command.
</P> </P>
<P>For the <I>index</I> style, one or more strings are specified. Initially, <P>For the <I>index</I> style, one or more strings are specified. Initially,
the 1st string is assigned to the variable. Each time a the 1st string is assigned to the variable. Each time a
@ -338,6 +365,31 @@ will be assigned to that atom. IDs can be listed in any order.
for all atoms is first set to 0.0. Thus values for atoms whose ID for all atoms is first set to 0.0. Thus values for atoms whose ID
does not appear in the set, will remain 0.0. does not appear in the set, will remain 0.0.
</P> </P>
<P>For the <I>python</I> style a Python function name is provided. This needs
to match a function name specified in a <A HREF = "python.html">python</A> command
which returns a value to this variable as defined by its <I>return</I>
keyword. For exampe these two commands would be self-consistent:
</P>
<PRE>variable foo python myMultiply
python myMultiply return v_foo format f file funcs.py
</PRE>
<P>The two commands can appear in either order so long as both are
specified before the Python function is invoked for the first time.
</P>
<P>Each time the variable is evaluated, the associated Python function is
invoked, and the value it returns is also returned by the variable.
Since the Python function can use other LAMMPS variables as input, or
query interal LAMMPS quantities to perform its computation, this means
the variable can return a different value each time it is evaluated.
</P>
<P>The type of value stored in the variable is determined by the <I>format</I>
keyword of the <A HREF = "python.html">python</A> command. It can be an integer
(i), floating point (f), or string (s) value. As mentioned above, if
it is a numeric value (integer or floating point), then the
python-style variable can be used in place of an equal-style variable
anywhere in an input script, e.g. as an argument to another command
that allows for equal-style variables.
</P>
<HR> <HR>
<P>For the <I>equal</I> and <I>atom</I> styles, a single string is specified which <P>For the <I>equal</I> and <I>atom</I> styles, a single string is specified which

View File

@ -13,7 +13,8 @@ variable command :h3
variable name style args ... :pre variable name style args ... :pre
name = name of variable to define :ulb,l name = name of variable to define :ulb,l
style = {delete} or {index} or {loop} or {world} or {universe} or {uloop} or {string} or {format} or {getenv} or {file} or {atomfile} or {equal} or {atom} :l style = {delete} or {index} or {loop} or {world} or {universe} or
{uloop} or {string} or {format} or {getenv} or {file} or {atomfile} or {python} or {equal} or {atom} :l
{delete} = no args {delete} = no args
{index} args = one or more strings {index} args = one or more strings
{loop} args = N {loop} args = N
@ -40,6 +41,7 @@ style = {delete} or {index} or {loop} or {world} or {universe} or {uloop} or {st
{getenv} arg = one string {getenv} arg = one string
{file} arg = filename {file} arg = filename
{atomfile} arg = filename {atomfile} arg = filename
{python} arg = function
{equal} or {atom} args = one formula containing numbers, thermo keywords, math operations, group functions, atom values and vectors, compute/fix/variable references {equal} or {atom} args = one formula containing numbers, thermo keywords, math operations, group functions, atom values and vectors, compute/fix/variable references
numbers = 0.0, 100, -5.4, 2.8e-4, etc numbers = 0.0, 100, -5.4, 2.8e-4, etc
constants = PI constants = PI
@ -81,6 +83,7 @@ variable b equal xcm(mol1,x)/2.0
variable b equal c_myTemp variable b equal c_myTemp
variable b atom x*y/vol variable b atom x*y/vol
variable foo string myfile variable foo string myfile
variable myPy python increase
variable f file values.txt variable f file values.txt
variable temp world 300.0 310.0 320.0 $\{Tfinal\} variable temp world 300.0 310.0 320.0 $\{Tfinal\}
variable x universe 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 variable x universe 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
@ -110,7 +113,9 @@ command) or used as input to an averaging fix (see the "fix
ave/spatial"_fix_ave_spatial.html and "fix ave/atom"_fix_ave_atom.html ave/spatial"_fix_ave_spatial.html and "fix ave/atom"_fix_ave_atom.html
commands). Variables of style {atomfile} can be used anywhere in an commands). Variables of style {atomfile} can be used anywhere in an
input script that atom-style variables are used; they get their input script that atom-style variables are used; they get their
per-atom values from a file rather than from a formula. per-atom values from a file rather than from a formula. Variables can
be hooked to Python functions using code you provide, so that the
variable gets its value from the evaluation of the Python code.
IMPORTANT NOTE: As discussed in "Section IMPORTANT NOTE: As discussed in "Section
3.2"_Section_commands.html#cmd_2 of the manual, an input script can 3.2"_Section_commands.html#cmd_2 of the manual, an input script can
@ -132,11 +137,31 @@ different values when it is evaluated at different times during a
simulation. simulation.
IMPORTANT NOTE: When the input script line is encountered that defines IMPORTANT NOTE: When the input script line is encountered that defines
a variable of style {equal} or {atom} that contains a formula, the a variable of style {equal} or {atom} or {python} that contains a
formula is NOT immediately evaluated and the result stored. See the formula or Python code, the formula is NOT immediately evaluated and
discussion below about "Immediate Evaluation of Variables" if you want the result stored. See the discussion below about "Immediate
to do this. This is also true of the {format} style variable Evaluation of Variables" if you want to do this. This is also true of
since it evaluates another variable when it is invoked. the {format} style variable since it evaluates another variable when
it is invoked.
IMPORTANT NOTE: Variables of style {equal} and {atom} can be used as
inputs to various other LAMMPS commands which evaluate their formulas
as needed, e.g. at different timesteps during a "run"_run.html.
Variables of style {python} can be used in place of an equal-style
variable so long as the associated Python function, as defined by the
"python"_python.html command, returns a numeric value. Thus any
command that states it can use an equal-style variable as an argument,
can also use such a python-style variable. This means that when the
LAMMPS command evaluates the variable, the Python function will be
executed.
When the input script line is encountered that defines
a variable of style {equal} or {atom} or {python} that contains a
formula or Python code, the formula is NOT immediately evaluated and
the result stored. See the discussion below about "Immediate
Evaluation of Variables" if you want to do this. This is also true of
the {format} style variable since it evaluates another variable when
it is invoked.
IMPORTANT NOTE: When a variable command is encountered in the input IMPORTANT NOTE: When a variable command is encountered in the input
script and the variable name has already been specified, the command script and the variable name has already been specified, the command
@ -149,12 +174,12 @@ means that using the "command-line switch"_Section_start.html#start_7
script. script.
There are two exceptions to this rule. First, variables of style There are two exceptions to this rule. First, variables of style
{string}, {getenv}, {equal} and {atom} ARE redefined each time the {string}, {getenv}, {equal}, {atom}, and {python} ARE redefined each
command is encountered. This allows these style of variables to be time the command is encountered. This allows these style of variables
redefined multiple times in an input script. In a loop, this means to be redefined multiple times in an input script. In a loop, this
the formula associated with an {equal} or {atom} style variable can means the formula associated with an {equal} or {atom} style variable
change if it contains a substitution for another variable, e.g. $x or can change if it contains a substitution for another variable, e.g. $x
v_x. or v_x.
Second, as described below, if a variable is iterated on to the end of Second, as described below, if a variable is iterated on to the end of
its list of strings via the "next"_next.html command, it is removed its list of strings via the "next"_next.html command, it is removed
@ -196,13 +221,15 @@ variable a delete :pre
:line :line
This section describes how various variable styles are defined and This section describes how all the various variable styles are defined
what they store. Many of the styles store one or more strings. Note and what they store. Except for the {equal} and {atom} styles,
that a single string can contain spaces (multiple words), if it is which are explaine in the next section.
enclosed in quotes in the variable command. When the variable is
substituted for in another input script command, its returned string Many of the styles store one or more strings. Note that a single
will then be interpreted as multiple arguments in the expanded string can contain spaces (multiple words), if it is enclosed in
command. quotes in the variable command. When the variable is substituted for
in another input script command, its returned string will then be
interpreted as multiple arguments in the expanded command.
For the {index} style, one or more strings are specified. Initially, For the {index} style, one or more strings are specified. Initially,
the 1st string is assigned to the variable. Each time a the 1st string is assigned to the variable. Each time a
@ -332,6 +359,31 @@ IMPORTANT NOTE: Every time a set of per-atom lines is read, the value
for all atoms is first set to 0.0. Thus values for atoms whose ID for all atoms is first set to 0.0. Thus values for atoms whose ID
does not appear in the set, will remain 0.0. does not appear in the set, will remain 0.0.
For the {python} style a Python function name is provided. This needs
to match a function name specified in a "python"_python.html command
which returns a value to this variable as defined by its {return}
keyword. For exampe these two commands would be self-consistent:
variable foo python myMultiply
python myMultiply return v_foo format f file funcs.py :pre
The two commands can appear in either order so long as both are
specified before the Python function is invoked for the first time.
Each time the variable is evaluated, the associated Python function is
invoked, and the value it returns is also returned by the variable.
Since the Python function can use other LAMMPS variables as input, or
query interal LAMMPS quantities to perform its computation, this means
the variable can return a different value each time it is evaluated.
The type of value stored in the variable is determined by the {format}
keyword of the "python"_python.html command. It can be an integer
(i), floating point (f), or string (s) value. As mentioned above, if
it is a numeric value (integer or floating point), then the
python-style variable can be used in place of an equal-style variable
anywhere in an input script, e.g. as an argument to another command
that allows for equal-style variables.
:line :line
For the {equal} and {atom} styles, a single string is specified which For the {equal} and {atom} styles, a single string is specified which

View File

@ -88,7 +88,8 @@ peptide: dynamics of a small solvated peptide chain (5-mer)
peri: Peridynamic model of cylinder impacted by indenter peri: Peridynamic model of cylinder impacted by indenter
pour: pouring of granular particles into a 3d box, then chute flow pour: pouring of granular particles into a 3d box, then chute flow
prd: parallel replica dynamics of vacancy diffusion in bulk Si prd: parallel replica dynamics of vacancy diffusion in bulk Si
qeq: use of the QEQ pacakge for charge equilibration python: use of PYTHON package to invoke Python code from input script
qeq: use of QEQ pacakge for charge equilibration
reax: RDX and TATB models using the ReaxFF reax: RDX and TATB models using the ReaxFF
rigid: rigid bodies modeled as independent or coupled rigid: rigid bodies modeled as independent or coupled
shear: sideways shear applied to 2d solid, with and without a void shear: sideways shear applied to 2d solid, with and without a void
@ -106,8 +107,7 @@ accelerate/README for Make.py commands suitable for its example
scripts. scripts.
cd src cd src
Make.py -j 16 -p none std no-lib no-kokkos reax meam poems reaxc orig \ Make.py -j 16 -p none std no-lib reax meam poems reaxc orig -a lib-all mpi
-a lib-all mpi
Here is how you might run and visualize one of the sample problems: Here is how you might run and visualize one of the sample problems:

22
examples/python/funcs.py Normal file
View File

@ -0,0 +1,22 @@
# Python function that implements a loop of short runs
# calls back to LAMMPS via "lmp" instance
# lammps() must be called with ptr=lmpptr for this to work
def loop(N,cut0,thresh,lmpptr):
print "LOOP ARGS",N,cut0,thresh,lmpptr
from lammps import lammps
lmp = lammps(ptr=lmpptr)
natoms = lmp.get_natoms()
for i in range(N):
cut = cut0 + i*0.1
lmp.set_variable("cut",cut) # set a variable in LAMMPS
lmp.command("pair_style lj/cut ${cut}") # LAMMPS command
#lmp.command("pair_style lj/cut %d" % cut) # LAMMPS command option
lmp.command("pair_coeff * * 1.0 1.0") # ditto
lmp.command("run 10") # ditto
pe = lmp.extract_compute("thermo_pe",0,0) # extract total PE from LAMMPS
print "PE",pe/natoms,thresh
if pe/natoms < thresh: return

64
examples/python/in.python Normal file
View File

@ -0,0 +1,64 @@
# 3d Lennard-Jones melt with Python functions added
units lj
atom_style atomic
lattice fcc 0.8442
region box block 0 10 0 10 0 10
create_box 1 box
create_atoms 1 box
mass 1 1.0
velocity all create 1.44 87287 loop geom
pair_style lj/cut 2.5
pair_coeff 1 1 1.0 1.0 2.5
neighbor 0.3 bin
neigh_modify delay 0 every 1 check yes
fix 1 all nve
run 10
# 1st Python function
# example of catching a syntax error
python simple here """
def simple():
import exceptions
print "Inside simple function"
try:
foo += 1
except Exception, e:
print "FOO error:",e
"""
python simple invoke
# 2nd Python function
# example of returning the function value to a python-style variable
# invoke it twice
variable fact python factorial
python factorial input 1 v_n return v_fact format ii here """
def factorial(n):
if n == 1: return 1
return n*factorial(n-1)
"""
variable n string 10
python factorial invoke
print "Factorial of $n = ${fact}"
variable n string 20
python factorial invoke
print "Factorial of $n = ${fact}"
# 3rd Python function
# example of calling back to LAMMPS and writing a run loop in Python
variable cut string 0.0
python loop input 4 10 1.0 -4.0 SELF format iffp file funcs.py
python loop invoke

View File

@ -0,0 +1,315 @@
LAMMPS (12 Mar 2015)
# 3d Lennard-Jones melt
units lj
atom_style atomic
lattice fcc 0.8442
Lattice spacing in x,y,z = 1.6796 1.6796 1.6796
region box block 0 10 0 10 0 10
create_box 1 box
Created orthogonal box = (0 0 0) to (16.796 16.796 16.796)
1 by 1 by 1 MPI processor grid
create_atoms 1 box
Created 4000 atoms
mass 1 1.0
velocity all create 1.44 87287 loop geom
pair_style lj/cut 2.5
pair_coeff 1 1 1.0 1.0 2.5
neighbor 0.3 bin
neigh_modify delay 0 every 1 check yes
fix 1 all nve
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 2.8
Memory usage per processor = 2.69271 Mbytes
Step Temp E_pair E_mol TotEng Press
0 1.44 -6.7733681 0 -4.6139081 -5.0199732
10 1.1259767 -6.3010653 0 -4.6125225 -2.5704638
Loop time of 0.03213 on 1 procs for 10 steps with 4000 atoms
Pair time (%) = 0.0242701 (75.5371)
Neigh time (%) = 0.006531 (20.3268)
Comm time (%) = 0.000502825 (1.56497)
Outpt time (%) = 2.09808e-05 (0.0652998)
Other time (%) = 0.00080514 (2.50588)
Nlocal: 4000 ave 4000 max 4000 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 5841 ave 5841 max 5841 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 155984 ave 155984 max 155984 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 155984
Ave neighs/atom = 38.996
Neighbor list builds = 1
Dangerous builds = 0
# 1st Python function
# example of catching a syntax error
python simple here """
def simple():
import exceptions
print "Inside simple function"
try:
foo += 1
except Exception, e:
print "FOO error:",e
"""
python simple invoke
# 2nd Python function
# example of returning the function value to a python-style variable
# invoke it twice
variable fact python factorial
python factorial input 1 v_n return v_fact format ii here """
def factorial(n):
if n == 1: return 1
return n*factorial(n-1)
"""
variable n string 10
python factorial invoke
print "Factorial of $n = ${fact}"
Factorial of 10 = 3628800
variable n string 20
python factorial invoke
print "Factorial of $n = ${fact}"
Factorial of 20 = 2432902008176640000
# 3rd Python function
# example of calling back to LAMMPS and writing a run loop in Python
variable cut string 0.0
python loop input 4 10 1.0 -4.0 SELF format iffp file funcs.py
python loop invoke
pair_style lj/cut ${cut}
pair_style lj/cut 1.0
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.3
Memory usage per processor = 2.78761 Mbytes
Step Temp E_pair E_mol TotEng Press
10 1.1259767 0.016557378 0 1.7051002 1.2784679
20 0.87608998 0.39300382 0 1.7068103 6.0488236
Loop time of 0.00451207 on 1 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00158691 (35.1704)
Neigh time (%) = 0.00194287 (43.0594)
Comm time (%) = 0.000257015 (5.69617)
Outpt time (%) = 2.09808e-05 (0.464993)
Other time (%) = 0.000704288 (15.609)
Nlocal: 4000 ave 4000 max 4000 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 2083 ave 2083 max 2083 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 17727 ave 17727 max 17727 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 17727
Ave neighs/atom = 4.43175
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.1
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.4
Memory usage per processor = 2.78761 Mbytes
Step Temp E_pair E_mol TotEng Press
20 0.87608998 -0.33042884 0 0.9833776 8.5817494
30 1.0155079 -0.83166219 0 0.69121891 7.9905553
Loop time of 0.00607896 on 1 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00298262 (49.0646)
Neigh time (%) = 0.00210714 (34.6629)
Comm time (%) = 0.000262499 (4.31816)
Outpt time (%) = 2.00272e-05 (0.329451)
Other time (%) = 0.000706673 (11.6249)
Nlocal: 4000 ave 4000 max 4000 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 2087 ave 2087 max 2087 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 21036 ave 21036 max 21036 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 21036
Ave neighs/atom = 5.259
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.2
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.5
Memory usage per processor = 2.78761 Mbytes
Step Temp E_pair E_mol TotEng Press
30 1.0155079 -2.0616558 0 -0.53877467 7.6238572
40 1.0490928 -2.1868324 0 -0.61358669 7.2084131
Loop time of 0.00735807 on 1 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00416398 (56.5906)
Neigh time (%) = 0.00219989 (29.8976)
Comm time (%) = 0.000262022 (3.56101)
Outpt time (%) = 1.90735e-05 (0.259218)
Other time (%) = 0.00071311 (9.69153)
Nlocal: 4000 ave 4000 max 4000 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 2250 ave 2250 max 2250 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 24095 ave 24095 max 24095 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 24095
Ave neighs/atom = 6.02375
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.3
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.6
Memory usage per processor = 2.78761 Mbytes
Step Temp E_pair E_mol TotEng Press
40 1.0490928 -3.0667608 0 -1.493515 6.2796311
50 1.0764484 -3.1173704 0 -1.5031014 6.0850409
Loop time of 0.0085659 on 1 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00486517 (56.7969)
Neigh time (%) = 0.00266886 (31.1568)
Comm time (%) = 0.000301838 (3.52371)
Outpt time (%) = 2.00272e-05 (0.233801)
Other time (%) = 0.000710011 (8.2888)
Nlocal: 4000 ave 4000 max 4000 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 2572 ave 2572 max 2572 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 27137 ave 27137 max 27137 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 27137
Ave neighs/atom = 6.78425
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.4
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.7
Memory usage per processor = 2.78761 Mbytes
Step Temp E_pair E_mol TotEng Press
50 1.0764484 -3.6112241 0 -1.9969552 5.4223348
60 1.1101013 -3.6616014 0 -1.9968657 5.2348251
Loop time of 0.0091939 on 1 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00552583 (60.1032)
Neigh time (%) = 0.00259781 (28.2558)
Comm time (%) = 0.000323296 (3.51642)
Outpt time (%) = 2.00272e-05 (0.217831)
Other time (%) = 0.000726938 (7.90675)
Nlocal: 4000 ave 4000 max 4000 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 3013 ave 3013 max 3013 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 30887 ave 30887 max 30887 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 30887
Ave neighs/atom = 7.72175
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.5
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.8
Memory usage per processor = 2.78761 Mbytes
Step Temp E_pair E_mol TotEng Press
60 1.1101013 -3.9655053 0 -2.3007696 4.7849008
70 1.1122144 -3.9657095 0 -2.297805 4.8014106
Loop time of 0.0102301 on 1 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00630403 (61.6225)
Neigh time (%) = 0.00282717 (27.6359)
Comm time (%) = 0.000349283 (3.41428)
Outpt time (%) = 2.00272e-05 (0.195768)
Other time (%) = 0.000729561 (7.13154)
Nlocal: 4000 ave 4000 max 4000 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 3388 ave 3388 max 3388 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 35959 ave 35959 max 35959 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 35959
Ave neighs/atom = 8.98975
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.6
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.9
Memory usage per processor = 2.78761 Mbytes
Step Temp E_pair E_mol TotEng Press
70 1.1122144 -4.1752688 0 -2.5073643 4.4755409
80 1.117224 -4.1831357 0 -2.5077187 4.446079
Loop time of 0.011508 on 1 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00736189 (63.972)
Neigh time (%) = 0.00303006 (26.3301)
Comm time (%) = 0.000365019 (3.17187)
Outpt time (%) = 2.00272e-05 (0.174028)
Other time (%) = 0.000730991 (6.35203)
Nlocal: 4000 ave 4000 max 4000 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Nghost: 3612 ave 3612 max 3612 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Neighs: 43239 ave 43239 max 43239 min
Histogram: 1 0 0 0 0 0 0 0 0 0
Total # of neighbors = 43239
Ave neighs/atom = 10.8097
Neighbor list builds = 1
Dangerous builds = 0

View File

@ -0,0 +1,315 @@
LAMMPS (12 Mar 2015)
# 3d Lennard-Jones melt
units lj
atom_style atomic
lattice fcc 0.8442
Lattice spacing in x,y,z = 1.6796 1.6796 1.6796
region box block 0 10 0 10 0 10
create_box 1 box
Created orthogonal box = (0 0 0) to (16.796 16.796 16.796)
1 by 2 by 2 MPI processor grid
create_atoms 1 box
Created 4000 atoms
mass 1 1.0
velocity all create 1.44 87287 loop geom
pair_style lj/cut 2.5
pair_coeff 1 1 1.0 1.0 2.5
neighbor 0.3 bin
neigh_modify delay 0 every 1 check yes
fix 1 all nve
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 2.8
Memory usage per processor = 2.60344 Mbytes
Step Temp E_pair E_mol TotEng Press
0 1.44 -6.7733681 0 -4.6139081 -5.0199732
10 1.1259767 -6.3010653 0 -4.6125225 -2.5704638
Loop time of 0.00962114 on 4 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00643039 (66.836)
Neigh time (%) = 0.00174427 (18.1296)
Comm time (%) = 0.00106865 (11.1073)
Outpt time (%) = 3.48091e-05 (0.361798)
Other time (%) = 0.000343025 (3.56532)
Nlocal: 1000 ave 1013 max 989 min
Histogram: 1 0 1 0 0 1 0 0 0 1
Nghost: 2901 ave 2912 max 2888 min
Histogram: 1 0 0 0 1 0 0 1 0 1
Neighs: 38996 ave 39269 max 38365 min
Histogram: 1 0 0 0 0 0 0 0 1 2
Total # of neighbors = 155984
Ave neighs/atom = 38.996
Neighbor list builds = 1
Dangerous builds = 0
# 1st Python function
# example of catching a syntax error
python simple here """
def simple():
import exceptions
print "Inside simple function"
try:
foo += 1
except Exception, e:
print "FOO error:",e
"""
python simple invoke
# 2nd Python function
# example of returning the function value to a python-style variable
# invoke it twice
variable fact python factorial
python factorial input 1 v_n return v_fact format ii here """
def factorial(n):
if n == 1: return 1
return n*factorial(n-1)
"""
variable n string 10
python factorial invoke
print "Factorial of $n = ${fact}"
Factorial of 10 = 3628800
variable n string 20
python factorial invoke
print "Factorial of $n = ${fact}"
Factorial of 20 = 2432902008176640000
# 3rd Python function
# example of calling back to LAMMPS and writing a run loop in Python
variable cut string 0.0
python loop input 4 10 1.0 -4.0 SELF format iffp file funcs.py
python loop invoke
pair_style lj/cut ${cut}
pair_style lj/cut 1.0
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.3
Memory usage per processor = 2.63679 Mbytes
Step Temp E_pair E_mol TotEng Press
10 1.1259767 0.016557378 0 1.7051002 1.2784679
20 0.87608998 0.39300382 0 1.7068103 6.0488236
Loop time of 0.00155491 on 4 procs for 10 steps with 4000 atoms
Pair time (%) = 0.000403821 (25.9708)
Neigh time (%) = 0.00049901 (32.0926)
Comm time (%) = 0.000386357 (24.8476)
Outpt time (%) = 2.87294e-05 (1.84766)
Other time (%) = 0.000236988 (15.2413)
Nlocal: 1000 ave 1015 max 987 min
Histogram: 1 0 0 1 0 1 0 0 0 1
Nghost: 943 ave 956 max 928 min
Histogram: 1 0 0 0 1 0 1 0 0 1
Neighs: 4431.75 ave 4498 max 4325 min
Histogram: 1 0 0 0 0 0 1 0 1 1
Total # of neighbors = 17727
Ave neighs/atom = 4.43175
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.1
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.4
Memory usage per processor = 2.63679 Mbytes
Step Temp E_pair E_mol TotEng Press
20 0.87608998 -0.33042884 0 0.9833776 8.5817494
30 1.0155079 -0.83166219 0 0.69121891 7.9905553
Loop time of 0.00199097 on 4 procs for 10 steps with 4000 atoms
Pair time (%) = 0.000789523 (39.6551)
Neigh time (%) = 0.000541985 (27.2221)
Comm time (%) = 0.000392973 (19.7377)
Outpt time (%) = 2.49147e-05 (1.25138)
Other time (%) = 0.000241578 (12.1336)
Nlocal: 1000 ave 1019 max 983 min
Histogram: 1 0 1 0 0 0 1 0 0 1
Nghost: 945.25 ave 962 max 925 min
Histogram: 1 0 0 0 1 0 0 1 0 1
Neighs: 5259 ave 5343 max 5125 min
Histogram: 1 0 0 0 0 1 0 0 0 2
Total # of neighbors = 21036
Ave neighs/atom = 5.259
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.2
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.5
Memory usage per processor = 2.63679 Mbytes
Step Temp E_pair E_mol TotEng Press
30 1.0155079 -2.0616558 0 -0.53877467 7.6238572
40 1.0490928 -2.1868324 0 -0.61358669 7.2084131
Loop time of 0.00233454 on 4 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00106812 (45.7528)
Neigh time (%) = 0.000583589 (24.9981)
Comm time (%) = 0.000406563 (17.4152)
Outpt time (%) = 2.41399e-05 (1.03403)
Other time (%) = 0.000252128 (10.7999)
Nlocal: 1000 ave 1013 max 984 min
Histogram: 1 0 0 1 0 0 0 0 1 1
Nghost: 1023 ave 1035 max 1005 min
Histogram: 1 0 0 0 0 1 0 0 0 2
Neighs: 6023.75 ave 6093 max 5953 min
Histogram: 2 0 0 0 0 0 0 0 0 2
Total # of neighbors = 24095
Ave neighs/atom = 6.02375
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.3
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.6
Memory usage per processor = 2.63679 Mbytes
Step Temp E_pair E_mol TotEng Press
40 1.0490928 -3.0667608 0 -1.493515 6.2796311
50 1.0764484 -3.1173704 0 -1.5031014 6.0850409
Loop time of 0.00265193 on 4 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00123417 (46.5387)
Neigh time (%) = 0.000687182 (25.9125)
Comm time (%) = 0.000449538 (16.9514)
Outpt time (%) = 2.40803e-05 (0.908028)
Other time (%) = 0.000256956 (9.68938)
Nlocal: 1000 ave 1013 max 974 min
Histogram: 1 0 0 0 0 0 0 1 0 2
Nghost: 1184.75 ave 1200 max 1165 min
Histogram: 1 0 0 0 1 0 0 0 1 1
Neighs: 6784.25 ave 6922 max 6577 min
Histogram: 1 0 0 0 0 1 0 0 1 1
Total # of neighbors = 27137
Ave neighs/atom = 6.78425
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.4
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.7
Memory usage per processor = 2.63679 Mbytes
Step Temp E_pair E_mol TotEng Press
50 1.0764484 -3.6112241 0 -1.9969552 5.4223348
60 1.1101013 -3.6616014 0 -1.9968657 5.2348251
Loop time of 0.00285125 on 4 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00141847 (49.7491)
Neigh time (%) = 0.000675321 (23.6851)
Comm time (%) = 0.000490129 (17.19)
Outpt time (%) = 2.77162e-05 (0.972071)
Other time (%) = 0.000239611 (8.40371)
Nlocal: 1000 ave 1016 max 981 min
Histogram: 1 0 0 0 1 0 1 0 0 1
Nghost: 1402.25 ave 1408 max 1390 min
Histogram: 1 0 0 0 0 0 0 1 0 2
Neighs: 7721.75 ave 7798 max 7615 min
Histogram: 1 0 0 1 0 0 0 0 0 2
Total # of neighbors = 30887
Ave neighs/atom = 7.72175
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.5
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.8
Memory usage per processor = 2.63679 Mbytes
Step Temp E_pair E_mol TotEng Press
60 1.1101013 -3.9655053 0 -2.3007696 4.7849008
70 1.1122144 -3.9657095 0 -2.297805 4.8014106
Loop time of 0.00325108 on 4 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00161421 (49.6517)
Neigh time (%) = 0.000730813 (22.4791)
Comm time (%) = 0.000600517 (18.4713)
Outpt time (%) = 2.87294e-05 (0.88369)
Other time (%) = 0.000276804 (8.51423)
Nlocal: 1000 ave 1022 max 982 min
Histogram: 1 0 0 1 0 1 0 0 0 1
Nghost: 1595.75 ave 1604 max 1588 min
Histogram: 1 0 0 1 0 0 1 0 0 1
Neighs: 8989.75 ave 9204 max 8776 min
Histogram: 1 0 0 0 1 1 0 0 0 1
Total # of neighbors = 35959
Ave neighs/atom = 8.98975
Neighbor list builds = 1
Dangerous builds = 0
pair_style lj/cut ${cut}
pair_style lj/cut 1.6
pair_coeff * * 1.0 1.0
run 10
Neighbor list info ...
1 neighbor list requests
update every 1 steps, delay 0 steps, check yes
master list distance cutoff = 1.9
Memory usage per processor = 2.63679 Mbytes
Step Temp E_pair E_mol TotEng Press
70 1.1122144 -4.1752688 0 -2.5073643 4.4755409
80 1.117224 -4.1831357 0 -2.5077187 4.446079
Loop time of 0.00360203 on 4 procs for 10 steps with 4000 atoms
Pair time (%) = 0.00191045 (53.0381)
Neigh time (%) = 0.000787675 (21.8676)
Comm time (%) = 0.000629485 (17.4758)
Outpt time (%) = 2.46167e-05 (0.683413)
Other time (%) = 0.000249803 (6.93507)
Nlocal: 1000 ave 1013 max 987 min
Histogram: 1 0 1 0 0 0 0 1 0 1
Nghost: 1706 ave 1720 max 1693 min
Histogram: 2 0 0 0 0 0 0 0 1 1
Neighs: 10809.8 ave 10831 max 10761 min
Histogram: 1 0 0 0 0 0 0 0 1 2
Total # of neighbors = 43239
Ave neighs/atom = 10.8097
Neighbor list builds = 1
Dangerous builds = 0

View File

@ -37,6 +37,8 @@ meam modified embedded atom method (MEAM) potential, MEAM package
from Greg Wagner (Sandia) from Greg Wagner (Sandia)
molfile hooks to VMD molfile plugins, used by the USER-MOLFILE package molfile hooks to VMD molfile plugins, used by the USER-MOLFILE package
from Axel Kohlmeyer (Temple U) and the VMD development team from Axel Kohlmeyer (Temple U) and the VMD development team
python hooks to the system Python library, used by the PYTHON package
from the LAMMPS development team
qmmm quantum mechanics/molecular mechanics coupling interface qmmm quantum mechanics/molecular mechanics coupling interface
from Axel Kohlmeyer (Temple U) from Axel Kohlmeyer (Temple U)
quip interface to QUIP/libAtoms framework, USER-QUIP package quip interface to QUIP/libAtoms framework, USER-QUIP package

View File

@ -0,0 +1,6 @@
# Settings that the LAMMPS build will import when this package library is used
# See the README file for more explanation
python_SYSINC = -I/usr/local/include/python2.7
python_SYSLIB = -lpython2.7 -lnsl -ldl -lreadline -ltermcap -lpthread -lutil -lm
python_SYSPATH =

View File

@ -0,0 +1,6 @@
# Settings that the LAMMPS build will import when this package library is used
# See the README file for more explanation
python_SYSINC = -I/usr/local/include/python2.7
python_SYSLIB = -lpython2.7 -lnsl -ldl -lreadline -ltermcap -lpthread -lutil -lm
python_SYSPATH =

58
lib/python/README Normal file
View File

@ -0,0 +1,58 @@
The Makefile.lammps file in this directory is used when building
LAMMPS with its PYTHON package installed. The file has several
settings needed to compile and link LAMMPS with the Python library.
You should choose a Makefile.lammps.* file compatible with your system
and your version of Python, and copy it to Makefile.lammps before
building LAMMPS itself. You may need to edit one of the provided
files to match your system.
Note that is not currently possible to use the PYTHON package with
Python 3, only with Python 2. The C API changed from Python 2 to 3
and the LAMMPS code is not compatible with both.
If you create a new Makefile.lammps file suitable for some version of
Python on some system, that is not a match to one of the provided
Makefile.lammps.* files, you can send it to the developers, and we can
include it in the distribution for others to use.
To illustrate, these are example settings from the
Makefile.lammps.python2.7 file:
python_SYSINC = -I/usr/local/include/python2.7
python_SYSLIB = -lpython2.7 -lnsl -ldl -lreadline -ltermcap -lpthread -lutil -lm
python_SYSPATH =
python_SYSINC refers to the directory where Python's Python.h file is
found. LAMMPS includes this file.
python_SYSLIB refers to the libraries needed to link to from an
application (LAMMPS in this case) to "embed" Python in the
application. The Python library itself is listed (-lpython2.7) are
are several system libraries needed by Python.
python_SYSPATH = refers to the path (e.g. -L/usr/local/lib) where the
Python library can be found. You may not need this setting if the
path is already included in your LD_LIBRARY_PATH environment variable.
-------------------------
Note that the trickiest issue to figure out for inclusion in
Makefile.lammps is what system libraries are needed by your Python to
run in embedded mode on your machine.
Here is what this Python doc page says about it:
https://docs.python.org/2/extending/embedding.html#compiling-and-linking-under-unix-like-systems
"It is not necessarily trivial to find the right flags to pass to your
compiler (and linker) in order to embed the Python interpreter into
your application, particularly because Python needs to load library
modules implemented as C dynamic extensions (.so files) linked against
it.
To find out the required compiler and linker flags, you can execute
the pythonX.Y-config script which is generated as part of the
installation process (a python-config script may also be available)."
It then gives examples of how to use the pythonX.Y-config script
and further instructions for what to do if that doesn't work.

View File

@ -1,6 +1,6 @@
This directory contains Python code which wraps LAMMPS as a library This directory contains Python code which wraps LAMMPS as a library
and allows the LAMMPS library interface to be invoked from Python, and allows the LAMMPS library interface to be invoked from Python,
either from a script or interactively. either from a Python script or using Python interactively.
Details on the Python interface to LAMMPS and how to build LAMMPS as a Details on the Python interface to LAMMPS and how to build LAMMPS as a
shared library, for use with Python, are given in shared library, for use with Python, are given in
@ -16,16 +16,22 @@ variables in your shell script. Or you can run the python/install.py
script directly to give you more control over where the two relevant script directly to give you more control over where the two relevant
files are installed. See doc/Section_python.html for details. files are installed. See doc/Section_python.html for details.
You can then launch Python and instantiate an instance of LAMMPS: You should then be able to launch Python and instantiate an instance
of LAMMPS:
% python % python
>>> from lammps import lammps >>> from lammps import lammps
>>> lmp = lammps() >>> lmp = lammps()
If that gives no errors, you have succesfully wrapped LAMMPS with If that gives no errors, you have succesfully wrapped LAMMPS with
Python. See doc/Section_python.html#py_5 for tests you can then use Python. See doc/Section_python.html#py_7 for tests you can then use
to run LAMMPS both in serial or parallel thru Python. to run LAMMPS both in serial or parallel thru Python.
Note that you can also invoke Python code from within a LAMMPS input
script, using the "python" command. See the doc/python.html doc page
for details. The Python code you invoke can also call back to LAMMPS
using the same interface described here for wrapping LAMMPS.
------------------------------------------------------------------- -------------------------------------------------------------------
Once you have successfully wrapped LAMMPS, you can run the Python Once you have successfully wrapped LAMMPS, you can run the Python

View File

@ -43,14 +43,14 @@ endif
PACKAGE = asphere body class2 colloid coreshell dipole fld gpu granular kim \ PACKAGE = asphere body class2 colloid coreshell dipole fld gpu granular kim \
kokkos kspace manybody mc meam misc molecule mpiio opt peri poems \ kokkos kspace manybody mc meam misc molecule mpiio opt peri poems \
qeq reax replica rigid shock snap srd voronoi xtc python qeq reax replica rigid shock snap srd voronoi xtc
PACKUSER = user-atc user-awpmd user-cg-cmm user-colvars \ PACKUSER = user-atc user-awpmd user-cg-cmm user-colvars \
user-cuda user-eff user-fep user-intel user-lb user-misc \ user-cuda user-eff user-fep user-intel user-lb user-misc \
user-molfile user-omp user-phonon user-qmmm user-quip \ user-molfile user-omp user-phonon user-qmmm user-quip \
user-reaxc user-sph user-reaxc user-sph
PACKLIB = gpu kim kokkos meam poems reax voronoi \ PACKLIB = gpu kim kokkos meam poems python reax voronoi \
user-atc user-awpmd user-colvars user-cuda user-molfile \ user-atc user-awpmd user-colvars user-cuda user-molfile \
user-qmmm user-quip user-qmmm user-quip

69
src/PYTHON/Install.sh Executable file
View File

@ -0,0 +1,69 @@
# Install/unInstall package files in LAMMPS
# mode = 0/1/2 for uninstall/install/update
mode=$1
# arg1 = file, arg2 = file it depends on
action () {
if (test $mode = 0) then
rm -f ../$1
elif (! cmp -s $1 ../$1) then
if (test -z "$2" || test -e ../$2) then
cp $1 ..
if (test $mode = 2) then
echo " updating src/$1"
fi
fi
elif (test -n "$2") then
if (test ! -e ../$2) then
rm -f ../$1
fi
fi
}
# force rebuild of files with LMP_KOKKOS switch
# also variable so its *.d dependence on changed python_wrapper.h is rebuilt
touch ../python_wrapper.h
touch ../variable.cpp
# all package files with no dependencies
for file in *.cpp *.h; do
action $file
done
# edit 2 Makefile.package files to include/exclude package info
if (test $1 = 1) then
if (test -e ../Makefile.package) then
sed -i -e 's/[^ \t]*python[^ \t]* //' ../Makefile.package
sed -i -e 's/[^ \t]*PYTHON[^ \t]* //g' ../Makefile.package
sed -i -e 's|^PKG_INC =[ \t]*|&-DLMP_PYTHON |' ../Makefile.package
sed -i -e 's|^PKG_SYSINC =[ \t]*|&$(python_SYSINC) |' ../Makefile.package
sed -i -e 's|^PKG_SYSLIB =[ \t]*|&$(python_SYSLIB) |' ../Makefile.package
sed -i -e 's|^PKG_SYSPATH =[ \t]*|&$(python_SYSPATH) |' ../Makefile.package
fi
if (test -e ../Makefile.package.settings) then
sed -i -e '/^include.*python.*$/d' ../Makefile.package.settings
# multiline form needed for BSD sed on Macs
sed -i -e '4 i \
include ..\/..\/lib\/python\/Makefile.lammps
' ../Makefile.package.settings
fi
elif (test $1 = 0) then
if (test -e ../Makefile.package) then
sed -i -e 's/[^ \t]*python[^ \t]* //' ../Makefile.package
sed -i -e 's/[^ \t]*PYTHON[^ \t]* //g' ../Makefile.package
fi
if (test -e ../Makefile.package.settings) then
sed -i -e '/^include.*python.*$/d' ../Makefile.package.settings
fi
fi

400
src/PYTHON/python.cpp Normal file
View File

@ -0,0 +1,400 @@
/* ----------------------------------------------------------------------
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.
------------------------------------------------------------------------- */
#include "Python.h"
#include "python.h"
#include "force.h"
#include "input.h"
#include "variable.h"
#include "memory.h"
#include "error.h"
using namespace LAMMPS_NS;
enum{NONE,INT,DOUBLE,STRING,PTR};
#define VALUELENGTH 64 // also in variable.cpp
/* ---------------------------------------------------------------------- */
Python::Python(LAMMPS *lmp) : Pointers(lmp)
{
python_exists = 1;
pyMain = NULL;
// pfuncs stores interface info for each Python function
nfunc = 0;
pfuncs = NULL;
}
/* ---------------------------------------------------------------------- */
Python::~Python()
{
// clean up
for (int i = 0; i < nfunc; i++) {
delete [] pfuncs[i].name;
deallocate(i);
PyObject *pFunc = (PyObject *) pfuncs[i].pFunc;
Py_XDECREF(pFunc);
}
// shutdown Python interpreter
if (pyMain) Py_Finalize();
memory->sfree(pfuncs);
}
/* ---------------------------------------------------------------------- */
void Python::command(int narg, char **arg)
{
if (narg < 2) error->all(FLERR,"Invalid python command");
// if invoke is only keyword, invoke the previously defined function
if (narg == 2 && strcmp(arg[1],"invoke") == 0) {
int ifunc = find(arg[0]);
if (ifunc < 0) error->all(FLERR,"Python invoke of undefined function");
char *str = NULL;
if (noutput) {
str = input->variable->pythonstyle(pfuncs[ifunc].ovarname,
pfuncs[ifunc].name);
if (!str)
error->all(FLERR,"Python variable does not match Python function");
}
invoke_function(ifunc,str);
return;
}
// parse optional args, invoke is not allowed in this mode
ninput = noutput = 0;
istr = NULL;
ostr = NULL;
format = NULL;
char *pyfile = NULL;
char *herestr = NULL;
int existflag = 0;
int iarg = 1;
while (iarg < narg) {
if (strcmp(arg[iarg],"input") == 0) {
if (iarg+2 > narg) error->all(FLERR,"Invalid python command");
ninput = force->inumeric(FLERR,arg[iarg+1]);
if (ninput < 0) error->all(FLERR,"Invalid python command");
iarg += 2;
istr = new char*[ninput];
if (iarg+ninput > narg) error->all(FLERR,"Invalid python command");
for (int i = 0; i < ninput; i++) istr[i] = arg[iarg+i];
iarg += ninput;
} else if (strcmp(arg[iarg],"return") == 0) {
if (iarg+2 > narg) error->all(FLERR,"Invalid python command");
noutput = 1;
ostr = arg[iarg+1];
iarg += 2;
} else if (strcmp(arg[iarg],"format") == 0) {
if (iarg+2 > narg) error->all(FLERR,"Invalid python command");
int n = strlen(arg[iarg+1]) + 1;
format = new char[n];
strcpy(format,arg[iarg+1]);
iarg += 2;
} else if (strcmp(arg[iarg],"file") == 0) {
if (iarg+2 > narg) error->all(FLERR,"Invalid python command");
int n = strlen(arg[iarg+1]) + 1;
pyfile = new char[n];
strcpy(pyfile,arg[iarg+1]);
iarg += 2;
} else if (strcmp(arg[iarg],"here") == 0) {
if (iarg+2 > narg) error->all(FLERR,"Invalid python command");
herestr = arg[iarg+1];
iarg += 2;
} else if (strcmp(arg[iarg],"exists") == 0) {
existflag = 1;
iarg++;
} else error->all(FLERR,"Invalid python command");
}
if (pyfile && herestr) error->all(FLERR,"Invalid python command");
if (pyfile && existflag) error->all(FLERR,"Invalid python command");
if (herestr && existflag) error->all(FLERR,"Invalid python command");
// create or overwrite entry in pfuncs vector with name = arg[0]
int ifunc = create_entry(arg[0]);
// one-time intitialization of Python interpreter
// Py_SetArgv() enables finding of *.py module files in current dir
// only needed for module load, not for direct file read into __main__
// pymain stores pointer to main module
if (pyMain == NULL) {
if (Py_IsInitialized())
error->all(FLERR,"Cannot embed Python when also "
"extending Python with LAMMPS");
Py_Initialize();
//char *arg = (char *) "./lmp";
//PySys_SetArgv(1,&arg);
//PyObject *pName = PyString_FromString("__main__");
//if (!pName) error->all(FLERR,"Bad pName");
//PyObject *pModule = PyImport_Import(pName);
//Py_DECREF(pName);
PyObject *pModule = PyImport_AddModule("__main__");
if (!pModule) error->all(FLERR,"Could not initialize embedded Python");
//if (!pModule) error->one(FLERR,"Could not initialize embedded Python");
pyMain = (void *) pModule;
}
// send Python code to Python interpreter
// file: read the file via PyRun_SimpleFile()
// here: process the here string directly
// exist: do nothing, assume code has already been run
if (pyfile) {
FILE *fp = fopen(pyfile,"r");
if (fp == NULL) error->all(FLERR,"Could not open Python file");
int err = PyRun_SimpleFile(fp,pyfile);
if (err) error->all(FLERR,"Could not process Python file");
} else if (herestr) {
int err = PyRun_SimpleString(herestr);
if (err) error->all(FLERR,"Could not process Python string");
}
// pFunc = function object for requested function
PyObject *pModule = (PyObject *) pyMain;
PyObject *pFunc = PyObject_GetAttrString(pModule,pfuncs[ifunc].name);
if (!pFunc) error->all(FLERR,"Could not find Python function");
if (!PyCallable_Check(pFunc))
error->all(FLERR,"Python function is not callable");
pfuncs[ifunc].pFunc = (void *) pFunc;
// clean-up input storage
delete [] istr;
delete [] format;
delete [] pyfile;
}
/* ------------------------------------------------------------------ */
void Python::invoke_function(int ifunc, char *result)
{
PyObject *pValue;
char *str;
PyObject *pFunc = (PyObject *) pfuncs[ifunc].pFunc;
// create Python tuple of input arguments
int ninput = pfuncs[ifunc].ninput;
PyObject *pArgs = PyTuple_New(ninput);
if (!pArgs) error->all(FLERR,"Could not create Python function arguments");
for (int i = 0; i < ninput; i++) {
int itype = pfuncs[ifunc].itype[i];
if (itype == INT) {
if (pfuncs[ifunc].ivarflag[i]) {
str = input->variable->retrieve(pfuncs[ifunc].svalue[i]);
if (!str)
error->all(FLERR,"Could not evaluate Python function input variable");
pValue = PyInt_FromLong(atoi(str));
} else pValue = PyInt_FromLong(pfuncs[ifunc].ivalue[i]);
} else if (itype == DOUBLE) {
if (pfuncs[ifunc].ivarflag[i]) {
str = input->variable->retrieve(pfuncs[ifunc].svalue[i]);
if (!str)
error->all(FLERR,"Could not evaluate Python function input variable");
pValue = PyFloat_FromDouble(atof(str));
} else pValue = PyFloat_FromDouble(pfuncs[ifunc].dvalue[i]);
} else if (itype == STRING) {
if (pfuncs[ifunc].ivarflag[i]) {
str = input->variable->retrieve(pfuncs[ifunc].svalue[i]);
if (!str)
error->all(FLERR,"Could not evaluate Python function input variable");
pValue = PyString_FromString(str);
} else pValue = PyString_FromString(pfuncs[ifunc].svalue[i]);
} else if (itype == PTR) {
pValue = PyCObject_FromVoidPtr((void *) lmp,NULL);
}
PyTuple_SetItem(pArgs,i,pValue);
}
// call the Python function
// error check with one() since only some procs may fail
pValue = PyObject_CallObject(pFunc,pArgs);
if (!pValue) error->one(FLERR,"Python function evaluation failed");
Py_DECREF(pArgs);
// function returned a value
// assign it to result string stored by python-style variable
if (pfuncs[ifunc].noutput) {
int otype = pfuncs[ifunc].otype;
if (otype == INT) {
sprintf(result,"%ld",PyInt_AsLong(pValue));
} else if (otype == DOUBLE) {
sprintf(result,"%.15g",PyFloat_AsDouble(pValue));
} else if (otype == STRING) {
char *pystr = PyString_AsString(pValue);
strncpy(result,pystr,VALUELENGTH-1);
}
Py_DECREF(pValue);
}
}
/* ------------------------------------------------------------------ */
int Python::find(char *name)
{
for (int i = 0; i < nfunc; i++)
if (strcmp(name,pfuncs[i].name) == 0) return i;
return -1;
}
/* ------------------------------------------------------------------ */
int Python::variable_match(char *name, char *varname, int numeric)
{
int ifunc = find(name);
if (ifunc < 0) return -1;
if (pfuncs[ifunc].noutput == 0) return -1;
if (strcmp(pfuncs[ifunc].ovarname,varname) != 0) return -1;
if (numeric && pfuncs[ifunc].otype == STRING) return -1;
return ifunc;
}
/* ------------------------------------------------------------------ */
int Python::create_entry(char *name)
{
// ifunc = index to entry by name in pfuncs vector, can be old or new
// free old vectors if overwriting old pfunc
int ifunc = find(name);
if (ifunc < 0) {
ifunc = nfunc;
nfunc++;
pfuncs = (PyFunc *)
memory->srealloc(pfuncs,nfunc*sizeof(struct PyFunc),"python:pfuncs");
int n = strlen(name) + 1;
pfuncs[ifunc].name = new char[n];
strcpy(pfuncs[ifunc].name,name);
} else deallocate(ifunc);
pfuncs[ifunc].ninput = ninput;
pfuncs[ifunc].noutput = noutput;
if (!format && ninput+noutput)
error->all(FLERR,"Invalid python command");
else if (format && strlen(format) != ninput+noutput)
error->all(FLERR,"Invalid python command");
// process inputs as values or variables
pfuncs[ifunc].itype = new int[ninput];
pfuncs[ifunc].ivarflag = new int[ninput];
pfuncs[ifunc].ivalue = new int[ninput];
pfuncs[ifunc].dvalue = new double[ninput];
pfuncs[ifunc].svalue = new char*[ninput];
for (int i = 0; i < ninput; i++) {
pfuncs[ifunc].svalue[i] = NULL;
char type = format[i];
if (type == 'i') {
pfuncs[ifunc].itype[i] = INT;
if (strstr(istr[i],"v_") == istr[i]) {
pfuncs[ifunc].ivarflag[i] = 1;
int n = strlen(&istr[i][2]) + 1;
pfuncs[ifunc].svalue[i] = new char[n];
strcpy(pfuncs[ifunc].svalue[i],&istr[i][2]);
} else {
pfuncs[ifunc].ivarflag[i] = 0;
pfuncs[ifunc].ivalue[i] = force->inumeric(FLERR,istr[i]);
}
} else if (type == 'f') {
pfuncs[ifunc].itype[i] = DOUBLE;
if (strstr(istr[i],"v_") == istr[i]) {
pfuncs[ifunc].ivarflag[i] = 1;
int n = strlen(&istr[i][2]) + 1;
pfuncs[ifunc].svalue[i] = new char[n];
strcpy(pfuncs[ifunc].svalue[i],&istr[i][2]);
} else {
pfuncs[ifunc].ivarflag[i] = 0;
pfuncs[ifunc].dvalue[i] = force->numeric(FLERR,istr[i]);
}
} else if (type == 's') {
pfuncs[ifunc].itype[i] = STRING;
if (strstr(istr[i],"v_") == istr[i]) {
pfuncs[ifunc].ivarflag[i] = 1;
int n = strlen(&istr[i][2]) + 1;
pfuncs[ifunc].svalue[i] = new char[n];
strcpy(pfuncs[ifunc].svalue[i],&istr[i][2]);
} else {
pfuncs[ifunc].ivarflag[i] = 0;
int n = strlen(istr[i]) + 1;
pfuncs[ifunc].svalue[i] = new char[n];
strcpy(pfuncs[ifunc].svalue[i],istr[i]);
}
} else if (type == 'p') {
pfuncs[ifunc].ivarflag[i] = 0;
pfuncs[ifunc].itype[i] = PTR;
if (strcmp(istr[i],"SELF") != 0)
error->all(FLERR,"Invalid python command");
} else error->all(FLERR,"Invalid python command");
}
// process output as value or variable
pfuncs[ifunc].ovarname = NULL;
if (!noutput) return ifunc;
char type = format[ninput];
if (type == 'i') pfuncs[ifunc].otype = INT;
else if (type == 'f') pfuncs[ifunc].otype = DOUBLE;
else if (type == 's') pfuncs[ifunc].otype = STRING;
else error->all(FLERR,"Invalid python command");
if (strstr(ostr,"v_") != ostr) error->all(FLERR,"Invalid python command");
int n = strlen(&ostr[2]) + 1;
pfuncs[ifunc].ovarname = new char[n];
strcpy(pfuncs[ifunc].ovarname,&ostr[2]);
return ifunc;
}
/* ------------------------------------------------------------------ */
void Python::deallocate(int i)
{
delete [] pfuncs[i].itype;
delete [] pfuncs[i].ivarflag;
delete [] pfuncs[i].ivalue;
delete [] pfuncs[i].dvalue;
for (int j = 0; j < pfuncs[i].ninput; j++)
delete [] pfuncs[i].svalue[j];
delete [] pfuncs[i].svalue;
delete [] pfuncs[i].ovarname;
}

59
src/PYTHON/python.h Normal file
View File

@ -0,0 +1,59 @@
/* -*- 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.
------------------------------------------------------------------------- */
#ifndef LMP_PYTHON_H
#define LMP_PYTHON_H
#include "pointers.h"
namespace LAMMPS_NS {
class Python : protected Pointers {
public:
int python_exists;
Python(class LAMMPS *);
~Python();
void command(int, char **);
void invoke_function(int, char *);
int find(char *);
int variable_match(char *, char *, int);
private:
int ninput,noutput;
char **istr;
char *ostr,*format;
void *pyMain;
struct PyFunc {
char *name;
int ninput,noutput;
int *itype,*ivarflag;
int *ivalue;
double *dvalue;
char **svalue;
int otype;
char *ovarname;
void *pFunc;
};
PyFunc *pfuncs;
int nfunc;
int create_entry(char *);
void deallocate(int);
};
}
#endif

View File

@ -161,17 +161,33 @@ void Input::file()
m = 0; m = 0;
while (1) { while (1) {
if (maxline-m < 2) reallocate(line,maxline,0); if (maxline-m < 2) reallocate(line,maxline,0);
// end of file reached, so break
// n == 0 if nothing read, else n = line with str terminator
if (fgets(&line[m],maxline-m,infile) == NULL) { if (fgets(&line[m],maxline-m,infile) == NULL) {
if (m) n = strlen(line) + 1; if (m) n = strlen(line) + 1;
else n = 0; else n = 0;
break; break;
} }
// continue if last char read was not a newline
// could happen if line is very long
m = strlen(line); m = strlen(line);
if (line[m-1] != '\n') continue; if (line[m-1] != '\n') continue;
// continue reading if final printable char is & char
// or if odd number of triple quotes
// else break with n = line with str terminator
m--; m--;
while (m >= 0 && isspace(line[m])) m--; while (m >= 0 && isspace(line[m])) m--;
if (m < 0 || line[m] != '&') { if (m < 0 || line[m] != '&') {
if (numtriple(line) % 2) {
m += 2;
continue;
}
line[m+1] = '\0'; line[m+1] = '\0';
n = m+2; n = m+2;
break; break;
@ -302,11 +318,11 @@ char *Input::one(const char *single)
/* ---------------------------------------------------------------------- /* ----------------------------------------------------------------------
parse copy of command line by inserting string terminators parse copy of command line by inserting string terminators
strip comment = all chars from # on strip comment = all chars from # on
replace all $ via variable substitution replace all $ via variable substitution except within quotes
command = first word command = first word
narg = # of args narg = # of args
arg[] = individual args arg[] = individual args
treat text between single/double quotes as one arg treat text between single/double/triple quotes as one arg via nextword()
------------------------------------------------------------------------- */ ------------------------------------------------------------------------- */
void Input::parse() void Input::parse()
@ -318,17 +334,32 @@ void Input::parse()
strcpy(copy,line); strcpy(copy,line);
// strip any # comment by replacing it with 0 // strip any # comment by replacing it with 0
// do not strip # inside single/double quotes // do not strip from a # inside single/double/triple quotes
// quoteflag = 1,2,3 when encounter first single/double,triple quote
char quote = '\0'; // quoteflag = 0 when encounter matching single/double,triple quote
int quoteflag = 0;
char *ptr = copy; char *ptr = copy;
while (*ptr) { while (*ptr) {
if (*ptr == '#' && !quote) { if (*ptr == '#' && !quoteflag) {
*ptr = '\0'; *ptr = '\0';
break; break;
} }
if (*ptr == quote) quote = '\0'; if (quoteflag == 0) {
else if (*ptr == '"' || *ptr == '\'') quote = *ptr; if (strstr(ptr,"\"\"\"") == ptr) {
quoteflag = 3;
ptr += 2;
}
else if (*ptr == '"') quoteflag = 2;
else if (*ptr == '\'') quoteflag = 1;
} else {
if (quoteflag == 3 && strstr(ptr,"\"\"\"") == ptr) {
quoteflag = 0;
ptr += 2;
}
else if (quoteflag == 2 && *ptr == '"') quoteflag = 0;
else if (quoteflag == 1 && *ptr == '\'') quoteflag = 0;
}
ptr++; ptr++;
} }
@ -345,7 +376,7 @@ void Input::parse()
// point arg[] at each subsequent arg in copy string // point arg[] at each subsequent arg in copy string
// nextword() inserts string terminators into copy string to delimit args // nextword() inserts string terminators into copy string to delimit args
// nextword() treats text between single/double quotes as one arg // nextword() treats text between single/double/triple quotes as one arg
narg = 0; narg = 0;
ptr = next; ptr = next;
@ -365,31 +396,53 @@ void Input::parse()
find next word in str find next word in str
insert 0 at end of word insert 0 at end of word
ignore leading whitespace ignore leading whitespace
treat text between single/double quotes as one arg treat text between single/double/triple quotes as one arg
matching quote must be followed by whitespace char if not end of string matching quote must be followed by whitespace char if not end of string
strip quotes from returned word strip quotes from returned word
return ptr to start of word return ptr to start of word or NULL if no word in string
return next = ptr after word or NULL if word ended with 0 also return next = ptr after word
return NULL if no word in string
------------------------------------------------------------------------- */ ------------------------------------------------------------------------- */
char *Input::nextword(char *str, char **next) char *Input::nextword(char *str, char **next)
{ {
char *start,*stop; char *start,*stop;
// start = first non-whitespace char
start = &str[strspn(str," \t\n\v\f\r")]; start = &str[strspn(str," \t\n\v\f\r")];
if (*start == '\0') return NULL; if (*start == '\0') return NULL;
if (*start == '"' || *start == '\'') { // if start is single/double/triple quote:
// start = first char beyond quote
// stop = first char of matching quote
// next = first char beyond matching quote
// next must be NULL or whitespace
// if start is not single/double/triple quote:
// stop = first whitespace char after start
// next = char after stop, or stop itself if stop is NULL
if (strstr(start,"\"\"\"") == start) {
stop = strstr(&start[3],"\"\"\"");
if (!stop) error->all(FLERR,"Unbalanced quotes in input line");
start += 3;
*next = stop+3;
if (**next && !isspace(**next))
error->all(FLERR,"Input line quote not followed by whitespace");
} else if (*start == '"' || *start == '\'') {
stop = strchr(&start[1],*start); stop = strchr(&start[1],*start);
if (!stop) error->all(FLERR,"Unbalanced quotes in input line"); if (!stop) error->all(FLERR,"Unbalanced quotes in input line");
if (stop[1] && !isspace(stop[1]))
error->all(FLERR,"Input line quote not followed by whitespace");
start++; start++;
} else stop = &start[strcspn(start," \t\n\v\f\r")]; *next = stop+1;
if (**next && !isspace(**next))
if (*stop == '\0') *next = NULL; error->all(FLERR,"Input line quote not followed by whitespace");
else *next = stop+1; } else {
stop = &start[strcspn(start," \t\n\v\f\r")];
if (*stop == '\0') *next = stop;
else *next = stop+1;
}
// set stop to NULL to terminate word
*stop = '\0'; *stop = '\0';
return start; return start;
} }
@ -405,7 +458,7 @@ void Input::substitute(char *&str, char *&str2, int &max, int &max2, int flag)
{ {
// use str2 as scratch space to expand str, then copy back to str // use str2 as scratch space to expand str, then copy back to str
// reallocate str and str2 as necessary // reallocate str and str2 as necessary
// do not replace $ inside single/double quotes // do not replace $ inside single/double/triple quotes
// var = pts at variable name, ended by NULL // var = pts at variable name, ended by NULL
// if $ is followed by '{', trailing '}' becomes NULL // if $ is followed by '{', trailing '}' becomes NULL
// else $x becomes x followed by NULL // else $x becomes x followed by NULL
@ -414,7 +467,7 @@ void Input::substitute(char *&str, char *&str2, int &max, int &max2, int flag)
int i,n,paren_count; int i,n,paren_count;
char immediate[256]; char immediate[256];
char *var,*value,*beyond; char *var,*value,*beyond;
char quote = '\0'; int quoteflag = 0;
char *ptr = str; char *ptr = str;
n = strlen(str) + 1; n = strlen(str) + 1;
@ -423,10 +476,11 @@ void Input::substitute(char *&str, char *&str2, int &max, int &max2, int flag)
char *ptr2 = str2; char *ptr2 = str2;
while (*ptr) { while (*ptr) {
// variable substitution // variable substitution
if (*ptr == '$' && !quote) { if (*ptr == '$' && !quoteflag) {
// value = ptr to expanded variable // value = ptr to expanded variable
// variable name between curly braces, e.g. ${a} // variable name between curly braces, e.g. ${a}
@ -441,7 +495,7 @@ void Input::substitute(char *&str, char *&str2, int &max, int &max2, int flag)
beyond = ptr + strlen(var) + 3; beyond = ptr + strlen(var) + 3;
value = variable->retrieve(var); value = variable->retrieve(var);
// immediate variable between parenthesis, e.g. $(1/2) // immediate variable between parenthesis, e.g. $(1/2)
} else if (*(ptr+1) == '(') { } else if (*(ptr+1) == '(') {
var = ptr+2; var = ptr+2;
@ -493,10 +547,29 @@ void Input::substitute(char *&str, char *&str2, int &max, int &max2, int flag)
continue; continue;
} }
if (*ptr == quote) quote = '\0'; // quoteflag = 1,2,3 when encounter first single/double,triple quote
else if (*ptr == '"' || *ptr == '\'') quote = *ptr; // quoteflag = 0 when encounter matching single/double,triple quote
// copy 2 extra triple quote chars into str2
if (quoteflag == 0) {
if (strstr(ptr,"\"\"\"") == ptr) {
quoteflag = 3;
*ptr2++ = *ptr++;
*ptr2++ = *ptr++;
}
else if (*ptr == '"') quoteflag = 2;
else if (*ptr == '\'') quoteflag = 1;
} else {
if (quoteflag == 3 && strstr(ptr,"\"\"\"") == ptr) {
quoteflag = 0;
*ptr2++ = *ptr++;
*ptr2++ = *ptr++;
}
else if (quoteflag == 2 && *ptr == '"') quoteflag = 0;
else if (quoteflag == 1 && *ptr == '\'') quoteflag = 0;
}
// copy current character into str2 // copy current character into str2
*ptr2++ = *ptr++; *ptr2++ = *ptr++;
@ -510,6 +583,21 @@ void Input::substitute(char *&str, char *&str2, int &max, int &max2, int flag)
strcpy(str,str2); strcpy(str,str2);
} }
/* ----------------------------------------------------------------------
return number of triple quotes in line
------------------------------------------------------------------------- */
int Input::numtriple(char *line)
{
int count = 0;
char *ptr = line;
while ((ptr = strstr(ptr,"\"\"\""))) {
ptr += 3;
count++;
}
return count;
}
/* ---------------------------------------------------------------------- /* ----------------------------------------------------------------------
rellocate a string rellocate a string
if n > 0: set max >= n in increments of DELTALINE if n > 0: set max >= n in increments of DELTALINE
@ -544,6 +632,7 @@ int Input::execute_command()
else if (!strcmp(command,"next")) next_command(); else if (!strcmp(command,"next")) next_command();
else if (!strcmp(command,"partition")) partition(); else if (!strcmp(command,"partition")) partition();
else if (!strcmp(command,"print")) print(); else if (!strcmp(command,"print")) print();
else if (!strcmp(command,"python")) python();
else if (!strcmp(command,"quit")) quit(); else if (!strcmp(command,"quit")) quit();
else if (!strcmp(command,"shell")) shell(); else if (!strcmp(command,"shell")) shell();
else if (!strcmp(command,"variable")) variable_command(); else if (!strcmp(command,"variable")) variable_command();
@ -980,6 +1069,13 @@ void Input::print()
/* ---------------------------------------------------------------------- */ /* ---------------------------------------------------------------------- */
void Input::python()
{
variable->python_command(narg,arg);
}
/* ---------------------------------------------------------------------- */
void Input::quit() void Input::quit()
{ {
if (narg) error->all(FLERR,"Illegal quit command"); if (narg) error->all(FLERR,"Illegal quit command");

View File

@ -58,6 +58,7 @@ class Input : protected Pointers {
void parse(); // parse an input text line void parse(); // parse an input text line
char *nextword(char *, char **); // find next word in string with quotes char *nextword(char *, char **); // find next word in string with quotes
int numtriple(char *); // count number of triple quotes
void reallocate(char *&, int &, int); // reallocate a char string void reallocate(char *&, int &, int); // reallocate a char string
int execute_command(); // execute a single command int execute_command(); // execute a single command
@ -71,6 +72,7 @@ class Input : protected Pointers {
void next_command(); void next_command();
void partition(); void partition();
void print(); void print();
void python();
void quit(); void quit();
void shell(); void shell();
void variable_command(); void variable_command();

View File

@ -357,6 +357,19 @@ void *lammps_extract_variable(void *ptr, char *name, char *group)
return NULL; return NULL;
} }
/* ----------------------------------------------------------------------
set the value of a STRING variable to str
return -1 if variable doesn't exist or not a STRING variable
return 0 for success
------------------------------------------------------------------------- */
int lammps_set_variable(void *ptr, char *name, char *str)
{
LAMMPS *lmp = (LAMMPS *) ptr;
int err = lmp->input->variable->set_string(name,str);
return err;
}
/* ---------------------------------------------------------------------- /* ----------------------------------------------------------------------
return the total number of atoms in the system return the total number of atoms in the system
useful before call to lammps_get_atoms() so can pre-allocate vector useful before call to lammps_get_atoms() so can pre-allocate vector
@ -365,6 +378,7 @@ void *lammps_extract_variable(void *ptr, char *name, char *group)
int lammps_get_natoms(void *ptr) int lammps_get_natoms(void *ptr)
{ {
LAMMPS *lmp = (LAMMPS *) ptr; LAMMPS *lmp = (LAMMPS *) ptr;
if (lmp->atom->natoms > MAXSMALLINT) return 0; if (lmp->atom->natoms > MAXSMALLINT) return 0;
int natoms = static_cast<int> (lmp->atom->natoms); int natoms = static_cast<int> (lmp->atom->natoms);
return natoms; return natoms;

View File

@ -37,6 +37,7 @@ void *lammps_extract_compute(void *, char *, int, int);
void *lammps_extract_fix(void *, char *, int, int, int, int); void *lammps_extract_fix(void *, char *, int, int, int, int);
void *lammps_extract_variable(void *, char *, char *); void *lammps_extract_variable(void *, char *, char *);
int lammps_set_variable(void *, char *, char *);
int lammps_get_natoms(void *); int lammps_get_natoms(void *);
void lammps_gather_atoms(void *, char *, int, int, void *); void lammps_gather_atoms(void *, char *, int, int, void *);
void lammps_scatter_atoms(void *, char *, int, int, void *); void lammps_scatter_atoms(void *, char *, int, int, void *);

47
src/python_wrapper.h Normal file
View File

@ -0,0 +1,47 @@
/* -*- 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.
------------------------------------------------------------------------- */
#ifndef LMP_PYTHON_WRAPPER_H
#define LMP_PYTHON_WRAPPER_H
// true interface to embedded Python
// used when PYTHON package is installed
#ifdef LMP_PYTHON
#include "python.h"
#else
// dummy interface to PYTHON
// needed for compiling when PYTHON is not installed
namespace LAMMPS_NS {
class Python {
public:
int python_exists;
Python(class LAMMPS *) {python_exists = 0;}
~Python() {}
void command(int, char **) {}
void invoke_function(int, char *) {}
int find(char *) {return -1;}
int variable_match(char *, char *, int) {return -1;}
};
}
#endif
#endif

View File

@ -28,14 +28,15 @@
#include "compute.h" #include "compute.h"
#include "fix.h" #include "fix.h"
#include "fix_store.h" #include "fix_store.h"
#include "force.h"
#include "output.h" #include "output.h"
#include "thermo.h" #include "thermo.h"
#include "random_mars.h" #include "random_mars.h"
#include "math_const.h" #include "math_const.h"
#include "atom_masks.h" #include "atom_masks.h"
#include "python_wrapper.h"
#include "memory.h" #include "memory.h"
#include "error.h" #include "error.h"
#include "force.h"
using namespace LAMMPS_NS; using namespace LAMMPS_NS;
using namespace MathConst; using namespace MathConst;
@ -44,13 +45,13 @@ using namespace MathConst;
#define MAXLEVEL 4 #define MAXLEVEL 4
#define MAXLINE 256 #define MAXLINE 256
#define CHUNK 1024 #define CHUNK 1024
#define VALUELENGTH 64 #define VALUELENGTH 64 // also in python.cpp
#define MAXFUNCARG 6 #define MAXFUNCARG 6
#define MYROUND(a) (( a-floor(a) ) >= .5) ? ceil(a) : floor(a) #define MYROUND(a) (( a-floor(a) ) >= .5) ? ceil(a) : floor(a)
enum{INDEX,LOOP,WORLD,UNIVERSE,ULOOP,STRING,GETENV, enum{INDEX,LOOP,WORLD,UNIVERSE,ULOOP,STRING,GETENV,
SCALARFILE,ATOMFILE,FORMAT,EQUAL,ATOM}; SCALARFILE,ATOMFILE,FORMAT,EQUAL,ATOM,PYTHON};
enum{ARG,OP}; enum{ARG,OP};
// customize by adding a function // customize by adding a function
@ -106,6 +107,10 @@ Variable::Variable(LAMMPS *lmp) : Pointers(lmp)
precedence[MULTIPLY] = precedence[DIVIDE] = precedence[MODULO] = 6; precedence[MULTIPLY] = precedence[DIVIDE] = precedence[MODULO] = 6;
precedence[CARAT] = 7; precedence[CARAT] = 7;
precedence[UNARY] = precedence[NOT] = 8; precedence[UNARY] = precedence[NOT] = 8;
// Python wrapper, real or dummy
python = new Python(lmp);
} }
/* ---------------------------------------------------------------------- */ /* ---------------------------------------------------------------------- */
@ -131,6 +136,8 @@ Variable::~Variable()
delete randomequal; delete randomequal;
delete randomatom; delete randomatom;
delete python;
} }
/* ---------------------------------------------------------------------- /* ----------------------------------------------------------------------
@ -413,9 +420,36 @@ void Variable::set(int narg, char **arg)
copy(1,&arg[2],data[nvar]); copy(1,&arg[2],data[nvar]);
} }
// PYTHON
// replace pre-existing var if also style PYTHON (allows it to be reset)
// num = 2, which = 1st value
// data = 2 values, 1st is Python func to invoke, 2nd is filled by invoke
} else if (strcmp(arg[1],"python") == 0) {
if (narg != 3) error->all(FLERR,"Illegal variable command");
if (!python->python_exists)
error->all(FLERR,"LAMMPS is not built with Python embedded");
int ivar = find(arg[0]);
if (ivar >= 0) {
if (style[ivar] != PYTHON)
error->all(FLERR,"Cannot redefine variable as a different style");
delete [] data[ivar][0];
copy(1,&arg[2],data[ivar]);
replaceflag = 1;
} else {
if (nvar == maxvar) grow();
style[nvar] = PYTHON;
num[nvar] = 2;
which[nvar] = 1;
pad[nvar] = 0;
data[nvar] = new char*[num[nvar]];
copy(1,&arg[2],data[nvar]);
data[nvar][1] = new char[VALUELENGTH];
}
} else error->all(FLERR,"Illegal variable command"); } else error->all(FLERR,"Illegal variable command");
// set name of variable, if not replacing (STRING/EQUAL/ATOM) // set name of variable, if not replacing (EQUAL/ATOM/STRING/PYTHON)
// name must be all alphanumeric chars or underscores // name must be all alphanumeric chars or underscores
if (replaceflag) return; if (replaceflag) return;
@ -446,6 +480,23 @@ void Variable::set(char *name, int narg, char **arg)
delete [] newarg; delete [] newarg;
} }
/* ----------------------------------------------------------------------
set existing STRING variable to str
return 0 if successful
return -1 if variable doesn't exist or isn't a STRING variable
called via library interface, so external programs can set variables
------------------------------------------------------------------------- */
int Variable::set_string(char *name, char *str)
{
int ivar = find(name);
if (ivar < 0) return -1;
if (style[ivar] != STRING) return -1;
delete [] data[ivar][0];
copy(1,&str,data[ivar]);
return 0;
}
/* ---------------------------------------------------------------------- /* ----------------------------------------------------------------------
increment variable(s) increment variable(s)
return 0 if OK if successfully incremented return 0 if OK if successfully incremented
@ -470,11 +521,12 @@ int Variable::next(int narg, char **arg)
error->all(FLERR,"All variables in next command must be same style"); error->all(FLERR,"All variables in next command must be same style");
} }
// invalid styles STRING or EQUAL or WORLD or ATOM or GETENV or FORMAT // invalid styles: STRING, EQUAL, WORLD, ATOM, GETENV, FORMAT, PYTHON
int istyle = style[find(arg[0])]; int istyle = style[find(arg[0])];
if (istyle == STRING || istyle == EQUAL || istyle == WORLD if (istyle == STRING || istyle == EQUAL || istyle == WORLD ||
|| istyle == GETENV || istyle == ATOM || istyle == FORMAT) istyle == GETENV || istyle == ATOM || istyle == FORMAT ||
istyle == PYTHON)
error->all(FLERR,"Invalid variable style with next command"); error->all(FLERR,"Invalid variable style with next command");
// if istyle = UNIVERSE or ULOOP, insure all such variables are incremented // if istyle = UNIVERSE or ULOOP, insure all such variables are incremented
@ -587,16 +639,96 @@ int Variable::next(int narg, char **arg)
return flag; return flag;
} }
/* ----------------------------------------------------------------------
search for name in list of variables names
return index or -1 if not found
------------------------------------------------------------------------- */
int Variable::find(char *name)
{
for (int i = 0; i < nvar; i++)
if (strcmp(name,names[i]) == 0) return i;
return -1;
}
/* ----------------------------------------------------------------------
initialize one atom's storage values in all VarReaders via fix STORE
called when atom is created
------------------------------------------------------------------------- */
void Variable::set_arrays(int i)
{
for (int i = 0; i < nvar; i++)
if (reader[i] && style[i] == ATOMFILE)
reader[i]->fixstore->vstore[i] = 0.0;
}
/* ----------------------------------------------------------------------
called by python command in input script
simply pass input script line args to Python class
------------------------------------------------------------------------- */
void Variable::python_command(int narg, char **arg)
{
if (!python->python_exists)
error->all(FLERR,"LAMMPS is not built with Python embedded");
python->command(narg,arg);
}
/* ----------------------------------------------------------------------
return 1 if variable is EQUAL or PYTHON numeric style, 0 if not
this is checked before call to compute_equal() to return a double
------------------------------------------------------------------------- */
int Variable::equalstyle(int ivar)
{
if (style[ivar] == EQUAL) return 1;
if (style[ivar] == PYTHON) {
int ifunc = python->variable_match(data[ivar][0],names[ivar],1);
if (ifunc < 0) return 0;
else return 1;
}
return 0;
}
/* ----------------------------------------------------------------------
return 1 if variable is ATOM or ATOMFILE style, 0 if not
this is checked before call to compute_atom() to return a vector of doubles
------------------------------------------------------------------------- */
int Variable::atomstyle(int ivar)
{
if (style[ivar] == ATOM || style[ivar] == ATOMFILE) return 1;
return 0;
}
/* ----------------------------------------------------------------------
check if variable with name is PYTHON and matches funcname
called by Python class before it invokes a Python function
return data storage so Python function can return a value for this variable
return NULL if not a match
------------------------------------------------------------------------- */
char *Variable::pythonstyle(char *name, char *funcname)
{
int ivar = find(name);
if (ivar == -1) return NULL;
if (style[ivar] != PYTHON) return NULL;
if (strcmp(data[ivar][0],funcname) != 0) return NULL;
return data[ivar][1];
}
/* ---------------------------------------------------------------------- /* ----------------------------------------------------------------------
return ptr to the data text associated with a variable return ptr to the data text associated with a variable
if INDEX or WORLD or UNIVERSE or STRING or SCALARFILE var, if INDEX or WORLD or UNIVERSE or STRING or SCALARFILE,
return ptr to stored string return ptr to stored string
if LOOP or ULOOP var, write int to data[0] and return ptr to string if LOOP or ULOOP, write int to data[0] and return ptr to string
if EQUAL var, evaluate variable and put result in str if EQUAL, evaluate variable and put result in str
if FORMAT var, evaluate its variable and put formatted result in str if FORMAT, evaluate its variable and put formatted result in str
if GETENV var, query environment and put result in str if GETENV, query environment and put result in str
if ATOM or ATOMFILE var, return NULL if PYTHON, evaluate Python function, it will put result in str
return NULL if no variable with name or which value is bad, if ATOM or ATOMFILE, return NULL
return NULL if no variable with name, or which value is bad,
caller must respond caller must respond
------------------------------------------------------------------------- */ ------------------------------------------------------------------------- */
@ -606,6 +738,10 @@ char *Variable::retrieve(char *name)
if (ivar == -1) return NULL; if (ivar == -1) return NULL;
if (which[ivar] >= num[ivar]) return NULL; if (which[ivar] >= num[ivar]) return NULL;
if (eval_in_progress[ivar])
error->all(FLERR,"Variable has circular dependency");
eval_in_progress[ivar] = 1;
char *str; char *str;
if (style[ivar] == INDEX || style[ivar] == WORLD || if (style[ivar] == INDEX || style[ivar] == WORLD ||
style[ivar] == UNIVERSE || style[ivar] == STRING || style[ivar] == UNIVERSE || style[ivar] == STRING ||
@ -625,16 +761,14 @@ char *Variable::retrieve(char *name)
strcpy(data[ivar][0],result); strcpy(data[ivar][0],result);
str = data[ivar][0]; str = data[ivar][0];
} else if (style[ivar] == EQUAL) { } else if (style[ivar] == EQUAL) {
eval_in_progress[ivar] = 1;
double answer = evaluate(data[ivar][0],NULL); double answer = evaluate(data[ivar][0],NULL);
eval_in_progress[ivar] = 0;
sprintf(data[ivar][1],"%.15g",answer); sprintf(data[ivar][1],"%.15g",answer);
str = data[ivar][1]; str = data[ivar][1];
} else if (style[ivar] == FORMAT) { } else if (style[ivar] == FORMAT) {
int jvar = find(data[ivar][0]); int jvar = find(data[ivar][0]);
if (jvar == -1) return NULL; if (jvar == -1) return NULL;
if (!equalstyle(jvar)) return NULL; if (!equalstyle(jvar)) return NULL;
double answer = evaluate(data[jvar][0],NULL); double answer = compute_equal(jvar);
sprintf(data[ivar][2],data[ivar][1],answer); sprintf(data[ivar][2],data[ivar][1],answer);
str = data[ivar][2]; str = data[ivar][2];
} else if (style[ivar] == GETENV) { } else if (style[ivar] == GETENV) {
@ -647,13 +781,24 @@ char *Variable::retrieve(char *name)
} }
strcpy(data[ivar][1],result); strcpy(data[ivar][1],result);
str = data[ivar][1]; str = data[ivar][1];
} else if (style[ivar] == PYTHON) {
int ifunc = python->variable_match(data[ivar][0],names[ivar],0);
if (ifunc < 0)
error->all(FLERR,"Python variable does not match Python function");
python->invoke_function(ifunc,data[ivar][1]);
str = data[ivar][1];
} else if (style[ivar] == ATOM || style[ivar] == ATOMFILE) return NULL; } else if (style[ivar] == ATOM || style[ivar] == ATOMFILE) return NULL;
eval_in_progress[ivar] = 0;
return str; return str;
} }
/* ---------------------------------------------------------------------- /* ----------------------------------------------------------------------
return result of equal-style variable evaluation return result of equal-style variable evaluation
can be EQUAL style or PYTHON numeric style
for PYTHON, don't need to check python->variable_match() error return,
since caller will have already checked via equalstyle()
------------------------------------------------------------------------- */ ------------------------------------------------------------------------- */
double Variable::compute_equal(int ivar) double Variable::compute_equal(int ivar)
@ -662,7 +807,14 @@ double Variable::compute_equal(int ivar)
error->all(FLERR,"Variable has circular dependency"); error->all(FLERR,"Variable has circular dependency");
eval_in_progress[ivar] = 1; eval_in_progress[ivar] = 1;
double value = evaluate(data[ivar][0],NULL); double value;
if (style[ivar] == EQUAL) value = evaluate(data[ivar][0],NULL);
else if (style[ivar] == PYTHON) {
int ifunc = python->find(data[ivar][0]);
if (ifunc < 0) error->all(FLERR,"Python variable has no function");
python->invoke_function(ifunc,data[ivar][1]);
value = atof(data[ivar][1]);
}
eval_in_progress[ivar] = 0; eval_in_progress[ivar] = 0;
return value; return value;
@ -671,6 +823,7 @@ double Variable::compute_equal(int ivar)
/* ---------------------------------------------------------------------- /* ----------------------------------------------------------------------
return result of immediate equal-style variable evaluation return result of immediate equal-style variable evaluation
called from Input::substitute() called from Input::substitute()
don't need to flag eval_in_progress since is an immediate variable
------------------------------------------------------------------------- */ ------------------------------------------------------------------------- */
double Variable::compute_equal(char *str) double Variable::compute_equal(char *str)
@ -744,54 +897,11 @@ void Variable::compute_atom(int ivar, int igroup,
eval_in_progress[ivar] = 0; eval_in_progress[ivar] = 0;
} }
/* ----------------------------------------------------------------------
search for name in list of variables names
return index or -1 if not found
------------------------------------------------------------------------- */
int Variable::find(char *name)
{
for (int i = 0; i < nvar; i++)
if (strcmp(name,names[i]) == 0) return i;
return -1;
}
/* ----------------------------------------------------------------------
initialize one atom's storage values in all VarReaders via fix STORE
called when atom is created
------------------------------------------------------------------------- */
void Variable::set_arrays(int i)
{
for (int i = 0; i < nvar; i++)
if (reader[i] && style[i] == ATOMFILE)
reader[i]->fixstore->vstore[i] = 0.0;
}
/* ----------------------------------------------------------------------
return 1 if variable is EQUAL style, 0 if not
------------------------------------------------------------------------- */
int Variable::equalstyle(int ivar)
{
if (style[ivar] == EQUAL) return 1;
return 0;
}
/* ----------------------------------------------------------------------
return 1 if variable is ATOM or ATOMFILE style, 0 if not
------------------------------------------------------------------------- */
int Variable::atomstyle(int ivar)
{
if (style[ivar] == ATOM || style[ivar] == ATOMFILE) return 1;
return 0;
}
/* ---------------------------------------------------------------------- /* ----------------------------------------------------------------------
save copy of EQUAL style ivar formula in copy save copy of EQUAL style ivar formula in copy
allocate copy here, later equal_restore() call will free it allocate copy here, later equal_restore() call will free it
insure data[ivar][0] is of VALUELENGTH since will be overridden insure data[ivar][0] is of VALUELENGTH since will be overridden
next 3 functions are used by create_atoms to temporarily override variables
------------------------------------------------------------------------- */ ------------------------------------------------------------------------- */
void Variable::equal_save(int ivar, char *&copy) void Variable::equal_save(int ivar, char *&copy)
@ -2712,8 +2822,6 @@ tagint Variable::int_between_brackets(char *&ptr, int varallow)
int ivar = find(id); int ivar = find(id);
if (ivar < 0) if (ivar < 0)
error->all(FLERR,"Invalid variable name in variable formula"); error->all(FLERR,"Invalid variable name in variable formula");
if (eval_in_progress[ivar])
error->all(FLERR,"Variable has circular dependency");
char *var = retrieve(id); char *var = retrieve(id);
if (var == NULL) if (var == NULL)

View File

@ -25,11 +25,17 @@ class Variable : protected Pointers {
~Variable(); ~Variable();
void set(int, char **); void set(int, char **);
void set(char *, int, char **); void set(char *, int, char **);
int set_string(char *, char *);
int next(int, char **); int next(int, char **);
int find(char *); int find(char *);
void set_arrays(int); void set_arrays(int);
void python_command(int, char **);
int equalstyle(int); int equalstyle(int);
int atomstyle(int); int atomstyle(int);
char *pythonstyle(char *, char *);
char *retrieve(char *); char *retrieve(char *);
double compute_equal(int); double compute_equal(int);
double compute_equal(char *); double compute_equal(char *);
@ -64,6 +70,8 @@ class Variable : protected Pointers {
int precedence[17]; // precedence level of math operators int precedence[17]; // precedence level of math operators
// set length to include up to OR in enum // set length to include up to OR in enum
class Python *python; // ptr to embedded Python interpreter
struct Tree { // parse tree for atom-style variables struct Tree { // parse tree for atom-style variables
double value; // single scalar double value; // single scalar
double *array; // per-atom or per-type list of doubles double *array; // per-atom or per-type list of doubles
@ -78,6 +86,7 @@ class Variable : protected Pointers {
Tree **extra; // ptrs further down tree for nextra args Tree **extra; // ptrs further down tree for nextra args
}; };
int compute_python(int);
void remove(int); void remove(int);
void grow(); void grow();
void copy(int, char **, char **); void copy(int, char **, char **);

View File

@ -1 +1 @@
#define LAMMPS_VERSION "12 Mar 2015" #define LAMMPS_VERSION "14 Mar 2015"