switch dump yaml/netcdf thermo output to use new caching API. remove old API.
This commit is contained in:
@ -753,9 +753,12 @@ run, this option is ignored since the output is already balanced.
|
||||
----------
|
||||
|
||||
The *thermo* keyword only applies the dump styles *netcdf* and *yaml*.
|
||||
It triggers writing of :doc:`thermo <thermo>` information to the dump file
|
||||
alongside per-atom data. The values included in the dump file are
|
||||
identical to the values specified by :doc:`thermo_style <thermo_style>`.
|
||||
It triggers writing of :doc:`thermo <thermo>` information to the dump
|
||||
file alongside per-atom data. The values included in the dump file are
|
||||
cached values from the last thermo output and include the exact same the
|
||||
values as specified by the :doc:`thermo_style <thermo_style>` command.
|
||||
Because these are cached values, they are only up-to-date when dump
|
||||
output is on a timestep that also has thermo output.
|
||||
|
||||
----------
|
||||
|
||||
|
||||
@ -60,21 +60,26 @@ void DumpYAML::write_header(bigint ndump)
|
||||
std::string thermo_data;
|
||||
if (thermo) {
|
||||
Thermo *th = output->thermo;
|
||||
thermo_data += "thermo:\n - keywords: [ ";
|
||||
for (int i = 0; i < th->nfield; ++i) thermo_data += fmt::format("{}, ", th->keyword[i]);
|
||||
thermo_data += "]\n - data: [ ";
|
||||
// output thermo data only on timesteps where it was computed
|
||||
if (update->ntimestep == th->get_timestep()) {
|
||||
|
||||
for (int i = 0; i < th->nfield; ++i) {
|
||||
th->call_vfunc(i);
|
||||
if (th->vtype[i] == Thermo::FLOAT)
|
||||
thermo_data += fmt::format("{}, ", th->dvalue);
|
||||
else if (th->vtype[i] == Thermo::INT)
|
||||
thermo_data += fmt::format("{}, ", th->ivalue);
|
||||
else if (th->vtype[i] == Thermo::BIGINT)
|
||||
thermo_data += fmt::format("{}, ", th->bivalue);
|
||||
thermo_data += "thermo:\n - keywords: [ ";
|
||||
for (auto key : th->get_keywords()) thermo_data += fmt::format("{}, ", key);
|
||||
thermo_data += "]\n - data: [ ";
|
||||
|
||||
for (auto val : th->get_fields()) {
|
||||
if (val.type == multitype::DOUBLE)
|
||||
thermo_data += fmt::format("{}, ", val.data.d);
|
||||
else if (val.type == multitype::INT)
|
||||
thermo_data += fmt::format("{}, ", val.data.i);
|
||||
else if (val.type == multitype::BIGINT)
|
||||
thermo_data += fmt::format("{}, ", val.data.b);
|
||||
else
|
||||
thermo_data += ", ";
|
||||
}
|
||||
thermo_data += "]\n";
|
||||
MPI_Barrier(world);
|
||||
}
|
||||
thermo_data += "]\n";
|
||||
MPI_Barrier(world);
|
||||
}
|
||||
|
||||
if (comm->me == 0) {
|
||||
|
||||
@ -223,7 +223,7 @@ void DumpNetCDF::openfile()
|
||||
|
||||
if (thermo && !singlefile_opened) {
|
||||
delete[] thermovar;
|
||||
thermovar = new int[output->thermo->nfield];
|
||||
thermovar = new int[output->thermo->get_keywords().size()];
|
||||
}
|
||||
|
||||
// now the computes and fixes have been initialized, so we can query
|
||||
@ -320,9 +320,10 @@ void DumpNetCDF::openfile()
|
||||
|
||||
// perframe variables
|
||||
if (thermo) {
|
||||
Thermo *th = output->thermo;
|
||||
for (int i = 0; i < th->nfield; i++) {
|
||||
NCERRX( nc_inq_varid(ncid, th->keyword[i].c_str(), &thermovar[i]), th->keyword[i].c_str() );
|
||||
auto keywords = output->thermo->get_keywords();
|
||||
int nfield = keywords.size();
|
||||
for (int i = 0; i < nfield; i++) {
|
||||
NCERRX( nc_inq_varid(ncid, keywords[i].c_str(), &thermovar[i]), keywords[i].c_str() );
|
||||
}
|
||||
}
|
||||
|
||||
@ -432,22 +433,16 @@ void DumpNetCDF::openfile()
|
||||
|
||||
// perframe variables
|
||||
if (thermo) {
|
||||
Thermo *th = output->thermo;
|
||||
for (int i = 0; i < th->nfield; i++) {
|
||||
if (th->vtype[i] == Thermo::FLOAT) {
|
||||
NCERRX( nc_def_var(ncid, th->keyword[i].c_str(), type_nc_real, 1, dims,
|
||||
&thermovar[i]), th->keyword[i].c_str() );
|
||||
} else if (th->vtype[i] == Thermo::INT) {
|
||||
NCERRX( nc_def_var(ncid, th->keyword[i].c_str(), NC_INT, 1, dims,
|
||||
&thermovar[i]), th->keyword[i].c_str() );
|
||||
} else if (th->vtype[i] == Thermo::BIGINT) {
|
||||
#if defined(LAMMPS_SMALLBIG) || defined(LAMMPS_BIGBIG)
|
||||
NCERRX( nc_def_var(ncid, th->keyword[i].c_str(), NC_INT64, 1, dims,
|
||||
&thermovar[i]), th->keyword[i].c_str() );
|
||||
#else
|
||||
NCERRX( nc_def_var(ncid, th->keyword[i].c_str(), NC_LONG, 1, dims,
|
||||
&thermovar[i]), th->keyword[i].c_str() );
|
||||
#endif
|
||||
auto fields = output->thermo->get_fields();
|
||||
auto keywords = output->thermo->get_keywords();
|
||||
int nfield = fields.size();
|
||||
for (int i = 0; i < nfield; i++) {
|
||||
if (fields[i].type == multitype::DOUBLE) {
|
||||
NCERRX( nc_def_var(ncid, keywords[i].c_str(), type_nc_real, 1, dims, &thermovar[i]), keywords[i].c_str() );
|
||||
} else if (fields[i].type == multitype::INT) {
|
||||
NCERRX( nc_def_var(ncid, keywords[i].c_str(), NC_INT, 1, dims, &thermovar[i]), keywords[i].c_str() );
|
||||
} else if (fields[i].type == multitype::BIGINT) {
|
||||
NCERRX( nc_def_var(ncid, keywords[i].c_str(), NC_INT64, 1, dims, &thermovar[i]), keywords[i].c_str() );
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -605,20 +600,17 @@ void DumpNetCDF::write()
|
||||
start[1] = 0;
|
||||
|
||||
if (thermo) {
|
||||
Thermo *th = output->thermo;
|
||||
for (int i = 0; i < th->nfield; i++) {
|
||||
th->call_vfunc(i);
|
||||
auto keywords = output->thermo->get_keywords();
|
||||
auto fields = output->thermo->get_fields();
|
||||
int nfield = fields.size();
|
||||
for (int i = 0; i < nfield; i++) {
|
||||
if (filewriter) {
|
||||
if (th->vtype[i] == Thermo::FLOAT) {
|
||||
NCERRX( nc_put_var1_double(ncid, thermovar[i], start,
|
||||
&th->dvalue),
|
||||
th->keyword[i].c_str() );
|
||||
} else if (th->vtype[i] == Thermo::INT) {
|
||||
NCERRX( nc_put_var1_int(ncid, thermovar[i], start, &th->ivalue),
|
||||
th->keyword[i].c_str() );
|
||||
} else if (th->vtype[i] == Thermo::BIGINT) {
|
||||
NCERRX( nc_put_var1_bigint(ncid, thermovar[i], start, &th->bivalue),
|
||||
th->keyword[i].c_str() );
|
||||
if (fields[i].type == multitype::DOUBLE) {
|
||||
NCERRX( nc_put_var1_double(ncid, thermovar[i], start, &fields[i].data.d), keywords[i].c_str() );
|
||||
} else if (fields[i].type == multitype::INT) {
|
||||
NCERRX( nc_put_var1_int(ncid, thermovar[i], start, &fields[i].data.i), keywords[i].c_str() );
|
||||
} else if (fields[i].type == multitype::BIGINT) {
|
||||
NCERRX( nc_put_var1_bigint(ncid, thermovar[i], start, &fields[i].data.b), keywords[i].c_str() );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -220,7 +220,7 @@ void DumpNetCDFMPIIO::openfile()
|
||||
|
||||
if (thermo && !singlefile_opened) {
|
||||
delete[] thermovar;
|
||||
thermovar = new int[output->thermo->nfield];
|
||||
thermovar = new int[output->thermo->get_keywords().size()];
|
||||
}
|
||||
|
||||
// now the computes and fixes have been initialized, so we can query
|
||||
@ -318,9 +318,10 @@ void DumpNetCDFMPIIO::openfile()
|
||||
|
||||
// perframe variables
|
||||
if (thermo) {
|
||||
Thermo *th = output->thermo;
|
||||
for (int i = 0; i < th->nfield; i++) {
|
||||
NCERRX( ncmpi_inq_varid(ncid, th->keyword[i].c_str(), &thermovar[i]), th->keyword[i].c_str() );
|
||||
auto keywords = output->thermo->get_keywords();
|
||||
int nfield = keywords.size();
|
||||
for (int i = 0; i < nfield; i++) {
|
||||
NCERRX( ncmpi_inq_varid(ncid, keywords[i].c_str(), &thermovar[i]), keywords[i].c_str() );
|
||||
}
|
||||
}
|
||||
|
||||
@ -422,18 +423,16 @@ void DumpNetCDFMPIIO::openfile()
|
||||
|
||||
// perframe variables
|
||||
if (thermo) {
|
||||
Thermo *th = output->thermo;
|
||||
for (int i = 0; i < th->nfield; i++) {
|
||||
if (th->vtype[i] == Thermo::FLOAT) {
|
||||
NCERRX( ncmpi_def_var(ncid, th->keyword[i].c_str(), type_nc_real, 1, dims, &thermovar[i]), th->keyword[i].c_str() );
|
||||
} else if (th->vtype[i] == Thermo::INT) {
|
||||
NCERRX( ncmpi_def_var(ncid, th->keyword[i].c_str(), NC_INT, 1, dims, &thermovar[i]), th->keyword[i].c_str() );
|
||||
} else if (th->vtype[i] == Thermo::BIGINT) {
|
||||
#if defined(LAMMPS_SMALLBIG) || defined(LAMMPS_BIGBIG)
|
||||
NCERRX( ncmpi_def_var(ncid, th->keyword[i].c_str(), NC_INT64, 1, dims, &thermovar[i]), th->keyword[i].c_str() );
|
||||
#else
|
||||
NCERRX( ncmpi_def_var(ncid, th->keyword[i].c_str(), NC_LONG, 1, dims, &thermovar[i]), th->keyword[i].c_str() );
|
||||
#endif
|
||||
auto fields = output->thermo->get_fields();
|
||||
auto keywords = output->thermo->get_keywords();
|
||||
int nfield = fields.size();
|
||||
for (int i = 0; i < nfield; i++) {
|
||||
if (fields[i].type == multitype::DOUBLE) {
|
||||
NCERRX( ncmpi_def_var(ncid, keywords[i].c_str(), type_nc_real, 1, dims, &thermovar[i]), keywords[i].c_str() );
|
||||
} else if (fields[i].type == multitype::INT) {
|
||||
NCERRX( ncmpi_def_var(ncid, keywords[i].c_str(), NC_INT, 1, dims, &thermovar[i]), keywords[i].c_str() );
|
||||
} else if (fields[i].type == multitype::BIGINT) {
|
||||
NCERRX( ncmpi_def_var(ncid, keywords[i].c_str(), NC_INT64, 1, dims, &thermovar[i]), keywords[i].c_str() );
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -594,20 +593,17 @@ void DumpNetCDFMPIIO::write()
|
||||
NCERR( ncmpi_begin_indep_data(ncid) );
|
||||
|
||||
if (thermo) {
|
||||
Thermo *th = output->thermo;
|
||||
for (int i = 0; i < th->nfield; i++) {
|
||||
th->call_vfunc(i);
|
||||
auto keywords = output->thermo->get_keywords();
|
||||
auto fields = output->thermo->get_fields();
|
||||
int nfield = fields.size();
|
||||
for (int i = 0; i < nfield; i++) {
|
||||
if (filewriter) {
|
||||
if (th->vtype[i] == Thermo::FLOAT) {
|
||||
NCERRX( ncmpi_put_var1_double(ncid, thermovar[i], start,
|
||||
&th->dvalue),
|
||||
th->keyword[i].c_str() );
|
||||
} else if (th->vtype[i] == Thermo::INT) {
|
||||
NCERRX( ncmpi_put_var1_int(ncid, thermovar[i], start, &th->ivalue),
|
||||
th->keyword[i].c_str() );
|
||||
} else if (th->vtype[i] == Thermo::BIGINT) {
|
||||
NCERRX( ncmpi_put_var1_bigint(ncid, thermovar[i], start, &th->bivalue),
|
||||
th->keyword[i].c_str() );
|
||||
if (fields[i].type == multitype::DOUBLE) {
|
||||
NCERRX( ncmpi_put_var1_double(ncid, thermovar[i], start, &fields[i].data.d), keywords[i].c_str() );
|
||||
} else if (fields[i].type == multitype::INT) {
|
||||
NCERRX( ncmpi_put_var1_int(ncid, thermovar[i], start, &fields[i].data.i), keywords[i].c_str() );
|
||||
} else if (fields[i].type == multitype::BIGINT) {
|
||||
NCERRX( ncmpi_put_var1_bigint(ncid, thermovar[i], start, &fields[i].data.b), keywords[i].c_str() );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -361,7 +361,7 @@ void Thermo::compute(int flag)
|
||||
int i;
|
||||
|
||||
firststep = flag;
|
||||
bigint ntimestep = update->ntimestep;
|
||||
ntimestep = update->ntimestep;
|
||||
|
||||
// check for lost atoms
|
||||
// turn off normflag if natoms = 0 to avoid divide by 0
|
||||
@ -405,18 +405,23 @@ void Thermo::compute(int flag)
|
||||
}
|
||||
|
||||
// add each thermo value to line with its specific format
|
||||
field_data.clear();
|
||||
field_data.resize(nfield);
|
||||
|
||||
for (ifield = 0; ifield < nfield; ifield++) {
|
||||
(this->*vfunc[ifield])();
|
||||
if (vtype[ifield] == FLOAT) {
|
||||
snprintf(fmtbuf, sizeof(fmtbuf), format[ifield].c_str(), dvalue);
|
||||
line += fmtbuf;
|
||||
field_data[ifield] = dvalue;
|
||||
} else if (vtype[ifield] == INT) {
|
||||
snprintf(fmtbuf, sizeof(fmtbuf), format[ifield].c_str(), ivalue);
|
||||
line += fmtbuf;
|
||||
field_data[ifield] = ivalue;
|
||||
} else if (vtype[ifield] == BIGINT) {
|
||||
snprintf(fmtbuf, sizeof(fmtbuf), format[ifield].c_str(), bivalue);
|
||||
line += fmtbuf;
|
||||
field_data[ifield] = bivalue;
|
||||
}
|
||||
}
|
||||
|
||||
@ -433,16 +438,6 @@ void Thermo::compute(int flag)
|
||||
firststep = 1;
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------------
|
||||
call function to compute property
|
||||
------------------------------------------------------------------------- */
|
||||
|
||||
void Thermo::call_vfunc(int ifield_in)
|
||||
{
|
||||
ifield = ifield_in;
|
||||
(this->*vfunc[ifield])();
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------------
|
||||
check for lost atoms, return current number of atoms
|
||||
also could number of warnings across MPI ranks and update total
|
||||
|
||||
11
src/thermo.h
11
src/thermo.h
@ -21,9 +21,6 @@ namespace LAMMPS_NS {
|
||||
|
||||
class Thermo : protected Pointers {
|
||||
friend class MinCG; // accesses compute_pe
|
||||
friend class DumpNetCDF; // accesses thermo properties
|
||||
friend class DumpNetCDFMPIIO; // accesses thermo properties
|
||||
friend class DumpYAML; // accesses thermo properties
|
||||
|
||||
public:
|
||||
char *style;
|
||||
@ -45,6 +42,11 @@ class Thermo : protected Pointers {
|
||||
void compute(int);
|
||||
int evaluate_keyword(const std::string &, double *);
|
||||
|
||||
// for accessing cached thermo data
|
||||
bigint get_timestep() const { return ntimestep; }
|
||||
const std::vector<multitype> &get_fields() const { return field_data; }
|
||||
const std::vector<std::string> &get_keywords() const { return keyword; }
|
||||
|
||||
private:
|
||||
int nfield, nfield_initial;
|
||||
int *vtype;
|
||||
@ -52,6 +54,7 @@ class Thermo : protected Pointers {
|
||||
std::vector<std::string> keyword, format, format_column_user, keyword_user;
|
||||
std::string format_line_user, format_float_user, format_int_user, format_bigint_user;
|
||||
std::map<std::string, int> key2col;
|
||||
std::vector<multitype> field_data;
|
||||
|
||||
int normvalue; // use this for normflag unless natoms = 0
|
||||
int normuserflag; // 0 if user has not set, 1 if has
|
||||
@ -66,6 +69,7 @@ class Thermo : protected Pointers {
|
||||
bigint last_step;
|
||||
|
||||
bigint natoms;
|
||||
bigint ntimestep;
|
||||
|
||||
// data used by routines that compute single values
|
||||
int ivalue; // integer value to print
|
||||
@ -114,7 +118,6 @@ class Thermo : protected Pointers {
|
||||
typedef void (Thermo::*FnPtr)();
|
||||
void addfield(const char *, FnPtr, int);
|
||||
FnPtr *vfunc; // list of ptrs to functions
|
||||
void call_vfunc(int ifield);
|
||||
|
||||
void compute_compute(); // functions that compute a single value
|
||||
void compute_fix(); // via calls to Compute,Fix,Variable classes
|
||||
|
||||
Reference in New Issue
Block a user