CASM  1.1.0
A Clusters Approach to Statistical Mechanics
ClexBasis_impl.hh
Go to the documentation of this file.
1 #ifndef CASM_ClexBasis_impl
2 #define CASM_ClexBasis_impl
3 
7 #include "casm/clex/ClexBasis.hh"
16 
17 namespace CASM {
18 
20 template <typename OrbitType>
21 Index _orbit_max_poly_order(OrbitType const &orbit,
22  BasisFunctionSpecs const &basis_function_specs) {
23  auto it = basis_function_specs.orbit_branch_max_poly_order.find(orbit.size());
24  if (it != basis_function_specs.orbit_branch_max_poly_order.end()) {
25  return it->second;
26  }
27  return basis_function_specs.global_max_poly_order;
28 }
29 
30 template <typename OrbitIteratorType>
31 void ClexBasis::generate(OrbitIteratorType _orbit_begin,
32  OrbitIteratorType _orbit_end) {
33  std::vector<DoFKey> dof_keys =
35  std::vector<DoFKey> global_keys;
36  std::vector<DoFKey> local_keys;
37 
38  if (dof_keys.empty()) {
39  for (auto const &dof : m_global_bases) {
40  global_keys.push_back(dof.first);
41  }
42  for (auto const &dof : m_site_bases) {
43  local_keys.push_back(dof.first);
44  }
45  } else if (dof_keys.size() > 1 || dof_keys[0] != "none") {
46  // separate local_args from global_args
47  for (DoFKey const &key : dof_keys) {
48  if (m_global_bases.find(key) != m_global_bases.end()) {
49  global_keys.push_back(key);
50  } else if (m_site_bases.find(key) != m_site_bases.end()) {
51  local_keys.push_back(key);
52  } else {
53  assert(0);
54  std::stringstream ss;
55  ss << "Attempting to build Clex basis set, but missing degree of "
56  "freedom '"
57  << key << "'\n";
58  throw std::runtime_error(ss.str());
59  }
60  }
61  }
62  m_bset_tree.resize(std::distance(_orbit_begin, _orbit_end));
63 
64  auto bset_it = m_bset_tree.begin();
65  for (; _orbit_begin != _orbit_end; ++_orbit_begin, ++bset_it) {
66  auto const &orbit = *_orbit_begin;
67  Index max_poly_order =
68  _orbit_max_poly_order(orbit, basis_set_specs().basis_function_specs);
69  bset_it->reserve(orbit.size());
70  bset_it->push_back(_construct_prototype_basis(orbit, local_keys,
71  global_keys, max_poly_order));
72  for (Index j = 1; j < orbit.size(); j++)
73  bset_it->push_back((*(orbit.equivalence_map(j).first)) * (*bset_it)[0]);
74  }
75 }
76 
77 //*******************************************************************************************
78 // @param local_args[i][j] is BasisSet for i'th DoFspace at j'th site of cluster
79 // site 0 site 1 site 2
80 // DoFKey 0: displacement {x0,y0,z0} {x1, y1, z1} {x2,y2,z2}
81 // DoFKey 1: configuration {pA0,pB0} {} {pA2, pB2}
82 //
83 // Step 1: Get the kroenecker product of cluster permutation with DoF symrep
84 //
85 // permutation | kronecker prod | DoF Symrep (e.g., x--y displacement)
86 // [ 0 1 ] v [cos -sin]
87 // [ 1 0 ] XkX [sin cos]
88 //
89 // [x0] [ 0 0 cos -sin ] [x0]
90 // [y0] [ 0 0 sin cos ] [y0]
91 // S * [x1] = [ cos -sin 0 0 ] [x1]
92 // [x2] [ sin cos 0 0 ] [x2]
93 //
94 // ----------------------------------------------------------------------
95 //
96 // Step 2: mix-in @param global_args to get all_argsets
97 //
98 // GLOBAL ARGS
99 //
100 // strain { e1, e2, e3, e4, e5, e6}
101 // composition { comp_a, comp_b }
102 //
103 // arg_subsets = [ {x0,y0,z0,x1,y1,z1,x2,y2,z2},
104 // {pA0,pB0,pA2,pB2},
105 // {e1,e2,e3,e4,e5,e6},
106 // {comp_a,comp_b}]
107 //
108 template <typename OrbitType>
110  OrbitType const &_orbit, std::vector<DoFKey> const &local_keys,
111  std::vector<DoFKey> const &global_keys, Index max_poly_order) const {
112  // std::cout<<"In IntegralCluster::generate_clust_basis, the size of this
113  // cluster is:"<<size()<<std::endl; std::cout<<"valid_index evaluates
114  // to:"<<valid_index(max_poly_order)<<std::endl;
115 
116  // Default polynomial order is cluster size
117  // if(!valid_index(max_poly_order))
118  max_poly_order = max(max_poly_order, Index(_orbit.prototype().size()));
119 
120  // std::cout<<"Max_poly_order "<<max_poly_order<<std::endl;
121 
122  // record pointers to global dof arguments
123  std::vector<BasisSet const *> arg_subsets;
124  for (DoFKey const &key : global_keys) {
125  auto find_it = m_global_bases.find(key);
126  if (find_it != m_global_bases.end())
127  arg_subsets.push_back(&(find_it->second[0]));
128  else
129  throw std::runtime_error(
130  "Unable to construct basis sets. No known global DoF: " + key + "\n");
131  }
132 
133  // copy local site bases to a temporary location where we can alter their DoF
134  // IDs
135  std::vector<BasisSet> all_local;
136  all_local.reserve(local_keys.size());
137 
138  // Loop over dof's
139  for (DoFKey const &key : local_keys) {
140  // Make copies of local arguments to ensure that they are distinguishable by
141  // their DoF_IDs i.e., make copies in 'tlocal' and reset the DoF_IDs to
142  // {0,1,2,etc...}
143  auto find_it = m_site_bases.find(key);
144  if (find_it == m_site_bases.end())
145  throw std::runtime_error(
146  "Unable to construct basis sets. No known local DoF: " + key + "\n");
147 
148  std::vector<BasisSet> const &arg_vec(find_it->second);
149  // std::cout << "skdsa Working on DoF " << key << " size() : " <<
150  // find_it->second.size() << "\n";
151  std::vector<BasisSet> tlocal;
152  tlocal.reserve(_orbit.prototype().size());
153  // Loop over sites
154  for (Index i = 0; i < _orbit.prototype().size(); i++) {
155  tlocal.push_back(arg_vec[_orbit.prototype()[i].sublattice()]);
156  tlocal.back().set_dof_IDs(std::vector<Index>(1, i));
157  }
158 
159  all_local.push_back(ClexBasis_impl::construct_proto_dof_basis(
160  _orbit, BasisSet::ArgList(tlocal)));
161 
162  if (all_local.back().size()) arg_subsets.push_back(&(all_local.back()));
163  }
164  SymGroup clust_group(_orbit.equivalence_map(0).first,
165  _orbit.equivalence_map(0).second);
166  return m_basis_builder->build_proto(_orbit.prototype(), clust_group,
167  arg_subsets, max_poly_order, 1);
168 }
169 
170 namespace ClexBasis_impl {
171 template <typename OrbitType>
172 BasisSet construct_proto_dof_basis(OrbitType const &_orbit,
173  BasisSet::ArgList const &site_dof_sets) {
174  SymGroup clust_group(_orbit.equivalence_map(0).first,
175  _orbit.equivalence_map(0).second);
176 
177  std::vector<SymGroupRep const *> subspace_reps;
178  for (BasisSet const *site_bset_ptr : site_dof_sets) {
179  if (site_bset_ptr) {
180  subspace_reps.push_back(SymGroupRep::RemoteHandle(
181  clust_group, site_bset_ptr->basis_symrep_ID())
182  .rep_ptr());
183  } else {
184  subspace_reps.push_back(
186  .rep_ptr());
187  }
188  }
189  SymGroupRep const *permute_rep =
190  SymGroupRep::RemoteHandle(clust_group, _orbit.canonization_rep_ID())
191  .rep_ptr();
192 
193  BasisSet result = direct_sum(site_dof_sets);
195  permuted_direct_sum_rep(*(permute_rep), subspace_reps)));
196 
197  return result;
198 }
199 
200 } // namespace ClexBasis_impl
201 } // namespace CASM
202 #endif
void set_basis_symrep_ID(SymGroupRepID new_ID)
Definition: BasisSet.hh:125
std::map< DoFKey, std::vector< BasisSet > > m_global_bases
Dictionary of all global BasisSets, initialized.
Definition: ClexBasis.hh:143
std::map< DoFKey, std::vector< BasisSet > > m_site_bases
Dictionary of all site BasisSets, initialized on construction m_site_basis[DOF][b] gives site basis f...
Definition: ClexBasis.hh:140
notstd::cloneable_ptr< ClexBasisBuilder > m_basis_builder
pointer to class that constructs cluster functions
Definition: ClexBasis.hh:129
void generate(OrbitIterType _begin, OrbitIterType _end)
generate clust_basis for all equivalent clusters in
BasisSet _construct_prototype_basis(OrbitType const &_orbit, std::vector< DoFKey > const &local_keys, std::vector< DoFKey > const &global_keys, Index max_poly_order) const
std::vector< BSetOrbit > m_bset_tree
Collection of all cluster orbits (are we keeping this?)
Definition: ClexBasis.hh:135
ClexBasisSpecs const & basis_set_specs() const
Definition: ClexBasis.cc:75
SymGroupRepID add_representation(const SymGroupRep &new_rep) const
Definition: SymGroup.cc:702
SymGroup is a collection of symmetry operations that satisfy the group property The symmetry operatio...
Definition: SymGroup.hh:42
const MasterSymGroup & master_group() const
Definition: SymGroup.hh:73
SymGroupRep const * rep_ptr() const
Definition: SymGroupRep.hh:221
SymGroupRep is an alternative representation of a SymGroup for something other than real space....
Definition: SymGroupRep.hh:31
SymGroupRepHandle RemoteHandle
Definition: SymGroupRep.hh:35
static SymGroupRepID identity(Index dim)
Static function to construct an ID for identity representations.
BasisSet construct_proto_dof_basis(OrbitType const &_orbit, BasisSet::ArgList const &site_dof_sets)
Main CASM namespace.
Definition: APICommand.hh:8
SymGroupRep permuted_direct_sum_rep(const SymGroupRep &permute_rep, const std::vector< SymGroupRep const * > &sum_reps)
BasisSet direct_sum(BasisSet::ArgList const &_subs)
Definition: BasisSet.cc:1324
std::string DoFKey
Definition: DoFDecl.hh:7
INDEX_TYPE Index
For long integer indexing:
Definition: definitions.hh:39
T max(const T &A, const T &B)
Definition: CASM_math.hh:95
Index _orbit_max_poly_order(OrbitType const &orbit, BasisFunctionSpecs const &basis_function_specs)
allow basis_function_specs to specify max_poly_order by branch, orbit, etc.
Specify how to construct basis functions.
std::map< OrbitBranchSize, MaxPolyOrder > orbit_branch_max_poly_order
std::vector< DoFKey > dof_keys
Which DoF types to include in the basis functions.
BasisFunctionSpecs basis_function_specs