1 #include <boost/filesystem.hpp>
26 const jsonParser &json_ref,
double lin_alg_tol) {
28 json[
"chemical_reference"][
"global"] = json_ref;
34 log() <<
"Initializing the chemical reference to: \n\n";
42 const jsonParser &json_ref,
double lin_alg_tol) {
48 if (input.second.empty()) {
51 chem_ref.
set_global(input.second.begin(), input.second.end(), lin_alg_tol);
54 log() <<
"Updating the project-wide chemical reference to: \n";
64 if (!fs::exists(chem_ref_path)) {
66 <<
"Error using 'casm ref --set --configname': No reference found.\n";
67 err_log() <<
" Expected file at: " << chem_ref_path <<
"\n";
68 err_log() <<
"Use 'casm ref --set' or 'casm ref --set-auto' to set a "
69 "project-wide reference first.\n";
81 err_log() <<
"Error using 'casm ref --set --configname': \n"
82 " Could not find configuration with name: "
88 if (input.second.empty()) {
95 log() <<
"Updating the " <<
configname <<
" specialized reference to: \n";
104 double lin_alg_tol) {
105 if (!fs::exists(chem_ref_path)) {
107 <<
"Error using 'casm ref --set --scelname': No reference found.\n";
108 err_log() <<
" Expected file at: " << chem_ref_path <<
"\n";
109 err_log() <<
"Use 'casm ref --set' or 'casm ref --set-auto' to set a "
110 "project-wide reference first.\n";
121 err_log() <<
"Error using 'casm ref --set --scelname': \n"
122 " Could not find supercell with name: "
128 if (input.second.empty()) {
135 log() <<
"Updating the " <<
scelname <<
" specialized reference to: \n";
144 namespace Completer {
157 (
"display,d",
"Display current reference states")(
159 "Automatically set project level reference states using DFT results")(
160 "set", po::value<std::string>(&
m_set_str),
161 "Set reference states using user specified compositions and energies "
162 "(Default: set project-wide references). \n"
163 "See examples below for the form of expected input.")(
165 "Erase reference states (Default: clear project-wide references).")(
167 "Name of the cluster expansion using the reference");
178 po::variables_map vm;
180 std::string species_order_string =
"\n\n";
182 const fs::path &root = args.
root;
184 std::stringstream ss;
189 ss <<
" For this project, the expected order is:\n"
192 for (
int i = 0; i < names.size(); i++) {
194 if (i != names.size() - 1) {
200 species_order_string = ss.str();
206 po::store(po::parse_command_line(args.
argc(), args.
argv(), ref_opt.
desc()),
209 bool call_help =
false;
212 if (!vm.count(
"help") && !vm.count(
"desc")) {
213 if (vm.count(
"set") + vm.count(
"display") + vm.count(
"erase") +
214 vm.count(
"set-auto") !=
216 log() <<
"Error in 'casm ref'. Please select one of --display, \n";
217 log() <<
"--set, --set-auto, or --erase to use this option."
223 if (vm.count(
"set")) {
224 if (vm.count(
"scelname") + vm.count(
"configname") > 1) {
225 err_log() <<
"Error in 'casm ref --set'. Please select only one of "
226 "--scelname, --configname \n";
232 if (vm.count(
"erase")) {
233 if (vm.count(
"scelname") + vm.count(
"configname") > 1) {
234 err_log() <<
"Error in 'casm ref --erase'. Please select only one of "
235 "--scelname, --configname \n";
244 if (vm.count(
"help") || call_help) {
246 log() << ref_opt.
desc() << std::endl;
251 if (vm.count(
"desc")) {
253 log() << ref_opt.
desc() << std::endl;
255 log() <<
"DESCRIPTION" << std::endl;
256 log() <<
" The chemical reference determines the value of the "
257 "formation energy \n"
258 " and chemical potentials calculated by CASM. "
261 " Chemical references states are set by specifying a "
263 " energy/atom - composition (as atom_frac) space. This may "
265 " specifying the hyperplane explicitly, or by specifying "
267 " reference states with energy/atom and composition (as "
269 " enough states to span the composition space of the allowed "
271 " specified in the prim. For consistency with other CASM "
273 " additional reference states extending to other "
275 " dimensions may be included also. The pure Va reference is "
278 log() <<
" The input to '--set' can be one of three forms: "
281 " 1) Input the energy_per_species for pure states: "
283 << R
"( '{"A": X, "B": X, "C": X}')"
287 " 2) Input reference state composition and energy_per_species: "
291 << R
"( {"A": 3.4, "C": 2.0, "energy_per_species": 2.0},)"
293 << R
"( {"B": 2.0, "energy_per_species": 4.0}, )"
295 << R
"( {"C": 1.0, "energy_per_species": 3.0} )"
301 " 3) Input an array of energy_per_species, for each species in "
303 " including 0.0 for vacancy: "
307 << species_order_string;
309 log() <<
" When using '--set' it is also possible to specialize the "
311 " reference at the supercell or configuration level by "
313 " --scelname or --configname option. "
316 log() <<
" Examples:\n";
322 log() <<
" casm ref --display \n";
323 log() <<
" - Print chemical reference\n";
325 log() <<
" casm ref --set-auto\n";
326 log() <<
" - set all reference states using DFT results for "
327 "configurations with\n";
328 log() <<
" extreme compositions.\n";
329 log() <<
" - set reference for compositions outside range of this "
332 log() <<
" casm ref --set \n"
333 " '[{\"Zr\":1, \"energy_per_species\":-8.546979385}, \n"
334 " {\"Zr\":1, \"O\":1, "
335 "\"energy_per_species\":-9.090697345}]'\n"
336 " - set Zr and ZrO, with given energy per species, as "
337 "reference states\n\n";
339 log() <<
" casm ref --scelname SCEL3_3_1_1_0_2_2 --set \n"
340 " '[{\"Zr\":1, \"energy_per_species\":-8.546979385}, \n"
341 " {\"Zr\":1, \"O\":1, "
342 "\"energy_per_species\":-9.090697345}]'\n"
343 " - set reference states as specified for configurations "
344 "in supercell SCEL3_3_1_1_0_2_2\n\n";
346 log() <<
" casm ref --configname SCEL3_3_1_1_0_2_2/2 --set \n"
347 " '[{\"Zr\":1, \"energy_per_species\":-8.546979385}, \n"
348 " {\"Zr\":1, \"O\":1, "
349 "\"energy_per_species\":-9.090697345}]'\n"
350 " - set reference states as specified for configuration "
351 "SCEL3_3_1_1_0_2_2/2\n\n";
353 log() <<
" casm ref --scelname SCEL3_3_1_1_0_2_2 --erase \n"
354 " - erase specialized reference states for configurations "
355 "in supercell SCEL3_3_1_1_0_2_2\n\n";
357 log() <<
" casm ref --configname SCEL3_3_1_1_0_2_2/2 --erase \n"
358 " - erase specialized reference states for configuration "
359 "SCEL3_3_1_1_0_2_2/2\n\n";
371 }
catch (po::error &e) {
372 err_log() <<
"ERROR: " << e.what() << std::endl << std::endl;
375 }
catch (std::exception &e) {
376 err_log() <<
"Unhandled Exception reached the top of main: " << e.what()
377 <<
", application will now exit" << std::endl;
389 std::unique_ptr<PrimClex> uniq_primclex;
395 if (!vm.count(
"clex")) {
401 err_log() << vm[
"clex"].as<std::string>() <<
" not found.";
404 clex_desc = it->second;
408 std::string
ref = clex_desc.
ref;
412 if (vm.count(
"display")) {
414 err_log() <<
"Error using 'casm ref --display': No reference found.\n";
415 err_log() <<
" Expected file at: " << chem_ref_path <<
"\n";
416 err_log() <<
"Use 'casm ref --set' or 'casm ref --set-auto' to set a "
425 }
else if (vm.count(
"set-auto")) {
427 log() <<
" Set reference states automatically.\n\n" << std::endl;
434 }
catch (std::exception &e) {
435 err_log() <<
"Error setting reference states automatically.\n\n";
436 err_log() << e.what() << std::endl;
439 }
else if (vm.count(
"set")) {
440 using namespace ref_impl;
445 }
catch (std::exception &e) {
446 err_log() <<
"Error parsing JSON input for 'casm ref --set ' with: \n"
447 << set_str << std::endl;
448 err_log() << e.what() << std::endl;
454 if (!(vm.count(
"scelname") + vm.count(
"configname"))) {
455 if (!fs::exists(chem_ref_path)) {
468 else if (vm.count(
"configname")) {
477 json_ref, lin_alg_tol);
480 }
else if (vm.count(
"erase")) {
483 if (!(vm.count(
"scelname") + vm.count(
"configname"))) {
484 if (!fs::exists(chem_ref_path)) {
485 err_log() <<
"No chemical reference found. \n";
488 fs::remove(chem_ref_path);
489 log() <<
"Erased chemical reference" << std::endl;
497 if (vm.count(
"configname")) {
502 log() <<
"Erased specialized reference for " <<
configname << std::endl;
514 log() <<
"Erased specialized reference for " <<
scelname << std::endl;
#define ERR_MISSING_INPUT_FILE
size_type erase_supercell(const std::string &scelname)
Erase hyperplane reference specialized for a Supercell.
void set_config(const std::string &configname, const Eigen::VectorXd &ref)
Set hyperplane reference specialized for a Configuration.
void set_global(const Eigen::VectorXd &ref)
Set global hyperplane reference.
size_type erase_config(const std::string &configname)
Erase hyperplane reference specialized for a Configuration.
void set_supercell(const std::string &scelname, const Eigen::VectorXd &ref)
Set hyperplane reference specialized for a Supercell.
static std::string clex()
Get value_type string for clex mode completion.
const po::options_description & desc()
Get the program options, filled with the initialized values.
void add_scelname_suboption()
Add a –scelname suboption.
void add_help_suboption()
Add a plain –help and –desc suboptions.
po::options_description m_desc
void add_configname_suboption()
Add a –configname suboption.
void initialize() override
Fill in the options descriptions accordingly.
const std::string & supercell_str() const
Returns the name of the supercell for add_scelname_suboption()
const std::string & config_str() const
const std::string & set_str() const
Specification of CASM project directory structure.
fs::path prim() const
Return prim.json path.
fs::path chemical_reference(std::string calctype, std::string ref) const
Return chemical reference file path.
void error(const std::string &what)
PrimClex is the top-level data structure for a CASM project.
double lin_alg_tol() const
Get current project linear algebra tolerance.
std::map< std::string, ClexDescription > const & cluster_expansions() const
Const access map of all ClexDescription.
DirectoryStructure const & dir() const
Access DirectoryStructure object. Throw if not set.
ClexDescription const & default_clex() const
Get default ClexDescription.
Structure specifies the lattice and atomic basis of a crystal.
Represents a supercell of the primitive parent crystal structure.
static jsonParser object()
Returns an empty json object.
static jsonParser parse(const std::string &str)
Construct a jsonParser from a string containing JSON data.
PrimClex & make_primclex_if_not(const CommandArgs &args, std::unique_ptr< PrimClex > &uniq_primclex)
If !_primclex, construct new PrimClex stored in uniq_primclex, then return reference to existing or c...
ProjectSettings & settings()
bool has_chemical_reference() const
check if ChemicalReference object initialized
const DirectoryStructure & dir() const
Access DirectoryStructure object. Throw if not set.
void refresh(bool read_settings=false, bool read_composition=false, bool read_chem_ref=false, bool read_configs=false, bool clear_clex=false)
Reload PrimClex data from settings.
const ChemicalReference & chemical_reference() const
const Access ChemicalReference object
ProjectSettings open_project_settings(fs::path path_in_project)
std::vector< std::string > struc_molecule_name(BasicStructure const &_struc)
Returns an Array of each possible Molecule in this Structure.
std::string scelname(const Structure &prim, const Lattice &superlat)
Make supercell name name [deprecated].
T get(Args &&... args) const
Get data from json, using one of several alternatives.
ConfigIO::GenericConfigFormatter< jsonParser > config()
ConfigIO::GenericConfigFormatter< std::string > configname()
Constructs DataFormmaterDictionary containing all Configuration DatumFormatters.
int initialize_global(fs::path chem_ref_path, const PrimClex &primclex, const jsonParser &json_ref, double lin_alg_tol)
int update_config(std::string configname, fs::path chem_ref_path, const PrimClex &primclex, const jsonParser &json_ref, double lin_alg_tol)
int update_supercell(std::string scelname, fs::path chem_ref_path, const PrimClex &primclex, const jsonParser &json_ref, double lin_alg_tol)
int update_global(fs::path chem_ref_path, const PrimClex &primclex, const jsonParser &json_ref, double lin_alg_tol)
void write_chemical_reference(const ChemicalReference &chem_ref, fs::path filename)
Write chemical reference states to JSON file.
std::pair< Eigen::VectorXd, std::vector< ChemicalReferenceState > > one_chemical_reference_from_json(xtal::BasicStructure const &prim, jsonParser const &json)
Read chemical reference from one of 3 alternative forms.
ChemicalReference auto_chemical_reference(const PrimClex &primclex, double lin_alg_tol)
Automatically set ChemicalReference using calculated Configurations with 'extreme' compositions.
xtal::BasicStructure read_prim(fs::path filename, double xtal_tol, ParsingDictionary< AnisoValTraits > const *_aniso_val_dict=nullptr)
Iterator find(Iterator begin, Iterator end, const T &value, BinaryCompare q)
Equivalent to std::find(begin, end, value), but with custom comparison.
ChemicalReference read_chemical_reference(fs::path filename, const xtal::BasicStructure &prim, double tol)
Read chemical reference states from JSON file.
int ref_command(const CommandArgs &args)
DirectoryStructure const & dir
BasicStructure to help print ChemicalReference.
Specifies a particular cluster expansion.
Data structure holding basic CASM command info.