1 #ifndef CASM_ClexBasisWriter_impl
2 #define CASM_ClexBasisWriter_impl
22 template <
typename OrbitType>
25 std::vector<OrbitType>
const &_tree,
27 std::ostream &stream,
double xtal_tol) {
28 enum FuncStringType { func_declaration = 0, func_definition = 1 };
32 std::map<UnitCellCoord, std::set<UnitCellCoord> > nhood =
35 Index N_flower = nhood.size();
36 for (
auto const &nbor : nhood)
39 std::stringstream bfunc_imp_stream, bfunc_def_stream;
41 std::string indent(2,
' ');
43 std::stringstream param_pack_stream;
44 print_param_pack(class_name, clex, _tree, _nlist, param_pack_stream, indent);
46 std::string uclass_name;
47 for (
Index i = 0; i < class_name.size(); i++)
48 uclass_name.push_back(std::toupper(class_name[i]));
50 std::string private_declarations =
53 N_flower, indent +
" ");
55 private_declarations +=
57 class_name, clex, indent +
" ");
59 std::string public_declarations =
61 class_name, clex, indent +
" ");
66 std::vector<std::unique_ptr<FunctionVisitor> >
const &visitors(
70 std::vector<std::string> orbit_method_names(N_corr,
"zero_func");
72 std::vector<std::vector<std::string> > flower_method_names(
73 N_flower, std::vector<std::string>(N_corr,
"zero_func"));
76 std::vector<std::vector<std::string> > dflower_method_names(
77 N_flower, std::vector<std::string>(N_corr,
"zero_func"));
80 std::vector<std::string> formulae, tformulae;
83 for (
Index no = 0; no < _tree.size(); no++) {
84 if (_tree[no].prototype().size() == 0)
85 bfunc_imp_stream << indent <<
"// Basis functions for empty cluster:\n";
87 bfunc_imp_stream << indent <<
"/**** Basis functions for orbit " << no
89 Log l(bfunc_imp_stream);
91 bfunc_imp_stream << indent <<
"****/\n";
94 auto orbit_method_namer = [lf, no, &orbit_method_names](
96 orbit_method_names[lf + nf] =
98 return orbit_method_names[lf + nf];
101 std::tuple<std::string, std::string> orbit_functions =
103 class_name, clex.
bset_orbit(no), _tree[no], orbit_method_namer,
104 _nlist, visitors, indent);
106 bfunc_def_stream << std::get<func_declaration>(orbit_functions);
107 bfunc_imp_stream << std::get<func_definition>(orbit_functions);
109 auto flower_method_namer = [lf, no, &flower_method_names](
111 flower_method_names[nb][lf + nf] =
114 return flower_method_names[nb][lf + nf];
117 std::tuple<std::string, std::string> flower_functions =
119 class_name, clex.
bset_orbit(no), _tree[no], flower_method_namer,
120 nhood, _nlist, visitors, indent);
122 bfunc_def_stream << std::get<func_declaration>(flower_functions);
123 bfunc_imp_stream << std::get<func_definition>(flower_functions);
125 auto dflower_method_namer = [lf, no, &dflower_method_names](
127 dflower_method_names[nb][lf + nf] =
130 return dflower_method_names[nb][lf + nf];
135 std::string dof_key(
"occ");
137 "(m_occ_func_%b_%f[occ_f] - m_occ_func_%b_%f[occ_i])");
139 auto site_bases_iter = clex.
site_bases().find(dof_key);
140 if (site_bases_iter != clex.
site_bases().end()) {
141 std::tuple<std::string, std::string> dflower_functions =
143 class_name, clex.
bset_orbit(no), site_bases_iter->second,
144 _tree[no], dflower_method_namer, nhood, _nlist, visitors,
145 site_prefactor_labeler, indent);
147 bfunc_def_stream << std::get<func_declaration>(dflower_functions);
148 bfunc_imp_stream << std::get<func_definition>(dflower_functions);
156 std::string constructor_definition =
159 orbit_method_names, flower_method_names, dflower_method_names,
162 std::string interface_declaration =
166 std::string prepare_methods_definition =
170 prepare_methods_definition +=
184 <<
"#include <cstddef>\n"
185 <<
"#include \"casm/clex/Clexulator.hh\"\n"
186 <<
"#include \"casm/clex/BasicClexParamPack.hh\"\n"
187 <<
"#include \"casm/global/eigen.hh\"\n"
191 <<
"/****** PROJECT SPECIFICATIONS ******\n\n"
193 <<
" ****** prim.json ******\n\n"
194 << json_prim <<
"\n\n"
195 <<
" ****** bspecs.json ******\n\n"
196 << basis_set_specs_json <<
"\n\n"
199 <<
"/// \\brief Returns a Clexulator_impl::Base* owning a " << class_name
201 <<
"extern \"C\" CASM::Clexulator_impl::Base *make_" + class_name
204 <<
"namespace CASM {\n\n"
206 <<
" /****** GENERATED CLEXPARAMPACK DEFINITION ******/\n\n"
208 << param_pack_stream.str() <<
"\n\n"
210 <<
" /****** GENERATED CLEXULATOR DEFINITION ******/\n\n"
212 << indent <<
"class " << class_name
213 <<
" : public Clexulator_impl::Base {\n\n"
215 << indent <<
"public:\n\n"
216 << public_declarations <<
"\n"
217 << bfunc_def_stream.str() <<
"\n"
219 << indent <<
"private:\n\n"
220 << private_declarations <<
"\n"
222 << indent <<
"};\n\n"
227 "~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n\n"
229 << constructor_definition <<
"\n"
230 << interface_declaration <<
"\n"
231 << prepare_methods_definition <<
"\n"
232 << bfunc_imp_stream.str() <<
"}\n\n\n"
234 <<
"extern \"C\" {\n"
235 << indent <<
"/// \\brief Returns a Clexulator_impl::Base* owning a "
236 << class_name <<
"\n"
237 << indent <<
"CASM::Clexulator_impl::Base *make_" + class_name <<
"() {\n"
238 << indent <<
" return new CASM::" + class_name +
"();\n"
248 template <
typename OrbitType>
251 std::vector<OrbitType>
const &_tree,
253 std::ostream &stream,
254 std::string
const &_indent)
const {
259 namespace ClexBasisWriter_impl {
261 template <
typename OrbitType>
264 OrbitType
const &_clust_orbit,
265 std::function<std::string(
Index,
Index)> method_namer,
267 std::vector<std::unique_ptr<FunctionVisitor> >
const &visitors,
268 std::string
const &indent) {
269 std::stringstream bfunc_def_stream;
270 std::stringstream bfunc_imp_stream;
272 std::vector<std::string> formulae =
274 std::string method_name;
276 bool make_newline =
false;
277 for (
Index nf = 0; nf < formulae.size(); nf++) {
278 if (!formulae[nf].size())
continue;
281 method_name = method_namer(0, nf);
282 bfunc_def_stream << indent <<
" template<typename Scalar>\n"
283 << indent <<
" Scalar " << method_name <<
"() const;\n";
285 bfunc_imp_stream << indent <<
"template<typename Scalar>\n"
286 << indent <<
"Scalar " << class_name <<
"::" << method_name
288 << indent <<
" return " << formulae[nf] <<
";\n"
292 bfunc_imp_stream <<
'\n';
293 bfunc_def_stream <<
'\n';
295 return std::tuple<std::string, std::string>(bfunc_def_stream.str(),
296 bfunc_imp_stream.str());
301 template <
typename OrbitType>
304 OrbitType
const &_clust_orbit,
305 std::function<std::string(
Index,
Index)> method_namer,
306 std::map<
UnitCellCoord, std::set<UnitCellCoord> >
const &_nhood,
308 std::vector<std::unique_ptr<FunctionVisitor> >
const &visitors,
309 std::string
const &indent) {
310 std::stringstream bfunc_def_stream, bfunc_imp_stream;
311 std::string method_name;
313 bool make_newline =
false;
315 for (
auto const &nbor : _nhood) {
316 make_newline =
false;
320 _nlist, visitors, nbor.first);
324 for (
Index nf = 0; nf < formulae.size(); nf++) {
325 if (!formulae[nf].size())
continue;
328 method_name = method_namer(nbor_ind, nf);
329 bfunc_def_stream << indent <<
" template<typename Scalar>\n"
330 << indent <<
" Scalar " << method_name <<
"() const;\n";
332 bfunc_imp_stream << indent <<
"template<typename Scalar>\n"
333 << indent <<
"Scalar " << class_name
334 <<
"::" << method_name <<
"() const {\n"
335 << indent <<
" return " << formulae[nf] <<
";\n"
340 bfunc_imp_stream <<
'\n';
341 bfunc_def_stream <<
'\n';
344 return std::tuple<std::string, std::string>(bfunc_def_stream.str(),
345 bfunc_imp_stream.str());
350 template <
typename OrbitType>
354 std::function<std::string(
Index,
Index)> method_namer,
355 std::map<
UnitCellCoord, std::set<UnitCellCoord> >
const &_nhood,
357 std::vector<std::unique_ptr<FunctionVisitor> >
const &visitors,
358 FunctionVisitor const &_site_func_labeler, std::string
const &indent) {
359 std::stringstream bfunc_def_stream, bfunc_imp_stream;
360 bool make_newline =
false;
363 for (
auto const &nbor : _nhood) {
364 std::vector<std::string> formulae(_bset_orbit[0].size());
367 Index sublat_ind = nbor.first.sublattice();
370 BasisSet site_basis(_site_bases[sublat_ind]);
371 site_basis.
set_dof_IDs(std::vector<Index>(1, nbor_ind));
373 site_basis.
accept(_site_func_labeler);
374 for (
Index nsbf = 0; nsbf < site_basis.
size(); nsbf++) {
375 Function const *func_ptr = site_basis[nsbf];
378 return bset.poly_quotient_set(func_ptr);
382 _bset_orbit, get_quotient_bset, _clust_orbit, _nhood, _nlist,
383 visitors, nbor.first);
385 for (
Index nf = 0; nf < tformulae.size(); nf++) {
386 if (!tformulae[nf].size())
continue;
388 if (formulae[nf].size()) formulae[nf] +=
" + ";
390 formulae[nf] += site_basis[nsbf]->formula();
392 if (tformulae[nf] ==
"1" || tformulae[nf] ==
"(1)")
continue;
394 formulae[nf] +=
" * ";
395 formulae[nf] += tformulae[nf];
400 std::string method_name;
401 make_newline =
false;
402 for (
Index nf = 0; nf < formulae.size(); nf++) {
403 if (!formulae[nf].size()) {
408 method_name = method_namer(nbor_ind, nf);
410 bfunc_def_stream << indent <<
" template<typename Scalar>\n"
411 << indent <<
" Scalar " << method_name
412 <<
"(int occ_i, int occ_f) const;\n";
414 bfunc_imp_stream << indent <<
" template<typename Scalar>\n"
415 << indent <<
"Scalar " << class_name
416 <<
"::" << method_name
417 <<
"(int occ_i, int occ_f) const {\n"
418 << indent <<
" return " << formulae[nf] <<
";\n"
422 bfunc_imp_stream <<
'\n';
423 bfunc_def_stream <<
'\n';
425 make_newline =
false;
428 return std::tuple<std::string, std::string>(bfunc_def_stream.str(),
429 bfunc_imp_stream.str());
435 template <
typename OrbitType>
439 std::vector<std::unique_ptr<FunctionVisitor> >
const &visitors) {
440 std::string prefix, suffix;
441 std::vector<std::string> formulae(_bset_orbit[0].size(), std::string());
442 if (_clust_orbit.size() > 1) {
447 for (
Index ne = 0; ne < _bset_orbit.size(); ne++) {
449 _clust_orbit[ne].elements().begin(), _clust_orbit[ne].elements().end());
450 _bset_orbit[ne].set_dof_IDs(
451 std::vector<Index>(nbor_IDs.begin(), nbor_IDs.end()));
452 for (
Index nl = 0; nl < visitors.size(); nl++)
453 _bset_orbit[ne].accept(*visitors[nl]);
456 for (
Index nf = 0; nf < _bset_orbit[0].size(); nf++) {
457 for (
Index ne = 0; ne < _bset_orbit.size(); ne++) {
458 if (!_bset_orbit[ne][nf] || (_bset_orbit[ne][nf]->is_zero()))
continue;
460 if (formulae[nf].empty())
461 formulae[nf] += prefix;
462 else if ((_bset_orbit[ne][nf]->formula())[0] !=
'-' &&
463 (_bset_orbit[ne][nf]->formula())[0] !=
'+')
464 formulae[nf] +=
" + ";
466 formulae[nf] += _bset_orbit[ne][nf]->formula();
469 if (!formulae[nf].empty()) formulae[nf] += suffix;
476 template <
typename OrbitType>
480 OrbitType
const &_clust_orbit,
481 std::map<
UnitCellCoord, std::set<UnitCellCoord> >
const &_nhood,
483 std::vector<std::unique_ptr<FunctionVisitor> >
const &visitors,
485 std::vector<std::string> formulae;
487 std::string prefix, suffix;
489 std::set<UnitCellCoord> trans_set;
495 trans_set.insert(site);
501 trans_set.begin(), trans_set.end(), nbor, _clust_orbit.prototype().prim(),
502 _clust_orbit.sym_compare());
505 if (_clust_orbit.size() > 1) {
511 for (
Index ne = 0; ne < _clust_orbit.size(); ne++) {
512 if (formulae.empty()) formulae.resize(_bset_orbit[ne].size());
517 if (!
contains(_clust_orbit[ne].elements(), trans))
continue;
519 typename OrbitType::Element trans_clust =
520 _clust_orbit[ne] - (trans.unitcell() - nbor.
unitcell());
523 trans_clust.elements().begin(), trans_clust.elements().end());
525 _bset_orbit[ne].set_dof_IDs(
526 std::vector<Index>(nbor_IDs.begin(), nbor_IDs.end()));
528 BasisSet transformed_bset(_bset_transform(_bset_orbit[ne]));
529 for (
Index nl = 0; nl < visitors.size(); nl++)
530 transformed_bset.
accept(*visitors[nl]);
532 for (
Index nf = 0; nf < transformed_bset.
size(); nf++) {
533 if (!transformed_bset[nf] || (transformed_bset[nf]->is_zero()))
536 if (formulae[nf].empty())
537 formulae[nf] += prefix;
538 else if ((transformed_bset[nf]->formula())[0] !=
'-' &&
539 (transformed_bset[nf]->formula())[0] !=
'+')
540 formulae[nf] +=
" + ";
542 formulae[nf] += transformed_bset[nf]->formula();
547 for (
Index nf = 0; nf < formulae.size(); nf++) {
548 if (!formulae[nf].empty()) formulae[nf] += suffix;
555 template <
typename OrbitType>
557 std::vector<OrbitType>
const &_tree) {
564 out.flags(std::ios::showpoint | std::ios::fixed | std::ios::left);
566 auto it = site_bases.begin(), end_it = site_bases.end();
567 for (; it != end_it; ++it) {
568 out <<
"Basis site definitions for DoF " << it->first <<
".\n";
570 for (
Index nb = 0; nb < (it->second).size(); ++nb) {
571 out <<
" Basis site " << nb + 1 <<
":\n"
576 (it->second)[nb], clex.
prim().
basis()[nb], nb);
582 for (
Index i = 0; i < _tree.size(); i++) {
584 _tree[i].prototype().size() != _tree[i - 1].prototype().size())
585 out <<
"** " << _tree[i].prototype().size() <<
"-site clusters ** \n"
588 out <<
" ** Orbit " << i + 1 <<
" of " << _tree.size() <<
" **"
589 <<
" Points: " << _tree[i].prototype().size()
590 <<
" Mult: " << _tree[i].size()
591 <<
" MinLength: " << _tree[i].prototype().min_length()
592 <<
" MaxLength: " << _tree[i].prototype().max_length() <<
'\n'
597 <<
" of " << _tree[i].size() <<
" Equivalent Clusters in Orbit " << i
604 out <<
"\n\n" << std::flush;
606 if (_tree[i].prototype().size() != 0) out <<
'\n' << std::flush;
613 template <
typename OrbitIterType>
615 OrbitIterType begin, OrbitIterType end) {
616 std::map<UnitCellCoord, std::set<UnitCellCoord> > result;
618 if (begin == end)
return result;
621 typedef typename OrbitIterType::value_type orbit_type;
624 OrbitIterType begin2 = begin;
625 for (; begin2 != end; ++begin2) {
626 auto const &orbit = *begin2;
627 for (
auto const &equiv : orbit) {
636 if (!ucc_ptr)
return result;
638 Structure const &prim(begin->prototype().prim());
641 orbit_type empty_orbit(cluster_type(prim), identity_group,
642 begin->sym_compare());
645 for (; begin != end; ++begin) {
646 auto const &orbit = *begin;
647 for (
auto const &equiv : orbit) {
650 cluster_type test(empty_orbit.prototype());
653 test.elements().push_back(ucc);
654 test = orbit.sym_compare().prepare(test);
656 UnitCell trans = test.element(0).unitcell() - ucc.unitcell();
658 result[test.element(0)].insert(ucc2 + trans);
668 template <
typename UCCIterType,
typename IntegralClusterSymCompareType>
670 UCCIterType begin, UCCIterType end,
UnitCellCoord const &pivot,
671 Structure const &prim, IntegralClusterSymCompareType
const &sym_compare) {
672 std::set<UnitCellCoord> result;
677 if (begin == end)
return result;
681 orbit_type empty_orbit(cluster_type(prim), identity_group, sym_compare);
683 cluster_type pclust(empty_orbit.prototype());
684 pclust.elements().push_back(pivot);
685 pclust = sym_compare.prepare(pclust);
688 for (; begin != end; ++begin) {
690 cluster_type test(empty_orbit.prototype());
693 test.elements().push_back(*begin);
695 test = sym_compare.prepare(test);
699 if (sym_compare.equal(test, pclust)) {
700 result.insert(*begin);
709 template <
typename OrbitType>
711 std::string
const &class_name,
ClexBasis const &clex,
712 std::vector<OrbitType>
const &_tree,
713 std::map<
UnitCellCoord, std::set<UnitCellCoord> >
const &_nhood,
715 std::vector<std::string>
const &orbit_method_names,
716 std::vector<std::vector<std::string> >
const &flower_method_names,
717 std::vector<std::vector<std::string> >
const &dflower_method_names,
718 std::string
const &indent) {
722 Index N_flower = _nhood.size();
728 for (
auto const &nbor : _nhood) {
735 std::stringstream ss;
737 ss << indent << class_name <<
"::" << class_name <<
"() :\n"
738 << indent <<
" Clexulator_impl::Base(" << N_hood <<
", " << N_corr <<
", "
739 << N_flower <<
") {\n";
743 clex.
prim(), dof.second, indent +
" ");
745 std::vector<DoFType::ParamAllocation> allo =
748 if (allo.empty())
continue;
750 for (
const auto &el : allo) {
751 Index num_param = el.num_param;
753 ss << indent <<
" m_" << el.param_name
754 <<
"_param_key = m_params.allocate(\"" << el.param_name <<
"\", "
755 << el.param_dim <<
", " << num_param <<
", "
756 << (el.independent ?
"true" :
"false") <<
");\n";
759 if (dof.first !=
"occ")
760 ss << indent <<
" _register_local_dof(\"" << dof.first <<
"\", m_"
761 << dof.first <<
"_var_param_key.index());\n\n";
768 clex.
prim(), dof.second, indent +
" ");
770 std::vector<DoFType::ParamAllocation> allo =
773 if (allo.empty())
continue;
775 for (
const auto &el : allo) {
776 Index num_param = el.num_param;
778 throw std::runtime_error(
779 "Global DoF " + dof.first +
780 " requested invalid ClexParamPack allocation\n");
781 ss << indent <<
" m_" << el.param_name
782 <<
"_param_key = m_params.allocate(\"" << el.param_name <<
"\", "
783 << el.param_dim <<
", " << num_param <<
", "
784 << (el.independent ?
"true" :
"false") <<
");\n";
787 ss << indent <<
" _register_global_dof(\"" << dof.first <<
"\", m_"
788 << dof.first <<
"_var_param_key.index());\n\n";
794 <<
" m_corr_param_key = m_params.allocate(\"corr\", corr_size(), 1, "
798 for (
auto const &specialization :
800 for (
Index nf = 0; nf < orbit_method_names.size(); nf++) {
801 ss << indent <<
" m_orbit_func_table_" << ispec <<
"[" << nf <<
"] = &"
802 << class_name <<
"::" << orbit_method_names[nf] <<
"<"
803 << specialization.second <<
">;\n";
807 for (
Index nb = 0; nb < flower_method_names.size(); nb++) {
808 for (
Index nf = 0; nf < flower_method_names[nb].size(); nf++) {
809 ss << indent <<
" m_flower_func_table_" << ispec <<
"[" << nb <<
"]["
810 << nf <<
"] = &" << class_name <<
"::" << flower_method_names[nb][nf]
811 <<
"<" << specialization.second <<
">;\n";
816 for (
Index nb = 0; nb < dflower_method_names.size(); nb++) {
817 for (
Index nf = 0; nf < dflower_method_names[nb].size(); nf++) {
818 ss << indent <<
" m_delta_func_table_" << ispec <<
"[" << nb <<
"]["
819 << nf <<
"] = &" << class_name
820 <<
"::" << dflower_method_names[nb][nf] <<
"<"
821 << specialization.second <<
">;\n";
830 ss << indent <<
" m_weight_matrix.row(0) << " << W(0, 0) <<
", " << W(0, 1)
831 <<
", " << W(0, 2) <<
";\n";
832 ss << indent <<
" m_weight_matrix.row(1) << " << W(1, 0) <<
", " << W(1, 1)
833 <<
", " << W(1, 2) <<
";\n";
834 ss << indent <<
" m_weight_matrix.row(2) << " << W(2, 0) <<
", " << W(2, 1)
835 <<
", " << W(2, 2) <<
";\n\n";
841 std::set<UnitCellCoord> nbors;
843 std::inserter(nbors, nbors.begin()));
845 std::set<UnitCell> ucnbors;
846 for (
UnitCellCoord const &ucc : nbors) ucnbors.insert(ucc.unitcell());
848 if (!ucnbors.empty()) {
849 ss << indent <<
" m_neighborhood = std::set<UnitCell> {\n";
850 auto it = ucnbors.begin();
851 while (it != ucnbors.end()) {
853 ss << indent <<
" UnitCell(" << (*it)[0] <<
", " << (*it)[1] <<
", "
856 if (it != ucnbors.end()) {
861 ss << indent <<
" };\n";
865 ss << indent <<
" m_orbit_neighborhood.resize(corr_size());\n";
868 std::set<UnitCellCoord> nbors;
871 std::set<UnitCell> ucnbors;
872 for (
UnitCellCoord const &ucc : nbors) ucnbors.insert(ucc.unitcell());
874 Index proto_index = lno;
883 if (ucnbors.empty()) {
888 ss << indent <<
" m_orbit_neighborhood[" << lno
889 <<
"] = std::set<UnitCell> {\n";
891 auto it = ucnbors.begin();
892 while (it != ucnbors.end()) {
893 ss << indent <<
" UnitCell(" << (*it)[0] <<
", " << (*it)[1] <<
", "
896 if (it != ucnbors.end()) {
901 ss << indent <<
" };\n";
904 ss << indent <<
" m_orbit_neighborhood[" << lno
905 <<
"] = m_orbit_neighborhood[" << proto_index <<
"];\n";
910 ss << indent <<
"}\n\n";
915 template <
typename OrbitType>
917 std::string
const &class_name,
ClexBasis const &clex,
918 std::vector<OrbitType>
const &_tree,
919 std::vector<std::unique_ptr<OrbitFunctionTraits> >
const
921 std::map<
UnitCellCoord, std::set<UnitCellCoord> >
const &_nhood,
923 std::string result(indent +
"template<typename Scalar>\n" + indent +
"void " +
924 class_name +
"::_point_prepare(int nlist_ind) const {\n");
927 for (
auto const &doftype : clex.
site_bases()) {
931 doftype.second, indent +
" ");
937 doftype.second, indent +
" ");
940 for (
auto const &func_trait : _orbit_func_traits) {
941 result += func_trait->clexulator_point_prepare_string(
942 clex.
prim(), _nhood, _nlist, indent +
" ");
944 result += (indent +
"}\n");
948 template <
typename OrbitType>
950 std::string
const &class_name,
ClexBasis const &clex,
951 std::vector<OrbitType>
const &_tree,
952 std::vector<std::unique_ptr<OrbitFunctionTraits> >
const
954 std::map<
UnitCellCoord, std::set<UnitCellCoord> >
const &_nhood,
956 std::string result(indent +
"template<typename Scalar>\n" + indent +
"void " +
957 class_name +
"::_global_prepare() const {\n");
960 for (
auto const &doftype : clex.
site_bases()) {
963 clex.
prim(), _nhood, _nlist, doftype.second, indent +
"");
970 clex.
prim(), _nhood, _nlist, doftype.second, indent +
"");
973 for (
auto const &func_trait : _orbit_func_traits) {
974 result += func_trait->clexulator_global_prepare_string(clex.
prim(), _nhood,
975 _nlist, indent +
"");
978 result += (indent +
"}\n");
void set_dof_IDs(const std::vector< Index > &new_IDs)
bool accept(const FunctionVisitor &visitor)
Index n_orbits() const
Total number of BasisSet orbits.
std::map< DoFKey, std::vector< BasisSet > > const & site_bases() const
Const access to dictionary of all site BasisSets.
std::vector< BasisSet > BSetOrbit
ParsingDictionary< DoFType::Traits > const * dof_dict() const
std::map< DoFKey, std::vector< BasisSet > > const & global_bases() const
Const access to dictionary of all global BasisSets.
PrimType const & prim() const
Index n_functions() const
Total number of basis functions.
ClexBasisSpecs const & basis_set_specs() const
BSetOrbit const & bset_orbit(Index orbit_ind) const
Const access of BSetOrbit of orbit.
notstd::cloneable_ptr< ParamPackMixIn > m_param_pack_mix_in
std::vector< std::unique_ptr< FunctionVisitor > > const & _clust_function_visitors() const
void print_clexulator(std::string class_name, ClexBasis const &clex, std::vector< OrbitType > const &_tree, PrimNeighborList &_nlist, std::ostream &stream, double xtal_tol)
Print clexulator.
void print_param_pack(std::string class_name, ClexBasis const &clex, std::vector< OrbitType > const &_tree, PrimNeighborList &_nlist, std::ostream &stream, std::string const &_indent) const
Print ClexParamPack specialization.
std::vector< std::unique_ptr< OrbitFunctionTraits > > const & _orbit_func_traits() const
virtual std::string clexulator_global_prepare_string(Structure const &_prim, std::map< UnitCellCoord, std::set< UnitCellCoord > > const &_nhood, PrimNeighborList &_nlist, std::vector< BasisSet > const &site_bases, std::string const &indent) const
virtual std::string clexulator_point_prepare_string(Structure const &_prim, std::map< UnitCellCoord, std::set< UnitCellCoord > > const &_nhood, PrimNeighborList &_nlist, std::vector< BasisSet > const &site_bases, std::string const &indent) const
virtual std::string site_basis_description(BasisSet site_bset, Site site, Index site_ix) const
virtual std::vector< ParamAllocation > param_pack_allocation(Structure const &_prim, std::vector< BasisSet > const &_bases) const
virtual std::string clexulator_constructor_string(Structure const &_prim, std::vector< BasisSet > const &site_bases, std::string const &indent) const
ParamPackMixIn is interface class to control ClexParamPack portion of Clexulator printing Used primar...
std::map< std::string, std::string > const & scalar_specializations() const
Dictionary of pairs ("EvalMode", "ScalarType") These correspond to the underlying scalar type to be u...
The PrimNeighborList gives the coordinates of UnitCell that are neighbors of the origin UnitCell.
std::vector< Scalar > neighbor_indices(UnitCellCoordIterator _begin, UnitCellCoordIterator _end)
Get neighborlist indices of a collection of UnitCells, stored in.
Scalar neighbor_index(UnitCellCoord const &_ucc)
Get neighborlist index of UnitCellCoord.
Matrix3Type weight_matrix() const
Return the weighting matrix W used to define the canonical order.
Eigen::Matrix3l Matrix3Type
Structure specifies the lattice and atomic basis of a crystal.
const std::vector< xtal::Site > & basis() const
const MasterSymGroup & factor_group() const
SymGroup is a collection of symmetry operations that satisfy the group property The symmetry operatio...
static std::string NAME()
get a string with the name of the active mode
const UnitCell & unitcell() const
std::string to_string(ENUM val)
Return string representation of enum class.
OutputIterator flower_neighborhood(OrbitType const &orbit, OutputIterator result)
Iterate over all sites in an orbit and insert a UnitCellCoord.
std::tuple< std::string, std::string > clexulator_dflower_function_strings(std::string const &class_name, ClexBasis::BSetOrbit const &_bset_orbit, ClexBasis::BSetOrbit const &_site_bases, OrbitType const &_clust_orbit, std::function< std::string(Index, Index)> method_namer, std::map< UnitCellCoord, std::set< UnitCellCoord > > const &_nhood, PrimNeighborList &_nlist, std::vector< std::unique_ptr< FunctionVisitor > > const &visitors, FunctionVisitor const &prefactor_labeler, std::string const &indent)
void print_proto_clust_funcs(ClexBasis const &clex, std::ostream &out, std::vector< OrbitType > const &_tree)
std::string clexulator_constructor_definition(std::string const &class_name, ClexBasis const &clex, std::vector< OrbitType > const &_tree, std::map< UnitCellCoord, std::set< UnitCellCoord > > const &_nhood, PrimNeighborList &_nlist, ParamPackMixIn const &_param_pack_mix_in, std::vector< std::string > const &orbit_method_names, std::vector< std::vector< std::string > > const &flower_method_names, std::vector< std::vector< std::string > > const &dflower_method_names, std::string const &indent)
std::string clexulator_point_prepare_definition(std::string const &class_name, ClexBasis const &clex, std::vector< OrbitType > const &_tree, std::vector< std::unique_ptr< OrbitFunctionTraits > > const &orbit_func_traits, std::map< UnitCellCoord, std::set< UnitCellCoord > > const &_nhood, PrimNeighborList &_nlist, std::string const &indent)
std::set< UnitCellCoord > equiv_ucc(UCCIterType begin, UCCIterType end, UnitCellCoord const &_pivot, Structure const &_prim, IntegralClusterSymCompareType const &_sym_compare)
std::vector< std::string > flower_function_cpp_strings(ClexBasis::BSetOrbit _bset_orbit, std::function< BasisSet(BasisSet const &)> _bset_transform, OrbitType const &_clust_orbit, std::map< UnitCellCoord, std::set< UnitCellCoord > > const &_nhood, PrimNeighborList &_nlist, std::vector< std::unique_ptr< FunctionVisitor > > const &_visitors, UnitCellCoord const &_nbor)
nlist_index is the index of the basis site in the neighbor list
std::tuple< std::string, std::string > clexulator_flower_function_strings(std::string const &class_name, ClexBasis::BSetOrbit const &_bset_orbit, OrbitType const &_clust_orbit, std::function< std::string(Index, Index)> method_namer, std::map< UnitCellCoord, std::set< UnitCellCoord > > const &_nhood, PrimNeighborList &_nlist, std::vector< std::unique_ptr< FunctionVisitor > > const &visitor, std::string const &indent)
Print the flower function formulae for orbit.
std::map< UnitCellCoord, std::set< UnitCellCoord > > dependency_neighborhood(OrbitIterType begin, OrbitIterType end)
std::string clexulator_interface_declaration(std::string const &class_name, ClexBasis const &clex, ParamPackMixIn const &_param_pack_mix_in, std::string const &indent)
std::string clexulator_private_method_declarations(std::string const &class_name, ClexBasis const &clex, std::string const &indent)
std::string clexulator_member_declarations(std::string const &class_name, ClexBasis const &clex, ParamPackMixIn const &_param_pack_mix_in, std::vector< std::unique_ptr< OrbitFunctionTraits > > const &orbit_func_traits, Index N_flower, std::string const &indent)
std::tuple< std::string, std::string > clexulator_orbit_function_strings(std::string const &class_name, ClexBasis::BSetOrbit const &_bset_orbit, OrbitType const &_clust_orbit, std::function< std::string(Index, Index)> method_namer, PrimNeighborList &_nlist, std::vector< std::unique_ptr< FunctionVisitor > > const &visitors, std::string const &indent)
std::string clexulator_public_method_declarations(std::string const &class_name, ClexBasis const &clex, std::string const &indent)
std::vector< std::string > orbit_function_cpp_strings(ClexBasis::BSetOrbit _bset_orbit, OrbitType const &_clust_orbit, PrimNeighborList &_nlist, std::vector< std::unique_ptr< FunctionVisitor > > const &visitors)
std::string clexulator_global_prepare_definition(std::string const &class_name, ClexBasis const &clex, std::vector< OrbitType > const &_tree, std::vector< std::unique_ptr< OrbitFunctionTraits > > const &orbit_func_traits, std::map< UnitCellCoord, std::set< UnitCellCoord > > const &_nhood, PrimNeighborList &_nlist, std::string const &indent)
Traits const & traits(std::string const &dof_key)
Lookup DoFType::Traits in the global dictionary.
jsonParser & to_json(const ClexDescription &desc, jsonParser &json)
void write_prim(const xtal::BasicStructure &prim, fs::path filename, COORD_TYPE mode, bool include_va=false)
Write prim.json to file.
Index print_clust_basis(std::ostream &stream, BasisSet _clust_basis, IntegralCluster const &_prototype, Index func_ind=0, int space=18, char delim='\n')
bool contains(const Container &container, const T &value)
Equivalent to container.end() != std::find(container.begin(), container.end(), value)
bool valid_index(Index i)
INDEX_TYPE Index
For long integer indexing:
PrototypePrinter< IntegralCluster > ProtoSitesPrinter
T max(const T &A, const T &B)
Unary transformation that behaves as Identity (i.e. transform(arg) == arg is true)