diff --git a/cmake/dca_config.cmake b/cmake/dca_config.cmake index 976f24253..1d660cead 100644 --- a/cmake/dca_config.cmake +++ b/cmake/dca_config.cmake @@ -100,15 +100,16 @@ endif() # TODO: Add more point groups and lattices. # Point group -set(DCA_POINT_GROUP "D4" CACHE STRING "Point group symmetry, options are: C6 | D4 | no_symmetry<2> | no_symmetry<3>.") -set_property(CACHE DCA_POINT_GROUP PROPERTY STRINGS C6 D4 no_symmetry<2> no_symmetry<3>) +set(DCA_POINT_GROUP "D4" CACHE STRING "Point group symmetry, options are: D6 | D4 | no_symmetry<2> | no_symmetry<3>.") +set_property(CACHE DCA_POINT_GROUP PROPERTY STRINGS D6 D4 no_symmetry<2> no_symmetry<3>) -if (DCA_POINT_GROUP STREQUAL "C6") +if (DCA_POINT_GROUP STREQUAL "D6") set(DCA_POINT_GROUP_INCLUDE - "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_hexagonal.hpp") + "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp") elseif (DCA_POINT_GROUP STREQUAL "D4") - set(DCA_POINT_GROUP_INCLUDE "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp") + set(DCA_POINT_GROUP_INCLUDE + "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp") elseif (DCA_POINT_GROUP STREQUAL "no_symmetry<2>") set(DCA_POINT_GROUP_INCLUDE "dca/phys/domains/cluster/symmetries/point_groups/no_symmetry.hpp") @@ -116,7 +117,7 @@ elseif (DCA_POINT_GROUP STREQUAL "no_symmetry<3>") set(DCA_POINT_GROUP_INCLUDE "dca/phys/domains/cluster/symmetries/point_groups/no_symmetry.hpp") else() - message(FATAL_ERROR "Please set DCA_POINT_GROUP to a valid option: C6 | D4 | no_symmetry<2> | no_symmetry<3>.") + message(FATAL_ERROR "Please set DCA_POINT_GROUP to a valid option: D6 | D4 | no_symmetry<2> | no_symmetry<3>.") endif() # Lattice type diff --git a/include/dca/phys/dca_step/symmetrization/derive_point_group.hpp b/include/dca/phys/dca_step/symmetrization/derive_point_group.hpp new file mode 100644 index 000000000..01649dc59 --- /dev/null +++ b/include/dca/phys/dca_step/symmetrization/derive_point_group.hpp @@ -0,0 +1,202 @@ +// Copyright (C) 2018 UT-Battelle, LLC +// All rights reserved. +// +// See LICENSE for terms of usage. +// See CITATION.md for citation guidelines, if DCA++ is used for scientific publications. +// +// Author: Tyler Sax (tylersax@gmail.com) +// +// Derives a 2D model's point group -- the built-in 2D holohedry pool filtered by the lattice geometry +// and by H0 invariance -- and compares it against the group realized from the model's declared +// DCA_point_group. Production symmetrization continues to use the DECLARED group: +// deriveAndComparePointGroup restores the declared symmetry state before returning and only +// reports divergences. The reports build a per-model map of models whose declaration disagrees with +// the symmetry encoded in their own Hamiltonian, which drives later declaration-free upgrades. + +#ifndef DCA_PHYS_DCA_STEP_SYMMETRIZATION_DERIVE_POINT_GROUP_HPP +#define DCA_PHYS_DCA_STEP_SYMMETRIZATION_DERIVE_POINT_GROUP_HPP + +#include +#include +#include +#include +#include +#include +#include + +#include "dca/function/domains.hpp" +#include "dca/function/function.hpp" +#include "dca/phys/dca_step/symmetrization/solve_orbital_op_signs.hpp" +#include "dca/phys/domains/cluster/cluster_symmetry.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" +#include "dca/phys/domains/cluster/symmetrization_algorithms/search_maximal_symmetry_group.hpp" +#include "dca/phys/domains/cluster/symmetrization_algorithms/set_symmetry_matrices.hpp" +#include "dca/phys/domains/quantum/electron_band_domain.hpp" +#include "dca/phys/domains/quantum/electron_spin_domain.hpp" +#include "dca/phys/domains/quantum/point_group_symmetry_element.hpp" + +namespace dca { +namespace phys { +// dca::phys:: + +namespace detail { +// dca::phys::detail:: + +// Geometric equality of two symmetry elements (same linear part .O and fractional translation .t), +// at the tolerance the symmetry search uses to deduplicate operations. +inline bool isSameSymmetryElement(const domains::point_group_symmetry_element& a, + const domains::point_group_symmetry_element& b) { + constexpr double tol = 1e-6; + if (a.DIMENSION != b.DIMENSION) + return false; + double diff = 0.; + for (int i = 0; i < a.DIMENSION * a.DIMENSION; ++i) + diff = std::max(diff, std::abs(a.O[i] - b.O[i])); + for (int i = 0; i < a.DIMENSION; ++i) + diff = std::max(diff, std::abs(a.t[i] - b.t[i])); + return diff < tol; +} + +inline bool containsSymmetryElement(const std::vector& set, + const domains::point_group_symmetry_element& op) { + for (const auto& element : set) + if (isSameSymmetryElement(element, op)) + return true; + return false; +} + +// Detects the initializeH0 lattice interface: the legacy lattices cannot feed the +// H0-invariance gate, so derivation skips them. +template +struct LatticeHasInitializeH0 : std::false_type {}; +template +struct LatticeHasInitializeH0(), std::declval()))>> + : std::true_type {}; + +// Makes PointGroup the live group of one cluster family, overwriting the previously realized group: +// clear the operation lists (the search only appends), re-search under the same geometric filter, +// resize the per-operation functions to the new count, and rebuild the symmetry tables. Assumes the +// family was already populated once by cluster_domain_symmetry_initializer. +template +void installPointGroup() { + using CS_k = domains::cluster_symmetry; + using CS_r = domains::cluster_symmetry; + using Family = typename CS_k::cluster_family_type; + + CS_k::sym_unit_cell_dmn_t::parameter_type::get_elements().clear(); + CS_k::sym_super_cell_dmn_t::parameter_type::get_elements().clear(); + domains::search_maximal_symmetry_group::execute(); + domains::search_maximal_symmetry_group::execute(); + CS_k::get_symmetry_matrix().reset(); + CS_r::get_symmetry_matrix().reset(); + CS_k::get_mapped_point().reset(); + CS_k::get_fold_phase().reset(); + CS_k::get_orbital_op().reset(); + domains::set_symmetry_matrices::execute(); +} + +} // namespace detail +// dca::phys:: + +// Derives the point group of a 2D model for one cluster family and returns a human-readable report +// of how it diverges from the declared group -- empty when they agree. Must be called right after +// cluster_domain_symmetry_initializer::execute() for the same family; +// the declared symmetry state is restored before returning, so production behavior is unchanged. +// 3D models (no 3D pool yet) and legacy lattices (no initializeH0) skip derivation entirely. +template +std::string deriveAndComparePointGroup(const Parameters& parameters) { + using Lattice = typename Model::lattice_type; + using RCluster = typename RClusterDmn::parameter_type; + using KCluster = typename domains::cluster_symmetry::dual_type; + using BDmn = func::dmn_0; + using SDmn = func::dmn_0; + using NuDmn = func::dmn_variadic; + using H0Type = + func::function, func::dmn_variadic>>; + + if constexpr (Lattice::DIMENSION != 2 || + !detail::LatticeHasInitializeH0::value) { + (void)parameters; + return ""; + } + else { + using KSymDmn = typename domains::cluster_symmetry::sym_super_cell_dmn_t; + using Element = domains::point_group_symmetry_element; + + // The realized declared group, populated by the initializer that just ran. Only the first + // get_size() entries are the live group: on a re-initialization (some tests run update_domains + // twice per process) the search zeroes the count but appends to the never-cleared element + // vector, so the vector can be longer than the group. The reference tracks the singleton + // through the group installs below; the copy preserves the declared ops. + const std::vector& realized = KSymDmn::parameter_type::get_elements(); + const int n_declared = KSymDmn::parameter_type::get_size(); + const std::vector declared(realized.begin(), realized.begin() + n_declared); + + // Derive: candidate pool -> same geometric filter -> H0-invariance gate. + detail::installPointGroup(); + + H0Type H0; + Model::initializeH0(parameters, H0); + + std::vector derived; + for (const int s : verifiedSymmetryOps(H0)) + derived.push_back(realized[s]); + + // Restore the declared state, and verify the restoration: every consumer of the symmetry + // domains must see exactly the state the declared initializer produced. + detail::installPointGroup(); + + if (KSymDmn::parameter_type::get_size() != n_declared) + throw std::logic_error( + "deriveAndComparePointGroup: failed to restore the declared symmetry state of " + + KCluster::get_name() + "."); + for (std::size_t i = 0; i < declared.size(); ++i) + if (!detail::isSameSymmetryElement(realized[i], declared[i])) + throw std::logic_error( + "deriveAndComparePointGroup: failed to restore the declared symmetry state of " + + KCluster::get_name() + "."); + + // Compare as sets and report the divergence, if any, naming the ops that differ. + std::vector underdeclared; + for (const auto& op : derived) + if (!detail::containsSymmetryElement(declared, op)) + underdeclared.push_back(op.describe()); + + std::vector unverified; + for (const auto& op : declared) + if (!detail::containsSymmetryElement(derived, op)) + unverified.push_back(op.describe()); + + if (underdeclared.empty() && unverified.empty()) + return ""; + + auto join = [](const std::vector& ops) { + std::string s; + for (std::size_t i = 0; i < ops.size(); ++i) + s += (i ? ", " : "") + ops[i]; + return s; + }; + + std::ostringstream report; + report << "derived-symmetry check [" << KCluster::get_name() << "]:\n" + << "\tdeclared group: " << declared.size() << " op(s); derived group: " << derived.size() + << " op(s).\n"; + if (!underdeclared.empty()) + report << "\tunder-declared: " << underdeclared.size() + << " derived H0-verified symmetry op(s) beyond the declared group " + << "(symmetry averaging left unexploited): " << join(underdeclared) << ".\n"; + if (!unverified.empty()) + report << "\tWARNING: " << unverified.size() + << " declared op(s) not reproduced by the derivation -- the op fails the " + << "H0-invariance check (or, the lattice is not in the pool's standard orientation): " + << join(unverified) << ".\n"; + return report.str(); + } +} + +} // namespace phys +} // namespace dca + +#endif // DCA_PHYS_DCA_STEP_SYMMETRIZATION_DERIVE_POINT_GROUP_HPP diff --git a/include/dca/phys/dca_step/symmetrization/solve_orbital_op_signs.hpp b/include/dca/phys/dca_step/symmetrization/solve_orbital_op_signs.hpp index ae2d5768f..80e602c55 100644 --- a/include/dca/phys/dca_step/symmetrization/solve_orbital_op_signs.hpp +++ b/include/dca/phys/dca_step/symmetrization/solve_orbital_op_signs.hpp @@ -29,9 +29,11 @@ // // The analytic models shipped with DCA++ have at most n_b = 3 orbitals, so once the gauge // sigma(0) = +1 is fixed there are at most 2^(n_b-1) <= 4 candidate sign vectors. We simply -// enumerate them and keep the one that satisfies every coupling constraint. Three conditions make +// enumerate them and keep the one that satisfies every coupling constraint. Four conditions make // an operation fail: // +// * a missing band image in the symmetry table (the -1 value recorded by set_symmetry_matrices +// when it finds no admissible image) means the op has no candidate permutation at all; // * a magnitude mismatch (an entry vanishing on only one side) means the permutation is not a // symmetry of H0; // * a non-real or non-unit ratio means the op needs a non-signed-permutation U_S (genuine orbital @@ -78,8 +80,18 @@ void solveSignsForOp(int s, int nb, int nk, const SymFunc& sym, const FoldFunc& // half of U_S (which orbital maps to which); it is k-independent for a point-group op, so read it // at k = 0. Only the signs that decorate it are unknown. std::vector image(nb); - for (int b = 0; b < nb; ++b) + for (int b = 0; b < nb; ++b) { image[b] = sym(0, b, s).second; + // set_symmetry_matrices records a silent -1 sentinel when its position/flavor matching finds + // no admissible image (its own throw is commented out), so the table cannot be assumed + // complete here. Reject the op before the sentinel is used to index H0. + if (image[b] < 0 || image[b] >= nb) + throw std::out_of_range( + "solveOrbitalOpSignsFromH0: no band image in the symmetry table for band " + + std::to_string(b) + " under op " + std::to_string(s) + + " -- the geometric position/flavor matching found no admissible image, so the op has no " + "candidate permutation."); + } // Gather one sign-product constraint per nonzero coupling, over all cluster momenta. Each nonzero // coupling forces sigma(b0) sigma(b1) to the +/-1 fold-corrected ratio of the two H0 entries. The diff --git a/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_hexagonal.hpp b/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_hexagonal.hpp deleted file mode 100644 index 70086253d..000000000 --- a/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_hexagonal.hpp +++ /dev/null @@ -1,81 +0,0 @@ -// Copyright (C) 2018 ETH Zurich -// Copyright (C) 2018 UT-Battelle, LLC -// All rights reserved. -// -// See LICENSE for terms of usage. -// See CITATION.md for citation guidelines, if DCA++ is used for scientific publications. -// -// Author: Peter Staar (taa@zurich.ibm.com) -// -// 2D hexagonal. - -#ifndef DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_HEXAGONAL_HPP -#define DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_HEXAGONAL_HPP - -#include "dca/phys/domains/cluster/symmetries/symmetry_operations/2d/Cn_2d.hpp" -#include "dca/phys/domains/cluster/symmetries/symmetry_operations/2d/Sn_2d.hpp" -#include "dca/util/type_list.hpp" - -namespace dca { -namespace phys { -namespace domains { -// dca::phys::domains:: - -// Group actions -typedef Cn_2D<1, 3> Cn_2D_1_3_type; -typedef Cn_2D<2, 3> Cn_2D_2_3_type; - -typedef Sn_2D<0, 3> Sn_2D_0_3_type; -typedef Sn_2D<1, 3> Sn_2D_1_3_type; -typedef Sn_2D<2, 3> Sn_2D_2_3_type; - -typedef Cn_2D<1, 6> Cn_2D_1_6_type; -typedef Cn_2D<2, 6> Cn_2D_2_6_type; -typedef Cn_2D<3, 6> Cn_2D_3_6_type; -typedef Cn_2D<4, 6> Cn_2D_4_6_type; -typedef Cn_2D<5, 6> Cn_2D_5_6_type; - -typedef Sn_2D<0, 6> Sn_2D_0_6_type; -typedef Sn_2D<1, 6> Sn_2D_1_6_type; -typedef Sn_2D<2, 6> Sn_2D_2_6_type; -typedef Sn_2D<3, 6> Sn_2D_3_6_type; -typedef Sn_2D<4, 6> Sn_2D_4_6_type; -typedef Sn_2D<5, 6> Sn_2D_5_6_type; - -// Point group: set of group actions -struct C3 { - typedef dca::util::Typelist point_group_type_list; -}; - -struct S3 { - typedef dca::util::Typelist point_group_type_list; -}; - -struct D3 { - typedef dca::util::Typelist - point_group_type_list; -}; - -struct C6 { - typedef dca::util::Typelist - point_group_type_list; -}; - -struct S6 { - typedef dca::util::Typelist - point_group_type_list; -}; - -struct D6 { - typedef dca::util::Typelist - point_group_type_list; -}; - -} // domains -} // phys -} // dca - -#endif // DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_HEXAGONAL_HPP diff --git a/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_oblique.hpp b/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_oblique.hpp deleted file mode 100644 index 3d52cc7ad..000000000 --- a/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_oblique.hpp +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright (C) 2018 ETH Zurich -// Copyright (C) 2018 UT-Battelle, LLC -// All rights reserved. -// -// See LICENSE for terms of usage. -// See CITATION.md for citation guidelines, if DCA++ is used for scientific publications. -// -// Author: Peter Staar (taa@zurich.ibm.com) -// -// 2D oblique. - -#ifndef DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_OBLIQUE_HPP -#define DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_OBLIQUE_HPP - -#include "dca/phys/domains/cluster/symmetries/symmetry_operations/2d/Cn_2d.hpp" -#include "dca/util/type_list.hpp" - -namespace dca { -namespace phys { -namespace domains { -// dca::phys::domains:: - -// Group actions -typedef Cn_2D<1, 2> Cn_2D_1_2_type; - -// Point group: set of group actions -typedef dca::util::Typelist C2; - -} // domains -} // phys -} // dca - -#endif // DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_OBLIQUE_HPP diff --git a/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_rectangular.hpp b/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_rectangular.hpp deleted file mode 100644 index 05f7e3135..000000000 --- a/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_rectangular.hpp +++ /dev/null @@ -1,38 +0,0 @@ -// Copyright (C) 2018 ETH Zurich -// Copyright (C) 2018 UT-Battelle, LLC -// All rights reserved. -// -// See LICENSE for terms of usage. -// See CITATION.md for citation guidelines, if DCA++ is used for scientific publications. -// -// Author: Peter Staar (taa@zurich.ibm.com) -// -// 2D rectangular. - -#ifndef DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_RECTANGULAR_HPP -#define DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_RECTANGULAR_HPP - -#include "dca/phys/domains/cluster/symmetries/symmetry_operations/2d/Sn_2d.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_oblique.hpp" // for C2 -#include "dca/util/type_list.hpp" - -namespace dca { -namespace phys { -namespace domains { -// dca::phys::domains:: - -// Group actions -typedef Sn_2D<0, 4> Sn_2D_0_4_type; -typedef Sn_2D<1, 4> Sn_2D_1_4_type; - -// Point group: set of group actions -typedef dca::util::Typelist Sx_2d; -typedef dca::util::Typelist Sy_2d; - -typedef dca::util::Append::type>::type D2; - -} // domains -} // phys -} // dca - -#endif // DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_RECTANGULAR_HPP diff --git a/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp b/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp deleted file mode 100644 index f0738f3a6..000000000 --- a/include/dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp +++ /dev/null @@ -1,74 +0,0 @@ -// Copyright (C) 2018 ETH Zurich -// Copyright (C) 2018 UT-Battelle, LLC -// All rights reserved. -// -// See LICENSE for terms of usage. -// See CITATION.md for citation guidelines, if DCA++ is used for scientific publications. -// -// Author: Peter Staar (taa@zurich.ibm.com) -// -// 2D square. - -#ifndef DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_SQUARE_HPP -#define DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_SQUARE_HPP - -#include "dca/phys/domains/cluster/symmetries/symmetry_operations/2d/Cn_2d.hpp" -#include "dca/phys/domains/cluster/symmetries/symmetry_operations/2d/Sn_2d.hpp" -#include "dca/phys/domains/cluster/symmetries/symmetry_operations/identity_group_operation.hpp" -#include "dca/util/type_list.hpp" - -namespace dca { -namespace phys { -namespace domains { -// dca::phys::domains:: - -// Group actions -typedef Cn_2D<1, 4> Cn_2D_1_4_type; -typedef Cn_2D<2, 4> Cn_2D_2_4_type; -typedef Cn_2D<3, 4> Cn_2D_3_4_type; -typedef Cn_2D<4, 4> Cn_2D_4_4_type; - -typedef Sn_2D<0, 8> Sn_2D_0_8_type; -typedef Sn_2D<1, 8> Sn_2D_1_8_type; -typedef Sn_2D<2, 8> Sn_2D_2_8_type; -typedef Sn_2D<3, 8> Sn_2D_3_8_type; -typedef Sn_2D<4, 8> Sn_2D_4_8_type; -typedef Sn_2D<5, 8> Sn_2D_5_8_type; -typedef Sn_2D<6, 8> Sn_2D_6_8_type; -typedef Sn_2D<7, 8> Sn_2D_7_8_type; -typedef Sn_2D<8, 8> Sn_2D_8_8_type; - -// Point group: set of group actions -struct C4 { - typedef dca::util::Typelist - point_group_type_list; -}; - -struct S4 { - typedef dca::util::Typelist - point_group_type_list; -}; - -struct S4_plus { - typedef dca::util::Typelist, Cn_2D_2_4_type, Sn_2D_0_8_type, Sn_2D_2_8_type> - point_group_type_list; -}; - -struct S8 { - typedef dca::util::Typelist> - point_group_type_list; -}; - -struct D4 { - using point_group_type_list = - dca::util::Typelist, Sn_2D<1, 8>, Sn_2D<2, 8>, Sn_2D<3, 8>, Cn_2D<1, 4>, - Cn_2D<2, 4>, Cn_2D<3, 4>, identity_group_operation<2>>; -}; - -} // namespace domains -} // namespace phys -} // namespace dca - -#endif // DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_2D_SQUARE_HPP diff --git a/include/dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp b/include/dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp new file mode 100644 index 000000000..c7eec398f --- /dev/null +++ b/include/dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp @@ -0,0 +1,60 @@ +// Copyright (C) 2018 UT-Battelle, LLC +// All rights reserved. +// +// See LICENSE for terms of usage. +// See CITATION.md for citation guidelines, if DCA++ is used for scientific publications. +// +// Author: Tyler Sax +// +// The two 2D crystallographic holohedries and the candidate pool they generate. +// +// D4 (square holohedry, order 8) and D6 (hexagonal holohedry, order 12) are the two maximal point +// groups in 2D. By the crystallographic restriction, every 2D crystallographic point group is a +// subgroup of one of them, so they are the only primitives needed: the lower-symmetry groups +// (rectangular D2, oblique C2, trigonal C3/D3, ...) are not declared per model but derived at +// runtime from the pool by the geometry filter (search_symmetry_group: is_lattice_compatible + +// is_unit_cell_compatible) and the H0-invariance gate. + +#ifndef DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_HOLOHEDRIES_2D_HPP +#define DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_HOLOHEDRIES_2D_HPP + +#include "dca/phys/domains/cluster/symmetries/symmetry_operations/2d/Cn_2d.hpp" +#include "dca/phys/domains/cluster/symmetries/symmetry_operations/2d/Sn_2d.hpp" +#include "dca/phys/domains/cluster/symmetries/symmetry_operations/identity_group_operation.hpp" +#include "dca/util/type_list.hpp" + +namespace dca { +namespace phys { +namespace domains { +// dca::phys::domains:: + +// Square holohedry (order 8): the three C4 rotations, four mirrors (reflection lines at n*pi/4, +// n={0...3}), and the identity. +struct D4 { + using point_group_type_list = + dca::util::Typelist, Sn_2D<1, 8>, Sn_2D<2, 8>, Sn_2D<3, 8>, Cn_2D<1, 4>, + Cn_2D<2, 4>, Cn_2D<3, 4>, identity_group_operation<2>>; +}; + +// Hexagonal holohedry (order 12): the five C6 rotations, six mirrors (reflection lines at n*pi/6, +// n = 0..5), and the identity. +struct D6 { + using point_group_type_list = + dca::util::Typelist, Cn_2D<2, 6>, Cn_2D<3, 6>, Cn_2D<4, 6>, Cn_2D<5, 6>, + Sn_2D<0, 12>, Sn_2D<1, 12>, Sn_2D<2, 12>, Sn_2D<3, 12>, Sn_2D<4, 12>, + Sn_2D<5, 12>, identity_group_operation<2>>; +}; + +// Universal 2D candidate pool = square holohedry D4 U hexagonal holohedry D6. Overlapping ops +// (identity, the C2 rotation) appear twice; search_symmetry_group::is_duplicate collapses them at +// populate time, so the union need not be hand-deduplicated. +struct holohedry_pool_2D { + using point_group_type_list = + dca::util::Append::type; +}; + +} // namespace domains +} // namespace phys +} // namespace dca + +#endif // DCA_PHYS_DOMAINS_CLUSTER_SYMMETRIES_POINT_GROUPS_2D_HOLOHEDRIES_2D_HPP diff --git a/include/dca/phys/domains/quantum/point_group_symmetry_element.hpp b/include/dca/phys/domains/quantum/point_group_symmetry_element.hpp index c61569ab8..9a808aae2 100644 --- a/include/dca/phys/domains/quantum/point_group_symmetry_element.hpp +++ b/include/dca/phys/domains/quantum/point_group_symmetry_element.hpp @@ -13,6 +13,7 @@ #define DCA_PHYS_DOMAINS_QUANTUM_POINT_GROUP_SYMMETRY_ELEMENT_HPP #include +#include #include namespace dca { @@ -38,6 +39,9 @@ class point_group_symmetry_element { void transform(const double* t0, double* t1) const; + // A short human-readable label for the operation. + std::string describe() const; + template void to_JSON(stream_type& ss) const; diff --git a/include/dca/phys/models/analytic_hamiltonians/fe_as_lattice.hpp b/include/dca/phys/models/analytic_hamiltonians/fe_as_lattice.hpp index 802beae01..6a31b41e1 100644 --- a/include/dca/phys/models/analytic_hamiltonians/fe_as_lattice.hpp +++ b/include/dca/phys/models/analytic_hamiltonians/fe_as_lattice.hpp @@ -17,7 +17,7 @@ #include "dca/function/domains.hpp" #include "dca/function/function.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/bilayer_lattice.hpp" #include "dca/phys/models/analytic_hamiltonians/cluster_shape_type.hpp" #include "dca/phys/models/traits.hpp" diff --git a/include/dca/phys/models/analytic_hamiltonians/threeband_hubbard.hpp b/include/dca/phys/models/analytic_hamiltonians/threeband_hubbard.hpp index e4a5ab094..34c6220e3 100644 --- a/include/dca/phys/models/analytic_hamiltonians/threeband_hubbard.hpp +++ b/include/dca/phys/models/analytic_hamiltonians/threeband_hubbard.hpp @@ -21,7 +21,7 @@ #include "dca/function/domains.hpp" #include "dca/function/function.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/cluster/symmetries/point_groups/no_symmetry.hpp" #include "dca/phys/models/analytic_hamiltonians/cluster_shape_type.hpp" #include "dca/util/type_list.hpp" diff --git a/include/dca/phys/models/analytic_hamiltonians/twoband_Cu.hpp b/include/dca/phys/models/analytic_hamiltonians/twoband_Cu.hpp index c8b2e65a0..56dff502e 100644 --- a/include/dca/phys/models/analytic_hamiltonians/twoband_Cu.hpp +++ b/include/dca/phys/models/analytic_hamiltonians/twoband_Cu.hpp @@ -21,7 +21,7 @@ #include "dca/function/domains.hpp" #include "dca/function/function.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/cluster/symmetries/point_groups/no_symmetry.hpp" #include "dca/phys/models/analytic_hamiltonians/cluster_shape_type.hpp" #include "dca/util/type_list.hpp" diff --git a/include/dca/phys/parameters/parameters.hpp b/include/dca/phys/parameters/parameters.hpp index b9bf52383..b1f66a280 100644 --- a/include/dca/phys/parameters/parameters.hpp +++ b/include/dca/phys/parameters/parameters.hpp @@ -40,6 +40,7 @@ #include "dca/phys/parameters/model_parameters.hpp" #include "dca/phys/parameters/output_parameters.hpp" #include "dca/phys/parameters/physics_parameters.hpp" +#include "dca/phys/dca_step/symmetrization/derive_point_group.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" #include "dca/phys/domains/cluster/cluster_domain_family.hpp" #include "dca/phys/domains/cluster/cluster_domain_initializer.hpp" @@ -138,6 +139,16 @@ class Parameters : public AnalysisParameters, void update_model(); void update_domains(); + // Derives the point group of one cluster family from the holohedry pool + H0 and prints how it + // diverges from the declared group (rank 0; silent on agreement). The declared symmetry state is + // restored by the check, so production symmetrization is unchanged. + template + void checkDerivedSymmetry() const { + const std::string report = deriveAndComparePointGroup(*this); + if (!report.empty() && concurrency_.id() == concurrency_.first()) + std::cout << report; + } + int get_buffer_size(const concurrency_type& concurrency) const; void pack(const concurrency_type& concurrency, char* buffer, int buffer_size, int& position) const; void unpack(const concurrency_type& concurrency, char* buffer, int buffer_size, int& position); @@ -285,8 +296,8 @@ void ParametersreadWrite(read_obj); // Detect model-section input mistakes while the parsed tree is still live (before close_file). - // Only the JSON reader tracks which sections were read; HDF5 as input is realistically - // machine-generated, so the access check is not implemented for that path + // Only the JSON reader tracks which sections were read; HDF5 as input is realistically + // machine-generated, so the access check is not implemented for that path if constexpr (std::is_same_v) { checkModelSections(read_obj.topLevelGroupAccess(), filename); } @@ -335,6 +346,10 @@ void Parameters::execute(); + // The check runs immediately after the initializer: the derivation temporarily overwrites + // this family's symmetry singletons with the pool-derived group and then restores exactly + // the state the line above just produced. + checkDerivedSymmetry(); if (concurrency_.id() == concurrency_.first()) KClusterDmn::parameter_type::print(std::cout); @@ -344,6 +359,7 @@ void Parameters::execute(); + checkDerivedSymmetry(); domains::MomentumExchangeDomain::initialize(*this); @@ -355,6 +371,7 @@ void Parameters::execute(); + checkDerivedSymmetry(); if (concurrency_.id() == concurrency_.first()) KQHostDmn::parameter_type::print(std::cout); @@ -364,6 +381,7 @@ void Parameters::execute(); + checkDerivedSymmetry(); if (concurrency_.id() == concurrency_.first()) KQFineDmn::parameter_type::print(std::cout); @@ -381,6 +399,7 @@ void Parameters::execute(); + checkDerivedSymmetry(); if (concurrency_.id() == concurrency_.first()) KTpHostDmn::parameter_type::print(std::cout); diff --git a/src/phys/domains/quantum/point_group_symmetry_element.cpp b/src/phys/domains/quantum/point_group_symmetry_element.cpp index 9c40ea952..82f1e824b 100644 --- a/src/phys/domains/quantum/point_group_symmetry_element.cpp +++ b/src/phys/domains/quantum/point_group_symmetry_element.cpp @@ -11,7 +11,10 @@ #include "dca/phys/domains/quantum/point_group_symmetry_element.hpp" +#include #include +#include +#include namespace dca { namespace phys { @@ -80,6 +83,70 @@ void point_group_symmetry_element::transform(const double* t0, double* t1) const t1[i] += t[i]; } +namespace { +// Writes the angle (num / den) * pi in lowest terms, e.g. 0, pi, pi/2, 2pi/3. +std::string formatPiFraction(int num, int den) { + if (num == 0) + return "0"; + + const int g = std::gcd(num, den); + num /= g; + den /= g; + + std::ostringstream angle; + if (num > 1) + angle << num; + angle << "pi"; + if (den > 1) + angle << "/" << den; + + return angle.str(); +} +} // namespace + +std::string point_group_symmetry_element::describe() const { + std::ostringstream label; + + if (DIMENSION == 2) { + // O is column major, so its first column (O[0], O[1]) is (cos, sin) of the rotation angle for a + // proper rotation (det +1) and (cos, sin) of twice the mirror-line angle for a reflection (det + // -1). Each operation gets a Schoenflies name (Cn^k for rotation, and sigma for reflection) and + // a geometric description. + // + // Rotations are decoded in twelfths of a full turn, and mirror lines are decoded in twelfths of + // pi. Both are reported in radians. + constexpr int kTurn = 12; + const double det = O[0] * O[3] - O[2] * O[1]; + if (det > 0.) { + const long raw = std::lround(std::atan2(O[1], O[0]) * kTurn / (2. * M_PI)); + const int t = static_cast((raw % kTurn + kTurn) % kTurn); + if (t == 0) { + label << "E (identity)"; + } + else { + const int g = std::gcd(t, kTurn); + label << "C" << kTurn / g; + if (t / g > 1) + label << "^" << t / g; + // A rotation by t twelfths of a turn is an angle of 2 pi t / 12 = t pi / 6. + label << " (rotation " << formatPiFraction(t, kTurn / 2) << " rad)"; + } + } + else { + // The mirror-line angle is half the angle carried by the first column, so halving turns + // twelfths of a turn into twelfths of pi and the mirror line is m * pi / 12. + const long raw = std::lround(std::atan2(O[1], O[0]) * kTurn / (2. * M_PI)); + const int m = static_cast((raw % kTurn + kTurn) % kTurn); + label << "sigma (mirror @ " << formatPiFraction(m, kTurn) << " rad)"; + } + } + else { + label << DIMENSION << "D symmetry element"; + } + + return label.str(); +} + } // namespace domains } // namespace phys } // namespace dca diff --git a/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_interband/bilayer_lattice_Nc1_interband.cpp b/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_interband/bilayer_lattice_Nc1_interband.cpp index c068ac3a1..7ea7e098a 100644 --- a/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_interband/bilayer_lattice_Nc1_interband.cpp +++ b/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_interband/bilayer_lattice_Nc1_interband.cpp @@ -29,7 +29,7 @@ #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_intra_plus_interband/bilayer_lattice_Nc1_intra_plus_interband.cpp b/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_intra_plus_interband/bilayer_lattice_Nc1_intra_plus_interband.cpp index 7b3427730..500c8db46 100644 --- a/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_intra_plus_interband/bilayer_lattice_Nc1_intra_plus_interband.cpp +++ b/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_intra_plus_interband/bilayer_lattice_Nc1_intra_plus_interband.cpp @@ -40,7 +40,7 @@ using McOptions = MockMcOptions; #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_intraband/bilayer_lattice_Nc1_intraband.cpp b/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_intraband/bilayer_lattice_Nc1_intraband.cpp index 16f8d9bef..68a2bc03f 100644 --- a/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_intraband/bilayer_lattice_Nc1_intraband.cpp +++ b/test/integration/cluster_solver/ctaux/bilayer_lattice/Nc1_intraband/bilayer_lattice_Nc1_intraband.cpp @@ -38,7 +38,7 @@ using McOptions = MockMcOptions; #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/integration/cluster_solver/ctaux/square_lattice/Nc4_nn/square_lattice_Nc4_nn.cpp b/test/integration/cluster_solver/ctaux/square_lattice/Nc4_nn/square_lattice_Nc4_nn.cpp index 4c22ccb6b..b13c0a084 100644 --- a/test/integration/cluster_solver/ctaux/square_lattice/Nc4_nn/square_lattice_Nc4_nn.cpp +++ b/test/integration/cluster_solver/ctaux/square_lattice/Nc4_nn/square_lattice_Nc4_nn.cpp @@ -39,7 +39,7 @@ using McOptions = MockMcOptions; #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/integration/cluster_solver/ctaux/square_lattice/Nc4_onSite_plus_nn/square_lattice_Nc4_onSite_plus_nn.cpp b/test/integration/cluster_solver/ctaux/square_lattice/Nc4_onSite_plus_nn/square_lattice_Nc4_onSite_plus_nn.cpp index bf972c72e..60d0307a5 100644 --- a/test/integration/cluster_solver/ctaux/square_lattice/Nc4_onSite_plus_nn/square_lattice_Nc4_onSite_plus_nn.cpp +++ b/test/integration/cluster_solver/ctaux/square_lattice/Nc4_onSite_plus_nn/square_lattice_Nc4_onSite_plus_nn.cpp @@ -39,7 +39,7 @@ using McOptions = MockMcOptions; #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/integration/cluster_solver/ctint/ctint_double_update_comparison_test.cpp b/test/integration/cluster_solver/ctint/ctint_double_update_comparison_test.cpp index 33104e949..1af69d9fc 100644 --- a/test/integration/cluster_solver/ctint/ctint_double_update_comparison_test.cpp +++ b/test/integration/cluster_solver/ctint/ctint_double_update_comparison_test.cpp @@ -38,7 +38,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_step/cluster_solver/ctint/walker/ctint_walker_cpu_submatrix.hpp" #include "test/unit/phys/dca_step/cluster_solver/ctint/walker/walker_wrapper_submatrix.hpp" #include "test/unit/phys/dca_step/cluster_solver/ctint/walker/walker_wrapper.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/fe_as_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_threading/no_threading.hpp" diff --git a/test/integration/cluster_solver/ctint/ctint_fe_as_test.cpp b/test/integration/cluster_solver/ctint/ctint_fe_as_test.cpp index d2722521c..dea7874a9 100644 --- a/test/integration/cluster_solver/ctint/ctint_fe_as_test.cpp +++ b/test/integration/cluster_solver/ctint/ctint_fe_as_test.cpp @@ -33,7 +33,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_data/dca_data.hpp" #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/fe_as_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_threading/no_threading.hpp" diff --git a/test/integration/cluster_solver/ctint/ctint_hund_lattice_test.cpp b/test/integration/cluster_solver/ctint/ctint_hund_lattice_test.cpp index 4b3ac5b4c..d0af55bb1 100644 --- a/test/integration/cluster_solver/ctint/ctint_hund_lattice_test.cpp +++ b/test/integration/cluster_solver/ctint/ctint_hund_lattice_test.cpp @@ -32,7 +32,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_data/dca_data.hpp" #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/hund_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_threading/no_threading.hpp" diff --git a/test/integration/cluster_solver/ctint/ctint_square_lattice_test.cpp b/test/integration/cluster_solver/ctint/ctint_square_lattice_test.cpp index d58c0cfb8..63d867952 100644 --- a/test/integration/cluster_solver/ctint/ctint_square_lattice_test.cpp +++ b/test/integration/cluster_solver/ctint/ctint_square_lattice_test.cpp @@ -32,7 +32,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_data/dca_data.hpp" #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_threading/no_threading.hpp" diff --git a/test/integration/cluster_solver/ctint/ctint_square_lattice_test_gpu.cpp b/test/integration/cluster_solver/ctint/ctint_square_lattice_test_gpu.cpp index 79464fcf9..248827a7c 100644 --- a/test/integration/cluster_solver/ctint/ctint_square_lattice_test_gpu.cpp +++ b/test/integration/cluster_solver/ctint/ctint_square_lattice_test_gpu.cpp @@ -35,7 +35,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_data/dca_data.hpp" #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_threading/no_threading.hpp" diff --git a/test/integration/cluster_solver/ctint/ctint_square_lattice_tp_test.cpp b/test/integration/cluster_solver/ctint/ctint_square_lattice_tp_test.cpp index 17ee70a33..62cf87ca5 100644 --- a/test/integration/cluster_solver/ctint/ctint_square_lattice_tp_test.cpp +++ b/test/integration/cluster_solver/ctint/ctint_square_lattice_tp_test.cpp @@ -36,7 +36,7 @@ using McOptions = MockMcOptions; #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_concurrency/no_concurrency.hpp" diff --git a/test/integration/cluster_solver/shared_tools/accumulation/tp/test_setup.hpp b/test/integration/cluster_solver/shared_tools/accumulation/tp/test_setup.hpp index 8f94854b1..b58f6f406 100644 --- a/test/integration/cluster_solver/shared_tools/accumulation/tp/test_setup.hpp +++ b/test/integration/cluster_solver/shared_tools/accumulation/tp/test_setup.hpp @@ -19,7 +19,7 @@ #include "dca/io/json/json_reader.hpp" #include "dca/phys/parameters/parameters.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/structs/interaction_vertices.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/integration/cluster_solver/stdthread_qmci/gpu/ctint_double_update_comparison_test.cpp b/test/integration/cluster_solver/stdthread_qmci/gpu/ctint_double_update_comparison_test.cpp index 445bebfa7..4c50f4a96 100644 --- a/test/integration/cluster_solver/stdthread_qmci/gpu/ctint_double_update_comparison_test.cpp +++ b/test/integration/cluster_solver/stdthread_qmci/gpu/ctint_double_update_comparison_test.cpp @@ -26,7 +26,7 @@ #include "dca/phys/dca_data/dca_data.hpp" #include "dca/parallel//no_concurrency/no_concurrency.hpp" #include "test/unit/phys/dca_step/cluster_solver/ctint/walker/walker_wrapper_submatrix.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/fe_as_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_threading/no_threading.hpp" diff --git a/test/integration/cluster_solver/stdthread_qmci/gpu/stdthread_ctaux_gpu_tp_test.cpp b/test/integration/cluster_solver/stdthread_qmci/gpu/stdthread_ctaux_gpu_tp_test.cpp index 9d78666f3..cfcf665bf 100644 --- a/test/integration/cluster_solver/stdthread_qmci/gpu/stdthread_ctaux_gpu_tp_test.cpp +++ b/test/integration/cluster_solver/stdthread_qmci/gpu/stdthread_ctaux_gpu_tp_test.cpp @@ -40,7 +40,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_concurrency/no_concurrency.hpp" diff --git a/test/integration/cluster_solver/stdthread_qmci/gpu/stdthread_ctint_gpu_tp_test.cpp b/test/integration/cluster_solver/stdthread_qmci/gpu/stdthread_ctint_gpu_tp_test.cpp index 004a48c49..827b01e29 100644 --- a/test/integration/cluster_solver/stdthread_qmci/gpu/stdthread_ctint_gpu_tp_test.cpp +++ b/test/integration/cluster_solver/stdthread_qmci/gpu/stdthread_ctint_gpu_tp_test.cpp @@ -35,7 +35,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_concurrency/no_concurrency.hpp" diff --git a/test/integration/cluster_solver/stdthread_qmci/stdthread_ctaux_tp_test.cpp b/test/integration/cluster_solver/stdthread_qmci/stdthread_ctaux_tp_test.cpp index b9516c765..09f712210 100644 --- a/test/integration/cluster_solver/stdthread_qmci/stdthread_ctaux_tp_test.cpp +++ b/test/integration/cluster_solver/stdthread_qmci/stdthread_ctaux_tp_test.cpp @@ -41,7 +41,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" #include "dca/phys/domains/cluster/momentum_exchange_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/time_and_frequency/frequency_exchange_domain.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" diff --git a/test/integration/cluster_solver/stdthread_qmci/stdthread_ctint_cluster_solver_io_test.cpp b/test/integration/cluster_solver/stdthread_qmci/stdthread_ctint_cluster_solver_io_test.cpp index ffe5db075..0e2ab0944 100644 --- a/test/integration/cluster_solver/stdthread_qmci/stdthread_ctint_cluster_solver_io_test.cpp +++ b/test/integration/cluster_solver/stdthread_qmci/stdthread_ctint_cluster_solver_io_test.cpp @@ -37,7 +37,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/mpi_concurrency/mpi_concurrency.hpp" diff --git a/test/integration/cluster_solver/stdthread_qmci/stdthread_ctint_cluster_solver_test.hpp b/test/integration/cluster_solver/stdthread_qmci/stdthread_ctint_cluster_solver_test.hpp index dd724a41e..872eb3e9c 100644 --- a/test/integration/cluster_solver/stdthread_qmci/stdthread_ctint_cluster_solver_test.hpp +++ b/test/integration/cluster_solver/stdthread_qmci/stdthread_ctint_cluster_solver_test.hpp @@ -28,7 +28,7 @@ #include "dca/config/profiler.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_concurrency/no_concurrency.hpp" diff --git a/test/integration/exact_diagonalization_advanced/ed_cluster_solver_test_helper.hpp b/test/integration/exact_diagonalization_advanced/ed_cluster_solver_test_helper.hpp index 662a4f030..d503a6c1d 100644 --- a/test/integration/exact_diagonalization_advanced/ed_cluster_solver_test_helper.hpp +++ b/test/integration/exact_diagonalization_advanced/ed_cluster_solver_test_helper.hpp @@ -21,7 +21,7 @@ #include "dca/phys/dca_data/dca_data.hpp" #include "dca/phys/dca_data/dca_data_real_freq.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/integration/exact_diagonalization_advanced/hamiltonian_test.cpp b/test/integration/exact_diagonalization_advanced/hamiltonian_test.cpp index 469a7eb9c..3aa3a0dfc 100644 --- a/test/integration/exact_diagonalization_advanced/hamiltonian_test.cpp +++ b/test/integration/exact_diagonalization_advanced/hamiltonian_test.cpp @@ -23,7 +23,7 @@ #include "dca/parallel/no_concurrency/no_concurrency.hpp" #include "dca/phys/dca_step/cluster_solver/exact_diagonalization_advanced/fock_space.hpp" #include "dca/phys/dca_step/cluster_solver/exact_diagonalization_advanced/options.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" diff --git a/test/integration/phys/lattice_mapping/lattice_mapping_sp_test.cpp b/test/integration/phys/lattice_mapping/lattice_mapping_sp_test.cpp index f397210dd..3e5c75fd6 100644 --- a/test/integration/phys/lattice_mapping/lattice_mapping_sp_test.cpp +++ b/test/integration/phys/lattice_mapping/lattice_mapping_sp_test.cpp @@ -39,7 +39,7 @@ using McOptions = MockMcOptions; #include "dca/profiling/null_profiler.hpp" #include "dca/phys/dca_step/cluster_solver/cluster_solver_id.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/integration/phys/symmetrization/CMakeLists.txt b/test/integration/phys/symmetrization/CMakeLists.txt index fd3ba98d8..7653c0dea 100644 --- a/test/integration/phys/symmetrization/CMakeLists.txt +++ b/test/integration/phys/symmetrization/CMakeLists.txt @@ -22,6 +22,17 @@ dca_add_gtest(symmetrize_characterization_threeband_D4_test TEST_DEFINES ThreebandD4 ) +# Regression case for solveSignsForOp's -1 guard: Kagome produces the -1 which the solver +# must reject instead of indexing H0 out of bounds. +dca_add_gtest(symmetrize_characterization_kagome_test + FAST + GTEST_MPI_MAIN + INCLUDE_DIRS ${DCA_INCLUDES};${PROJECT_SOURCE_DIR};${FFTW_INCLUDE_DIR} + LIBS ${DCA_LIBS} + CUSTOM_SOURCE symmetrize_characterization_test.cpp + TEST_DEFINES KagomeNoSym + ) + dca_add_gtest(symmetrize_characterization_singleband_chain_test FAST GTEST_MPI_MAIN diff --git a/test/integration/phys/symmetrization/kagome_input.json b/test/integration/phys/symmetrization/kagome_input.json new file mode 100644 index 000000000..0df6aae0d --- /dev/null +++ b/test/integration/phys/symmetrization/kagome_input.json @@ -0,0 +1,31 @@ +{ + "physics": { + "beta" : 1., + "chemical-potential" : 0. + }, + + "Kagome-Hubbard-model": + { + "t" : 1., + "U" : 2. + }, + + "domains": { + "real-space-grids": { + "cluster": [[2, 0], [0, 2]], + "sp-host": [[8, 0], [0, 8]] + }, + + "imaginary-time": { + "sp-time-intervals": 128 + }, + + "imaginary-frequency": { + "sp-fermionic-frequencies": 64 + } + }, + + "DCA": { + "interacting-orbitals": [0, 1, 2] + } +} diff --git a/test/integration/phys/symmetrization/symmetrize_characterization_test.cpp b/test/integration/phys/symmetrization/symmetrize_characterization_test.cpp index 558f10bf1..495ab4729 100644 --- a/test/integration/phys/symmetrization/symmetrize_characterization_test.cpp +++ b/test/integration/phys/symmetrization/symmetrize_characterization_test.cpp @@ -40,6 +40,7 @@ #include "dca/platform/dca_gpu.h" #include "dca/phys/dca_step/symmetrization/symmetrize.hpp" +#include "dca/phys/dca_step/symmetrization/derive_point_group.hpp" #include "dca/phys/dca_step/symmetrization/solve_orbital_op_signs.hpp" #include @@ -58,10 +59,11 @@ #include "dca/parallel/no_concurrency/no_concurrency.hpp" #include "dca/phys/dca_algorithms/compute_free_greens_function.hpp" #include "dca/phys/domains/cluster/cluster_symmetry.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/cluster/symmetries/point_groups/no_symmetry.hpp" #include "dca/phys/parameters/parameters.hpp" #include "dca/profiling/null_profiler.hpp" +#include "dca/phys/models/analytic_hamiltonians/Kagome_hubbard.hpp" #include "dca/phys/models/analytic_hamiltonians/singleband_chain.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/analytic_hamiltonians/threeband_hubbard.hpp" @@ -107,6 +109,7 @@ struct SquareD4 { static std::vector expectedFailingKOps() { return {}; } static std::vector expectedFailingROps() { return {}; } static std::vector expectedUnverifiedKOps() { return {}; } + static constexpr int expected_num_derived_symmetries = 8; }; // CASE 2 -- three-band Hubbard (Emery/CuO2) model on D4. This case fails the @@ -126,6 +129,7 @@ struct ThreebandD4 { static std::vector expectedFailingKOps() { return {}; } static std::vector expectedFailingROps() { return {}; } static std::vector expectedUnverifiedKOps() { return {}; } + static constexpr int expected_num_derived_symmetries = 8; }; // CASE 3 -- 1D chain. Since this model has identity-only symmetry, this test exercises @@ -141,6 +145,25 @@ struct SinglebandChain { static std::vector expectedFailingKOps() { return {}; } static std::vector expectedFailingROps() { return {}; } static std::vector expectedUnverifiedKOps() { return {}; } + static constexpr int expected_num_derived_symmetries = 4; +}; + +// CASE 4 -- Kagome lattice declared with no_symmetry<2>, mirroring the production +// instantiation in test/unit/phys/dca_step/cluster_solver/test_setup.hpp. This is the +// regression case for solveSignsForOp's -1 guard: the hexagonal has the 12 D6 ops, +// but the orbital position+flavor matching in set_symmetry_matrices filters them all out, +// and records (-1, -1). The H0 sign solver must reject the ops instead of indexing H0 with +// band -1 (an OOB). +struct KagomeNoSym { + using Scalar = double; + using Lattice = dca::phys::models::KagomeHubbard>; + static constexpr char Input[] = "kagome_input.json"; + static constexpr int expected_num_symmetries = 1; + static std::vector expectedFailingReps() { return {}; } + static std::vector expectedFailingKOps() { return {}; } + static std::vector expectedFailingROps() { return {}; } + static std::vector expectedUnverifiedKOps() { return {}; } + static constexpr int expected_num_derived_symmetries = 2; }; // Templated test fixture @@ -514,6 +537,48 @@ TYPED_TEST(SymmetrizeCharacterizationTest, GroupShadowCrossCheck) { "sign-consistency check rejects changed vs the expectation."; } +// TEST 5c: DerivedGroupReport -- the production derive-and-report step. update_domains now derives +// each 2D model's point group from scratch (2D holohedry pool -> geometry filter -> H0 gate), +// reports any divergence from the declared group, and keeps symmetrizing with the declared group. +// This exercises the same routine directly and asserts the three things production relies on: +// (1) the declared symmetry state is restored, so the derivation is invisible downstream +// (2) the report is silent when derived == declared, and names the divergence otherwise +// (3) the derived-group size matches the trait expectation +TYPED_TEST(SymmetrizeCharacterizationTest, DerivedGroupReport) { + using Fixture = SymmetrizeCharacterizationTest; + using RClusterDmn = typename Fixture::RClusterDmn; + using KCluster = typename Fixture::KCluster; + using Model = typename Fixture::Model; + using CS_k = dca::phys::domains::cluster_symmetry; + + const int n_ops_before = Fixture::KSymDmn::dmn_size(); + const auto symmetry_matrix_before = CS_k::get_symmetry_matrix(); + + const std::string report = + dca::phys::deriveAndComparePointGroup(this->parameters_); + + // (1) restoration: production must be left in exactly the declared state. + ASSERT_EQ(Fixture::KSymDmn::dmn_size(), n_ops_before); + const auto& symmetry_matrix_after = CS_k::get_symmetry_matrix(); + for (int i = 0; i < symmetry_matrix_before.size(); ++i) + ASSERT_EQ(symmetry_matrix_after(i), symmetry_matrix_before(i)) + << "symmetry table changed at linear index " << i; + + // (2) + (3): silent on match; on divergence the report names the derived-group size and the + // under-declaration. + if (TypeParam::expected_num_derived_symmetries == TypeParam::expected_num_symmetries) { + EXPECT_TRUE(report.empty()) << "unexpected divergence report:\n" << report; + } + else { + const std::string expected_size = "derived group: " + + std::to_string(TypeParam::expected_num_derived_symmetries) + + " op(s)"; + EXPECT_NE(report.find(expected_size), std::string::npos) << report; + EXPECT_NE(report.find("under-declared"), std::string::npos) << report; + std::cout << "[derived group] " << TypeParam::Input << ":\n" << report; + } +} + // TEST 6: MappedPointShadow -- the mapped_point accessor. The band-independent ".first" of the // legacy symmetry matrix (the image of each momentum under each op) is promoted into its own // (cluster-point x op) accessor. Verify it reproduces .first for every band, which confirms both @@ -606,11 +671,12 @@ TYPED_TEST(SymmetrizeCharacterizationTest, PerOpMapRealSpace) { << "Real-space per-op red/green map changed vs the expected failing set."; } -// TEST 8 (a/b/c): rejection fixtures for the sign-consistency solver. +// TEST 8 (a/b/c/d): rejection fixtures for the sign-consistency solver. // -// solveOrbitalOpSignsFromH0 has three throw branches. No shipped model exercises any of the -// three on a correct H0 -- the spine cases all pass -- so we perturb a copy of the (exactly -// symmetric) H0 to break one operation and assert the solver throws for the intended reason. +// solveOrbitalOpSignsFromH0 has four throw branches. No shipped model exercises any of the +// four on a correct H0 and a complete symmetry table -- the spine cases all pass -- so we +// perturb a copy of the (exactly symmetric) H0 (8a-8c), or the table itself (8d), to break one +// operation and assert the solver throws for the intended reason. // // These need a multi-orbital model. A single band has no off-diagonal coupling to corrupt, // and on the spine's square cluster every nonzero single-band entry sits at a k that is a @@ -640,6 +706,29 @@ TYPED_TEST(SymmetrizeCharacterizationTest, RejectsBrokenOffDiagonalCoupling) { const auto t = findStrongestOffDiagonal(this->H0_, nb, nk); ASSERT_GT(t.mag, kTolerance) << "no off-diagonal coupling to perturb."; + // The perturbation is only visible to an op that maps the corrupted entry to a *different* + // (unperturbed) H0 entry. Both the entry and its Hermitian partner are perturbed, so an op + // landing on either sees a consistent H0 and cannot throw. An identity-only group (e.g. a + // multi-band lattice declared with no_symmetry) therefore has nothing to detect: skip. + { + const auto& sym = dca::phys::domains::cluster_symmetry::get_symmetry_matrix(); + const int n_ops = Fixture::KSymDmn::dmn_size(); + bool movable = false; + for (int s = 0; s < n_ops && !movable; ++s) { + const int k_new = sym(t.k, 0, s).first; + const int b0_new = sym(0, t.b0, s).second; + const int b1_new = sym(0, t.b1, s).second; + const bool fixes = k_new == t.k && b0_new == t.b0 && b1_new == t.b1; + const bool hermitian_partner = k_new == t.k && b0_new == t.b1 && b1_new == t.b0; + movable = !fixes && !hermitian_partner; + } + if (!movable) { + std::cout << "[skip] " << TypeParam::Input + << ": no op moves the corrupted coupling to an unperturbed entry.\n"; + return; + } + } + // Vanish: the op connecting this entry to its (still nonzero) image sees it gone on one side only. { auto H0p = this->H0_; @@ -765,4 +854,36 @@ TEST(SolveOrbitalOpSigns, BoundaryFoldDoesNotMaskPxParity) { EXPECT_DOUBLE_EQ(u_s(2, 2, 0), 1.); } +// 8d -- missing band image: the geometric position/flavor matching in set_symmetry_matrices +// records -1 when it finds no admissible image, so the solver cannot assume a complete table. +// Unlike 8a-8c this perturbs the symmetry table, not H0: the whole-group populator must throw, +// and the non-throwing classifier must omit the op instead of indexing H0 with -1 (an OOB). The +// table is shared static state, so it gets restored. +TYPED_TEST(SymmetrizeCharacterizationTest, RejectsMissingBandImage) { + using Fixture = SymmetrizeCharacterizationTest; + using KCluster = typename Fixture::KCluster; + + const std::vector baseline = dca::phys::verifiedSymmetryOps(this->H0_); + ASSERT_FALSE(baseline.empty()) << "no verified op to corrupt (identity should always pass)."; + const int s_target = baseline.front(); + + auto& sym = dca::phys::domains::cluster_symmetry::get_symmetry_matrix(); + const int saved_image = sym(0, 0, s_target).second; + sym(0, 0, s_target).second = -1; + + const std::string msg = + captureThrowMessage([&] { dca::phys::solveOrbitalOpSignsFromH0(this->H0_); }); + const std::vector verified = dca::phys::verifiedSymmetryOps(this->H0_); + + sym(0, 0, s_target).second = saved_image; + + ASSERT_FALSE(msg.empty()) << "sign solver did not reject a -1 sentinel band image."; + EXPECT_NE(msg.find("no band image"), std::string::npos) << "actual: " << msg; + + std::vector expected = baseline; + expected.erase(std::find(expected.begin(), expected.end(), s_target)); + EXPECT_EQ(verified, expected) + << "classifier did not cleanly omit (only) the op with the sentinel image."; +} + } // namespace diff --git a/test/integration/statistical_tests/bilayer_lattice/bilayer_lattice_setup.hpp b/test/integration/statistical_tests/bilayer_lattice/bilayer_lattice_setup.hpp index 2632fb73d..8d3c4c328 100644 --- a/test/integration/statistical_tests/bilayer_lattice/bilayer_lattice_setup.hpp +++ b/test/integration/statistical_tests/bilayer_lattice/bilayer_lattice_setup.hpp @@ -25,7 +25,7 @@ #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/math/random/random.hpp" #include "dca/math/statistical_testing/function_cut.hpp" #include "dca/math/statistical_testing/statistical_testing.hpp" diff --git a/test/integration/statistical_tests/rashba_lattice/rashba_lattice_setup.hpp b/test/integration/statistical_tests/rashba_lattice/rashba_lattice_setup.hpp index 05ff0e97d..9e414b258 100644 --- a/test/integration/statistical_tests/rashba_lattice/rashba_lattice_setup.hpp +++ b/test/integration/statistical_tests/rashba_lattice/rashba_lattice_setup.hpp @@ -29,7 +29,7 @@ #include "dca/phys/dca_step/cluster_mapping/double_counting_correction.hpp" #include "dca/phys/dca_step/cluster_mapping/update_chemical_potential.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/math/random/random.hpp" #include "dca/phys/dca_step/cluster_mapping/update_chemical_potential.hpp" #include "dca/math/statistical_testing/function_cut.hpp" diff --git a/test/integration/statistical_tests/square_lattice/square_lattice_setup.hpp b/test/integration/statistical_tests/square_lattice/square_lattice_setup.hpp index d3b84bde4..d485cd7c9 100644 --- a/test/integration/statistical_tests/square_lattice/square_lattice_setup.hpp +++ b/test/integration/statistical_tests/square_lattice/square_lattice_setup.hpp @@ -25,7 +25,7 @@ #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/math/random/random.hpp" #include "dca/math/statistical_testing/function_cut.hpp" #include "dca/math/statistical_testing/statistical_testing.hpp" diff --git a/test/performance/phys/accumulation/sp_accumulation_performance_test.cpp b/test/performance/phys/accumulation/sp_accumulation_performance_test.cpp index cc7be41f5..8328f887d 100644 --- a/test/performance/phys/accumulation/sp_accumulation_performance_test.cpp +++ b/test/performance/phys/accumulation/sp_accumulation_performance_test.cpp @@ -34,7 +34,7 @@ using Profiler = dca::profiling::CountingProfiler; #include "dca/io/json/json_reader.hpp" #include "dca/math/random/std_random_wrapper.hpp" #include "dca/phys/dca_data/dca_data.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_concurrency/no_concurrency.hpp" diff --git a/test/performance/phys/ctint/ctint_walker_performance_test.cpp b/test/performance/phys/ctint/ctint_walker_performance_test.cpp index e58793e58..d3db7fcd9 100644 --- a/test/performance/phys/ctint/ctint_walker_performance_test.cpp +++ b/test/performance/phys/ctint/ctint_walker_performance_test.cpp @@ -30,7 +30,7 @@ using McOptions = MockMcOptions; } // namespace dca #include "dca/phys/dca_step/cluster_solver/ctint/walker/ctint_walker_choice.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/bilayer_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/parallel/no_concurrency/no_concurrency.hpp" diff --git a/test/system-level/analysis/dca_post_interpolation_pp_up_down/analysis_dca_post_interpolation_pp_up_down_test.cpp b/test/system-level/analysis/dca_post_interpolation_pp_up_down/analysis_dca_post_interpolation_pp_up_down_test.cpp index 641ba3111..1a9df8028 100644 --- a/test/system-level/analysis/dca_post_interpolation_pp_up_down/analysis_dca_post_interpolation_pp_up_down_test.cpp +++ b/test/system-level/analysis/dca_post_interpolation_pp_up_down/analysis_dca_post_interpolation_pp_up_down_test.cpp @@ -42,7 +42,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_analysis/bse_solver/bse_solver.hpp" #include "dca/phys/dca_data/dca_data.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/phys/parameters/parameters.hpp" diff --git a/test/system-level/analysis/dca_pp_up_down_full/analysis_dca_pp_up_down_full_test.cpp b/test/system-level/analysis/dca_pp_up_down_full/analysis_dca_pp_up_down_full_test.cpp index 367483335..202c41f37 100644 --- a/test/system-level/analysis/dca_pp_up_down_full/analysis_dca_pp_up_down_full_test.cpp +++ b/test/system-level/analysis/dca_pp_up_down_full/analysis_dca_pp_up_down_full_test.cpp @@ -42,7 +42,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_analysis/bse_solver/bse_solver.hpp" #include "dca/phys/dca_data/dca_data.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/phys/parameters/parameters.hpp" diff --git a/test/system-level/analysis/dca_pp_up_down_sym/analysis_dca_pp_up_down_sym_test.cpp b/test/system-level/analysis/dca_pp_up_down_sym/analysis_dca_pp_up_down_sym_test.cpp index 2c177a041..c54db984e 100644 --- a/test/system-level/analysis/dca_pp_up_down_sym/analysis_dca_pp_up_down_sym_test.cpp +++ b/test/system-level/analysis/dca_pp_up_down_sym/analysis_dca_pp_up_down_sym_test.cpp @@ -40,7 +40,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_analysis/bse_solver/bse_solver.hpp" #include "dca/phys/dca_data/dca_data.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/phys/parameters/parameters.hpp" diff --git a/test/system-level/analysis/dcaplus_pp_up_down_full/analysis_dcaplus_pp_up_down_full_test.cpp b/test/system-level/analysis/dcaplus_pp_up_down_full/analysis_dcaplus_pp_up_down_full_test.cpp index b74cc6f33..054c2e063 100644 --- a/test/system-level/analysis/dcaplus_pp_up_down_full/analysis_dcaplus_pp_up_down_full_test.cpp +++ b/test/system-level/analysis/dcaplus_pp_up_down_full/analysis_dcaplus_pp_up_down_full_test.cpp @@ -42,7 +42,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_analysis/bse_solver/bse_solver.hpp" #include "dca/phys/dca_data/dca_data.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/phys/parameters/parameters.hpp" diff --git a/test/system-level/analysis/dcaplus_pp_up_down_sym/analysis_dcaplus_pp_up_down_sym_test.cpp b/test/system-level/analysis/dcaplus_pp_up_down_sym/analysis_dcaplus_pp_up_down_sym_test.cpp index c6591b8cd..cd5c54d61 100644 --- a/test/system-level/analysis/dcaplus_pp_up_down_sym/analysis_dcaplus_pp_up_down_sym_test.cpp +++ b/test/system-level/analysis/dcaplus_pp_up_down_sym/analysis_dcaplus_pp_up_down_sym_test.cpp @@ -40,7 +40,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_analysis/bse_solver/bse_solver.hpp" #include "dca/phys/dca_data/dca_data.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/phys/parameters/parameters.hpp" diff --git a/test/system-level/dca/ctint_sp_DCA_mpi_thread_test.cpp b/test/system-level/dca/ctint_sp_DCA_mpi_thread_test.cpp index e4d397e1b..7a34b0a21 100644 --- a/test/system-level/dca/ctint_sp_DCA_mpi_thread_test.cpp +++ b/test/system-level/dca/ctint_sp_DCA_mpi_thread_test.cpp @@ -36,7 +36,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_loop/dca_loop.hpp" #include "dca/phys/dca_data/dca_data.hpp" #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/phys/parameters/parameters.hpp" diff --git a/test/system-level/dca/dca_sp_DCA+_mpi_cuda_test.cpp b/test/system-level/dca/dca_sp_DCA+_mpi_cuda_test.cpp index 5ef504b71..b05250392 100644 --- a/test/system-level/dca/dca_sp_DCA+_mpi_cuda_test.cpp +++ b/test/system-level/dca/dca_sp_DCA+_mpi_cuda_test.cpp @@ -40,7 +40,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_loop/dca_loop.hpp" #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/phys/parameters/parameters.hpp" diff --git a/test/system-level/dca/dca_sp_DCA+_mpi_test.cpp b/test/system-level/dca/dca_sp_DCA+_mpi_test.cpp index 1d15396d6..d18e42508 100644 --- a/test/system-level/dca/dca_sp_DCA+_mpi_test.cpp +++ b/test/system-level/dca/dca_sp_DCA+_mpi_test.cpp @@ -41,7 +41,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_loop/dca_loop.hpp" #include "dca/phys/dca_step/cluster_solver/ctaux/ctaux_cluster_solver.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/phys/parameters/parameters.hpp" diff --git a/test/system-level/dca/dca_sp_DCA+_thread_test.cpp b/test/system-level/dca/dca_sp_DCA+_thread_test.cpp index 53dc07d1a..eef8e76e4 100644 --- a/test/system-level/dca/dca_sp_DCA+_thread_test.cpp +++ b/test/system-level/dca/dca_sp_DCA+_thread_test.cpp @@ -41,7 +41,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_step/cluster_solver/stdthread_qmci/stdthread_qmci_cluster_solver.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/unit/math/function_transform/function_transform_test.cpp b/test/unit/math/function_transform/function_transform_test.cpp index 6a1f68dba..f9354754b 100644 --- a/test/unit/math/function_transform/function_transform_test.cpp +++ b/test/unit/math/function_transform/function_transform_test.cpp @@ -16,7 +16,7 @@ #include "dca/io/json/json_reader.hpp" #include "dca/io/hdf5/hdf5_reader.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "test/mock_mcconfig.hpp" namespace dca { diff --git a/test/unit/phys/dca_algorithms/compute_band_structure_test.cpp b/test/unit/phys/dca_algorithms/compute_band_structure_test.cpp index f1b236bb4..e98fd127d 100644 --- a/test/unit/phys/dca_algorithms/compute_band_structure_test.cpp +++ b/test/unit/phys/dca_algorithms/compute_band_structure_test.cpp @@ -22,7 +22,7 @@ #include "dca/parallel/no_threading/no_threading.hpp" #include "dca/profiling/null_profiler.hpp" #include "dca/phys/dca_step/cluster_solver/cluster_solver_id.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/brillouin_zone_cut_domain.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" diff --git a/test/unit/phys/dca_algorithms/compute_free_greens_function_test.cpp b/test/unit/phys/dca_algorithms/compute_free_greens_function_test.cpp index 03117e75e..c572e99b7 100644 --- a/test/unit/phys/dca_algorithms/compute_free_greens_function_test.cpp +++ b/test/unit/phys/dca_algorithms/compute_free_greens_function_test.cpp @@ -21,7 +21,7 @@ #include "dca/function/domains.hpp" #include "dca/function/function.hpp" #include "dca/parallel/no_concurrency/no_concurrency.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/bilayer_lattice.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" diff --git a/test/unit/phys/dca_algorithms/compute_greens_function_test.cpp b/test/unit/phys/dca_algorithms/compute_greens_function_test.cpp index 9f485b0c7..92577e123 100644 --- a/test/unit/phys/dca_algorithms/compute_greens_function_test.cpp +++ b/test/unit/phys/dca_algorithms/compute_greens_function_test.cpp @@ -21,7 +21,7 @@ #include "dca/function/function.hpp" #include "dca/parallel/no_concurrency/no_concurrency.hpp" #include "dca/phys/dca_algorithms/compute_free_greens_function.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/bilayer_lattice.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" diff --git a/test/unit/phys/dca_step/cluster_solver/ctint/ct_int_solver_methods_test.cpp b/test/unit/phys/dca_step/cluster_solver/ctint/ct_int_solver_methods_test.cpp index ac8802612..6508d3fd0 100644 --- a/test/unit/phys/dca_step/cluster_solver/ctint/ct_int_solver_methods_test.cpp +++ b/test/unit/phys/dca_step/cluster_solver/ctint/ct_int_solver_methods_test.cpp @@ -14,7 +14,7 @@ using McOptions = MockMcOptions; #include "dca/phys/dca_step/cluster_solver/ctint/ctint_cluster_solver.hpp" #include "dca/testing/gtest_h_w_warning_blocking.h" #include "test/unit/phys/dca_step/cluster_solver/stub_rng.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/parallel/no_concurrency/no_concurrency.hpp" #include "dca/parallel/no_threading/no_threading.hpp" diff --git a/test/unit/phys/dca_step/cluster_solver/test_setup.hpp b/test/unit/phys/dca_step/cluster_solver/test_setup.hpp index 2cf8821e3..0cbc408f9 100644 --- a/test/unit/phys/dca_step/cluster_solver/test_setup.hpp +++ b/test/unit/phys/dca_step/cluster_solver/test_setup.hpp @@ -21,7 +21,7 @@ #include "dca/phys/parameters/parameters.hpp" #include "dca/phys/dca_step/cluster_solver/ctint/structs/interaction_vertices.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/quantum/electron_band_domain.hpp" #include "dca/phys/domains/quantum/electron_spin_domain.hpp" #include "dca/phys/domains/time_and_frequency/frequency_domain.hpp" diff --git a/test/unit/phys/dca_step/lattice_mapping/deconvolution/deconvolution_routines_test.cpp b/test/unit/phys/dca_step/lattice_mapping/deconvolution/deconvolution_routines_test.cpp index 1c59a3bed..524255a93 100644 --- a/test/unit/phys/dca_step/lattice_mapping/deconvolution/deconvolution_routines_test.cpp +++ b/test/unit/phys/dca_step/lattice_mapping/deconvolution/deconvolution_routines_test.cpp @@ -19,7 +19,7 @@ #include "dca/parallel/no_concurrency/no_concurrency.hpp" #include "dca/profiling/null_profiler.hpp" #include "dca/phys/dca_step/cluster_solver/cluster_solver_id.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" diff --git a/test/unit/phys/domains/cluster/CMakeLists.txt b/test/unit/phys/domains/cluster/CMakeLists.txt index 821b36155..716421069 100644 --- a/test/unit/phys/domains/cluster/CMakeLists.txt +++ b/test/unit/phys/domains/cluster/CMakeLists.txt @@ -13,5 +13,7 @@ dca_add_gtest(cluster_domain_test GTEST_MAIN LIBS ${LAPACK_LIBRARIES} function enumerations quantum_domains cluster_domains dca_io FFTW::Double ${DCA_GPU_LIBS}) +add_subdirectory(symmetries) + # deprecated (requires NFFT) # add_subdirectory(interpolation/wannier_interpolation) diff --git a/test/unit/phys/domains/cluster/interpolation/wannier_interpolation/wannier_interpolation_test.cpp b/test/unit/phys/domains/cluster/interpolation/wannier_interpolation/wannier_interpolation_test.cpp index 2acf8a390..b4d351d43 100644 --- a/test/unit/phys/domains/cluster/interpolation/wannier_interpolation/wannier_interpolation_test.cpp +++ b/test/unit/phys/domains/cluster/interpolation/wannier_interpolation/wannier_interpolation_test.cpp @@ -22,7 +22,7 @@ #include "dca/parallel/no_threading/no_threading.hpp" #include "dca/profiling/null_profiler.hpp" #include "dca/phys/dca_step/cluster_solver/cluster_solver_name.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" #include "dca/phys/models/tight_binding_model.hpp" #include "dca/phys/parameters/parameters.hpp" diff --git a/test/unit/phys/domains/cluster/symmetries/CMakeLists.txt b/test/unit/phys/domains/cluster/symmetries/CMakeLists.txt new file mode 100644 index 000000000..1361082fb --- /dev/null +++ b/test/unit/phys/domains/cluster/symmetries/CMakeLists.txt @@ -0,0 +1,5 @@ +# domains/cluster/symmetries unit tests + +dca_add_gtest(holohedries_2d_test + GTEST_MAIN + LIBS ${DCA_GPU_LIBS}) diff --git a/test/unit/phys/domains/cluster/symmetries/holohedries_2d_test.cpp b/test/unit/phys/domains/cluster/symmetries/holohedries_2d_test.cpp new file mode 100644 index 000000000..a2dfc7618 --- /dev/null +++ b/test/unit/phys/domains/cluster/symmetries/holohedries_2d_test.cpp @@ -0,0 +1,146 @@ +// Copyright (C) 2018 UT-Battelle, LLC +// All rights reserved. +// +// See LICENSE for terms of usage. +// See CITATION.md for citation guidelines, if DCA++ is used for scientific publications. +// +// Author: Tyler Sax +// +// Completeness oracle for the 2D holohedry candidate pool. Proves the pool is a complete +// crystallographic op set: filtering the pool by each 2D Bravais lattice reproduces that +// lattice's full holohedry (square -> D4 order 8, hexagonal -> D6 order 12, rectangular -> D2 +// order 4, oblique -> C2 order 2). Because every one of the ten 2D crystallographic point groups +// is a subgroup of one of these holohedries, realizing all four maximal groups proves the pool +// misses no op. + +#include +#include +#include + +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" + +#include "gtest/gtest.h" + +#include "dca/util/type_list.hpp" + +namespace { + +// A 2x2 op stored row-major: m[i][j]. +using Mat2 = std::array, 2>; + +constexpr double kTol = 1e-10; + +// The op classes store their matrix column-major (m[i + 2*j] = row i, col j); convert to nested +// row-major in order to make the algebra more readable, and easier to verify. +Mat2 fromColumnMajor(const double* m) { + return {{{m[0], m[2]}, {m[1], m[3]}}}; +} + +// Materialize a point_group_type_list into its op matrices. Recurses over the typelist by index so +// the same helper serves any pool/group. +template +struct Collect { + static void run(std::vector& out) { + using Op = typename dca::util::TypeAt::type; + out.push_back(fromColumnMajor(Op::matrix())); + Collect::run(out); + } +}; +template +struct Collect { + static void run(std::vector&) {} +}; + +template +std::vector collectOps() { + using List = typename PointGroup::point_group_type_list; + std::vector out; + Collect::value>::run(out); + return out; +} + +// Note that the algebra below is implemented directly in this test, as opposed to being imported +// via the existing linalg path. Given this is a logic-only test operating on 2x2 matrices, hand +// rolling makes more sense than adding a dependency on LAPACK/BLAS, which is overkill here. +bool equal(const Mat2& a, const Mat2& b) { + for (int i = 0; i < 2; ++i) + for (int j = 0; j < 2; ++j) + if (std::abs(a[i][j] - b[i][j]) > kTol) + return false; + return true; +} + +std::vector dedup(const std::vector& ops) { + std::vector out; + for (const auto& o : ops) { + bool seen = false; + for (const auto& k : out) + seen = seen || equal(o, k); + if (!seen) + out.push_back(o); + } + return out; +} + +Mat2 matmul(const Mat2& a, const Mat2& b) { + Mat2 c{}; + for (int i = 0; i < 2; ++i) + for (int j = 0; j < 2; ++j) + c[i][j] = a[i][0] * b[0][j] + a[i][1] * b[1][j]; + return c; +} + +double det(const Mat2& a) { + return a[0][0] * a[1][1] - a[0][1] * a[1][0]; +} + +Mat2 inverse(const Mat2& a) { + const double d = det(a); + return {{{a[1][1] / d, -a[0][1] / d}, {-a[1][0] / d, a[0][0] / d}}}; +} + +bool isInteger(const Mat2& a) { + for (int i = 0; i < 2; ++i) + for (int j = 0; j < 2; ++j) + if (std::abs(a[i][j] - std::round(a[i][j])) > 1e-8) + return false; + return true; +} + +// Order of the holohedry of the lattice whose primitive vectors are the columns of `basis`: the +// number of pool ops that map the lattice onto itself (verified by applying the operation to the +// basis vectors, multiplying by the inverse of the basis, and checking whether the resulting +// matrix has integer values.) +int holohedryOrder(const std::vector& ops, const Mat2& basis) { + const Mat2 binv = inverse(basis); + int count = 0; + for (const auto& O : ops) + if (isInteger(matmul(binv, matmul(O, basis)))) + ++count; + return count; +} + +const double kHalfRoot3 = std::sqrt(3.0) / 2.0; + +} // namespace + +// Completeness: filtering the pool by each 2D Bravais lattice yields that lattice's full holohedry. +// Covering all four maximal groups (D4, D6, D2, C2) covers all ten 2D point groups as subgroups, so +// this is the load-bearing check that the pool misses no op. +// +// The pool lists D4 (8) + D6 (12) = 20 ops; the shared {identity, C2, mirror@0, mirror@90} collapse +// under dedup to 16 distinct ops, which is what the per-lattice filter runs over. +TEST(HolohedryPool2DTest, RealizesEvery2DHolohedry) { + const auto ops = dedup(collectOps()); + ASSERT_EQ(ops.size(), 16u); // 20 listed, 16 distinct after the D4/D6 overlap collapses + + const Mat2 square{{{1, 0}, {0, 1}}}; + const Mat2 hexagonal{{{1, -0.5}, {0, kHalfRoot3}}}; + const Mat2 rectangular{{{1, 0}, {0, 2}}}; + const Mat2 oblique{{{1, 0}, {0.3, 1.7}}}; + + EXPECT_EQ(holohedryOrder(ops, square), 8); // D4 + EXPECT_EQ(holohedryOrder(ops, hexagonal), 12); // D6 + EXPECT_EQ(holohedryOrder(ops, rectangular), 4); // D2 + EXPECT_EQ(holohedryOrder(ops, oblique), 2); // C2 +} diff --git a/test/unit/phys/models/analytic_hamiltonians/bilayer_lattice_test.cpp b/test/unit/phys/models/analytic_hamiltonians/bilayer_lattice_test.cpp index 41c0ae3d3..9e1d3b353 100644 --- a/test/unit/phys/models/analytic_hamiltonians/bilayer_lattice_test.cpp +++ b/test/unit/phys/models/analytic_hamiltonians/bilayer_lattice_test.cpp @@ -22,7 +22,7 @@ #include "dca/function/function.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" #include "dca/phys/domains/cluster/cluster_domain_initializer.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/cluster/cluster_domain_aliases.hpp" #include "dca/phys/parameters/model_parameters.hpp" diff --git a/test/unit/phys/models/analytic_hamiltonians/square_lattice_test.cpp b/test/unit/phys/models/analytic_hamiltonians/square_lattice_test.cpp index 2ae7c7665..04683e1f4 100644 --- a/test/unit/phys/models/analytic_hamiltonians/square_lattice_test.cpp +++ b/test/unit/phys/models/analytic_hamiltonians/square_lattice_test.cpp @@ -22,7 +22,7 @@ #include "dca/function/function.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" #include "dca/phys/domains/cluster/cluster_domain_initializer.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/cluster/cluster_domain_aliases.hpp" #include "dca/phys/parameters/model_parameters.hpp" diff --git a/test/unit/phys/models/analytic_hamiltonians/triangular_lattice_test.cpp b/test/unit/phys/models/analytic_hamiltonians/triangular_lattice_test.cpp index 0ef7e3431..ff9d9f8ae 100644 --- a/test/unit/phys/models/analytic_hamiltonians/triangular_lattice_test.cpp +++ b/test/unit/phys/models/analytic_hamiltonians/triangular_lattice_test.cpp @@ -22,14 +22,14 @@ #include "dca/function/function.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" #include "dca/phys/domains/cluster/cluster_domain_initializer.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_hexagonal.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/domains/cluster/cluster_domain_aliases.hpp" #include "dca/phys/parameters/model_parameters.hpp" using namespace dca; TEST(TriangularLatticeTest, Initialize_H_0) { - using PointGroup = phys::domains::C6; + using PointGroup = phys::domains::D6; using Lattice = phys::models::triangular_lattice; using BandDmn = func::dmn<1, int>; @@ -77,7 +77,7 @@ TEST(TriangularLatticeTest, Initialize_H_0) { } TEST(TriangularLatticeTest, Initialize_H_interaction) { - using PointGroup = phys::domains::C6; + using PointGroup = phys::domains::D6; using Lattice = phys::models::triangular_lattice; using BandDmn = func::dmn_0>; diff --git a/test/unit/phys/models/general_interaction_test.cpp b/test/unit/phys/models/general_interaction_test.cpp index a303fc624..07aec3601 100644 --- a/test/unit/phys/models/general_interaction_test.cpp +++ b/test/unit/phys/models/general_interaction_test.cpp @@ -17,7 +17,7 @@ #include "dca/function/function.hpp" #include "dca/phys/domains/cluster/cluster_domain.hpp" #include "dca/phys/domains/cluster/cluster_domain_initializer.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/bilayer_lattice.hpp" #include "dca/phys/domains/cluster/cluster_domain_aliases.hpp" #include "dca/phys/parameters/model_parameters.hpp" diff --git a/test/unit/phys/parameters/model_parameters/model_parameters_2d_2band_test.cpp b/test/unit/phys/parameters/model_parameters/model_parameters_2d_2band_test.cpp index 2482eeb01..0b2f5c4e8 100644 --- a/test/unit/phys/parameters/model_parameters/model_parameters_2d_2band_test.cpp +++ b/test/unit/phys/parameters/model_parameters/model_parameters_2d_2band_test.cpp @@ -14,7 +14,7 @@ #include "dca/phys/parameters/model_parameters.hpp" #include "gtest/gtest.h" #include "dca/io/json/json_reader.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" using PointGroup = dca::phys::domains::D4; diff --git a/test/unit/phys/parameters/model_parameters/model_parameters_2d_4band_test.cpp b/test/unit/phys/parameters/model_parameters/model_parameters_2d_4band_test.cpp index 4ff63e190..361c59c51 100644 --- a/test/unit/phys/parameters/model_parameters/model_parameters_2d_4band_test.cpp +++ b/test/unit/phys/parameters/model_parameters/model_parameters_2d_4band_test.cpp @@ -14,7 +14,7 @@ #include "dca/phys/parameters/model_parameters.hpp" #include "gtest/gtest.h" #include "dca/io/json/json_reader.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" using PointGroup = dca::phys::domains::D4; diff --git a/test/unit/phys/parameters/model_parameters/model_parameters_bilayer_hubbard_test.cpp b/test/unit/phys/parameters/model_parameters/model_parameters_bilayer_hubbard_test.cpp index 640ff77ac..bc6fe528f 100644 --- a/test/unit/phys/parameters/model_parameters/model_parameters_bilayer_hubbard_test.cpp +++ b/test/unit/phys/parameters/model_parameters/model_parameters_bilayer_hubbard_test.cpp @@ -16,7 +16,7 @@ #include "dca/phys/parameters/model_parameters.hpp" #include "gtest/gtest.h" #include "dca/io/json/json_reader.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" using PointGroup = dca::phys::domains::D4; diff --git a/test/unit/phys/parameters/model_parameters/model_parameters_material_test.cpp b/test/unit/phys/parameters/model_parameters/model_parameters_material_test.cpp index 8dad1373d..cc7d8f7db 100644 --- a/test/unit/phys/parameters/model_parameters/model_parameters_material_test.cpp +++ b/test/unit/phys/parameters/model_parameters/model_parameters_material_test.cpp @@ -16,7 +16,7 @@ #include "dca/testing/gtest_h_w_warning_blocking.h" #include "dca/io/json/json_reader.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" using PointGroup = dca::phys::domains::D4; diff --git a/test/unit/phys/parameters/model_parameters/model_parameters_rashba_hubbard_test.cpp b/test/unit/phys/parameters/model_parameters/model_parameters_rashba_hubbard_test.cpp index 439579ce5..807d327f2 100644 --- a/test/unit/phys/parameters/model_parameters/model_parameters_rashba_hubbard_test.cpp +++ b/test/unit/phys/parameters/model_parameters/model_parameters_rashba_hubbard_test.cpp @@ -16,7 +16,7 @@ #include "dca/phys/parameters/model_parameters.hpp" #include "dca/testing/gtest_h_w_warning_blocking.h" #include "dca/io/json/json_reader.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/rashba_hubbard.hpp" using Lattice = dca::phys::models::RashbaHubbard>; diff --git a/test/unit/phys/parameters/model_parameters/model_parameters_single_band_hubbard_test.cpp b/test/unit/phys/parameters/model_parameters/model_parameters_single_band_hubbard_test.cpp index 7ff326ca8..a9e86574e 100644 --- a/test/unit/phys/parameters/model_parameters/model_parameters_single_band_hubbard_test.cpp +++ b/test/unit/phys/parameters/model_parameters/model_parameters_single_band_hubbard_test.cpp @@ -15,7 +15,7 @@ #include "dca/phys/parameters/model_parameters.hpp" #include "dca/testing/gtest_h_w_warning_blocking.h" #include "dca/io/json/json_reader.hpp" -#include "dca/phys/domains/cluster/symmetries/point_groups/2d/2d_square.hpp" +#include "dca/phys/domains/cluster/symmetries/point_groups/2d/holohedries_2d.hpp" #include "dca/phys/models/analytic_hamiltonians/square_lattice.hpp" using PointGroup = dca::phys::domains::D4;