16 #ifndef INCLUDE_SHAPE_CONSTEXPR_PROPERTIES_H
17 #define INCLUDE_SHAPE_CONSTEXPR_PROPERTIES_H
29 namespace Molassembler {
48 namespace ConstexprProperties {
50 constexpr
double floatingPointEqualityTolerance = 1e-4;
58 template<
typename ShapeClass>
65 if(returnedAngle < smallestAngle) {
66 smallestAngle = returnedAngle;
80 template<
typename ShapeClass>
86 static constexpr std::pair<double, double>
value() {
88 double largestAngle = 0;
93 if(returnedAngle < smallestAngle) {
94 smallestAngle = returnedAngle;
97 if(returnedAngle > largestAngle) {
98 largestAngle = returnedAngle;
113 template<
typename ... ShapeClass>
120 const std::array<double,
sizeof...(ShapeClass)> smallestAngles {{
121 calculateSmallestAngle<ShapeClass>()...
125 double minElement = smallestAngles.at(0);
127 for(
unsigned i = 1; i <
sizeof...(ShapeClass); ++i) {
128 if(smallestAngles.at(i) < minElement) {
129 minElement = smallestAngles.at(i);
142 template<
typename T,
size_t size>
146 template<
typename ShapeClass>
148 return Temple::iota<ArrayType, unsigned, ShapeClass::size>();
152 template<
typename ShapeClass,
size_t... Indices>
155 const unsigned rotationFunctionIndex,
156 std::index_sequence<Indices...>
169 template<
typename ShapeClass>
172 const unsigned rotationFunctionIndex
174 return applyRotationImpl<ShapeClass>(
176 rotationFunctionIndex,
177 std::make_index_sequence<ShapeClass::size>{}
182 template<
typename ShapeClass,
unsigned rotationFunctionIndex>
190 startingIndexSequence<ShapeClass>()
196 return rotationPeriodicityImpl<ShapeClass, rotationFunctionIndex>(
197 applyRotation<ShapeClass>(
199 rotationFunctionIndex
215 template<
typename ShapeClass,
unsigned rotationFunctionIndex>
217 return rotationPeriodicityImpl<ShapeClass, rotationFunctionIndex>(
218 applyRotation<ShapeClass>(
219 startingIndexSequence<ShapeClass>(),
220 rotationFunctionIndex
227 template<
typename ShapeClass,
size_t ...Inds>
230 return { rotationPeriodicity<ShapeClass, Inds>()... };
234 template<
typename ShapeClass>
236 return rotationPeriodicitiesImpl<ShapeClass>(
252 template<
typename ShapeClass>
257 >
value = rotationPeriodicitiesImpl<ShapeClass>(
263 template<
typename ... ShapeClasses>
265 static constexpr
unsigned value() {
266 ArrayType<unsigned,
sizeof...(ShapeClasses)> sizes {
287 template<
typename ShapeClass>
313 using AngleFunctionPtr = double(*)(
const unsigned,
const unsigned);
325 template<
size_t size>
328 const size_t sourceSymmetrySize,
329 const AngleFunctionPtr sourceAngleFunction,
330 const AngleFunctionPtr targetAngleFunction
332 double distortionSum = 0;
334 for(
unsigned i = 0; i < sourceSymmetrySize; ++i) {
335 for(
unsigned j = i + 1; j < sourceSymmetrySize; ++j) {
336 distortionSum += Temple::Math::abs(
337 sourceAngleFunction(i, j)
338 - targetAngleFunction(
346 return distortionSum;
360 template<
size_t size>
362 const unsigned symmetryPosition,
366 return indexMapping.at(symmetryPosition);
383 template<
typename ShapeClassFrom,
typename ShapeClassTo>
393 double chiralDistortion = 0;
400 chiralDistortion += Temple::Math::abs(
402 getCoordinates<ShapeClassFrom>(tetrahedron.at(0)),
403 getCoordinates<ShapeClassFrom>(tetrahedron.at(1)),
404 getCoordinates<ShapeClassFrom>(tetrahedron.at(2)),
405 getCoordinates<ShapeClassFrom>(tetrahedron.at(3))
407 getCoordinates<ShapeClassTo>(
410 getCoordinates<ShapeClassTo>(
413 getCoordinates<ShapeClassTo>(
416 getCoordinates<ShapeClassTo>(
423 return chiralDistortion;
436 template<
size_t size>
483 for(
unsigned i = 0; i <
size; ++i) {
484 symmetryPositions.at(
489 return symmetryPositions;
502 template<
typename ShapeClass>
504 return Temple::reduce(rotationPeriodicities<ShapeClass>(), 1u, std::multiplies<>());
508 template<
typename ShapeClass>
509 using IndicesList = ArrayType<unsigned, ShapeClass::size>;
511 using IndexListStorageType = unsigned;
513 template<
typename ShapeClass>
515 IndicesList<ShapeClass>,
516 maxRotations<ShapeClass>() * 2
519 template<
typename ShapeClass>
521 IndicesList<ShapeClass>,
522 maxRotations<ShapeClass>() * 2
525 template<
typename ShapeClass>
528 maxRotations<ShapeClass>() * 2
537 template<
typename ShapeClass>
541 rotations.
insert(indices);
544 chainStructures.push_back(indices);
550 auto generated = applyRotation<ShapeClass>(
551 chainStructures.back(),
555 if(!rotations.
contains(generated)) {
556 rotations.
insert(generated);
557 chainStructures.push_back(generated);
566 chainStructures.pop_back();
582 static constexpr
size_t maxMappingsSize = 50;
590 double angularDistortion, chiralDistortion;
593 : angularDistortion(std::numeric_limits<double>::max()),
594 chiralDistortion(std::numeric_limits<double>::max())
597 constexpr MappingsReturnType(
599 double&& passAngularDistortion,
600 double&& passChiralDistortion
601 ) : mappings(passMappings),
602 angularDistortion(passAngularDistortion),
603 chiralDistortion(passChiralDistortion)
607 constexpr
bool operator == (
const MappingsReturnType& other)
const {
609 mappings == other.mappings
610 && angularDistortion == other.angularDistortion
611 && chiralDistortion == other.chiralDistortion
616 constexpr
bool operator < (
const MappingsReturnType& other)
const {
618 std::tie(mappings, angularDistortion, chiralDistortion)
619 < std::tie(other.mappings, other.angularDistortion, other.chiralDistortion)
634 template<
class ShapeClassFrom,
class ShapeClassTo>
641 "This function can handle only cases of equal or increasing shape size"
646 double lowestAngleDistortion = 100;
647 double lowestChiralDistortion = 100;
649 auto indexMapping = startingIndexSequence<ShapeClassTo>();
654 floatingPointEqualityTolerance
661 if(!encounteredMappings.test(storageVersion)) {
685 comparator.isLessThan(angularDistortion, lowestAngleDistortion)
687 comparator.isEqual(angularDistortion, lowestAngleDistortion)
688 && comparator.isLessOrEqual(chiralDistortion, lowestChiralDistortion)
692 bool clearExisting = (
695 comparator.isEqual(angularDistortion, lowestAngleDistortion)
696 && comparator.isEqual(chiralDistortion, lowestChiralDistortion)
701 bestMappings.
clear();
702 lowestAngleDistortion = angularDistortion;
703 lowestChiralDistortion = chiralDistortion;
707 bestMappings.
insert(indexMapping);
711 auto allRotations = generateAllRotations<ShapeClassTo>(mapped);
713 for(
const auto& rotation : allRotations) {
714 encounteredMappings.set(
719 }
while(Temple::inPlaceNextPermutation(indexMapping));
722 std::move(bestMappings),
723 std::move(lowestAngleDistortion),
724 std::move(lowestChiralDistortion)
735 template<
class ShapeClassFrom,
class ShapeClassTo>
740 "Ligand loss pathway calculation must involve shape size decrease"
748 double lowestAngleDistortion = 100;
749 double lowestChiralDistortion = 100;
753 for(
unsigned i = 0; i < deletedSymmetryPosition; ++i) {
754 indexMapping.at(i) = i;
757 indexMapping.at(i) = i + 1;
766 floatingPointEqualityTolerance
773 if(!encounteredMappings.
test(storageVersion)) {
787 comparator.isLessThan(angularDistortion, lowestAngleDistortion)
789 comparator.isEqual(angularDistortion, lowestAngleDistortion)
790 && comparator.isLessOrEqual(chiralDistortion, lowestChiralDistortion)
794 bool clearExisting = (
797 comparator.isEqual(angularDistortion, lowestAngleDistortion)
798 && comparator.isEqual(chiralDistortion, lowestChiralDistortion)
803 bestMappings.
clear();
804 lowestAngleDistortion = angularDistortion;
805 lowestChiralDistortion = chiralDistortion;
809 bestMappings.
insert(indexMapping);
813 auto allRotations = generateAllRotations<ShapeClassTo>(indexMapping);
815 for(
const auto& rotation : allRotations) {
816 encounteredMappings.
set(
821 }
while(Temple::inPlaceNextPermutation(indexMapping));
824 std::move(bestMappings),
825 std::move(lowestAngleDistortion),
826 std::move(lowestChiralDistortion)
832 template<
typename SymmetrySource,
typename SymmetryTarget>
845 symmetryTransitionMappings<SymmetrySource, SymmetryTarget>()
850 template<
typename SymmetrySource,
typename SymmetryTarget>
874 template<
typename ShapeClass>
876 const unsigned nIdenticalLigands
880 auto indices = startingIndexSequence<ShapeClass>();
882 for(
unsigned i = 0; i < nIdenticalLigands; ++i) {
888 auto initialRotations = generateAllRotations<ShapeClass>(indices);
890 for(
const auto& rotation : initialRotations) {
894 while(Temple::inPlaceNextPermutation(indices)) {
896 auto allRotations = generateAllRotations<ShapeClass>(indices);
897 for(
const auto& rotation : allRotations) {
916 template<
typename ShapeClass>
922 auto indices = startingIndexSequence<ShapeClass>();
924 for(
unsigned i = 0; i < nIdenticalLigands; ++i) {
930 auto initialRotations = generateAllRotations<ShapeClass>(indices);
932 for(
const auto& rotation : initialRotations) {
936 while(Temple::inPlaceNextPermutation(indices)) {
Stubs to work with numeric data.
PURITY_WEAK constexpr bool contains(const T &item) const
Check if the set contains an element.
Definition: DynamicSet.h:61
auto at(Container &&container)
Make functor calling at on arguments.
Definition: Functor.h:58
constexpr double calculateChiralDistortion(const ArrayType< unsigned, Temple::Math::max(ShapeClassFrom::size, ShapeClassTo::size) > &indexMapping)
Calculates the chiral distortion caused by a shape transition.
Definition: Properties.h:384
Data struct to collect the results of calculating the ideal index mappings between pairs of indices...
Definition: Properties.h:581
constexpr auto unpackToFunction()
Definition: TupleType.h:133
constexpr ArrayType< unsigned, ShapeClass::rotations.size()> rotationPeriodicities()
Calculates all multiplicities of a shape group's rotations.
Definition: Properties.h:235
constexpr auto max(const ContainerType &container)
Composable max function. Returns the smallest value of any container.
Definition: Numeric.h:188
Definition: DynamicArray.h:26
std::tuple< Line, Bent, EquilateralTriangle, VacantTetrahedron, T, Tetrahedron, Square, Seesaw, TrigonalPyramid, SquarePyramid, TrigonalBipyramid, Pentagon, Octahedron, TrigonalPrism, PentagonalPyramid, Hexagon, PentagonalBipyramid, CappedOctahedron, CappedTrigonalPrism, SquareAntiprism, Cube, TrigonalDodecahedron, HexagonalBipyramid, TricappedTrigonalPrism, CappedSquareAntiprism, HeptagonalBipyramid, BicappedSquareAntiprism, EdgeContractedIcosahedron, Icosahedron, Cuboctahedron > allShapeDataTypes
Type collecting all types of the Symmetry classes.
Definition: Data.h:1805
An Option monadic type.
Definition: Optional.h:33
Finds the largest size value of a set of symmetries.
Definition: Properties.h:264
BTree-based std::set-like container (but max size is space allocated)
Centralizes basic shape data in runtime types.
const TetrahedronList & tetrahedra(const Shape shape)
Fetches the list of tetrahedra defined in a shape.
constexpr ArrayType< unsigned, ShapeClass::size > applyRotationImpl(const ArrayType< unsigned, ShapeClass::size > &indices, const unsigned rotationFunctionIndex, std::index_sequence< Indices...>)
Helper to perform applyRotation in constexpr fashion.
Definition: Properties.h:153
constexpr ArrayType< unsigned, size > symPosMapping(const ArrayType< unsigned, size > &mapping)
Transform shape positions through a mapping.
Definition: Properties.h:437
const RotationsList & rotations(const Shape shape)
Fetches a shape's list of rotations.
constexpr Temple::Vector getCoordinates(const unsigned indexInSymmetry)
Fetches the coordinates of an index in a shape.
Definition: Properties.h:288
constexpr unsigned rotationPeriodicityImpl(const ArrayType< unsigned, ShapeClass::size > &runningIndices, const unsigned count)
Helper to perform rotationPeriodicity in constexpr fashion.
Definition: Properties.h:183
constexpr void set(const std::size_t i)
Sets a specific bit.
Definition: Bitset.h:53
constexpr auto startingIndexSequence()
Generate an integer sequence to use with stereopermutations.
Definition: Properties.h:147
constexpr unsigned numUnlinkedStereopermutations(const unsigned nIdenticalLigands)
Calculate stereopermutations for an unlinked shape.
Definition: Properties.h:875
Functor to find out the minimum angle among all shape class types passed as template arguments...
Definition: Properties.h:114
Temple::Array< T, size > ArrayType
Definition: Properties.h:143
Central symmetry data class definitions.
static constexpr double value()
Minimum angle among all shape classes.
Definition: Properties.h:119
constexpr unsigned rotationPeriodicity()
Determines the multiplicity of a shape group rotation.
Definition: Properties.h:216
constexpr void clear()
Remove all elements of the set.
Definition: DynamicSet.h:78
Tree-based set.
Definition: DynamicSet.h:34
Constexpr bitset class.
Definition: Bitset.h:26
constexpr bool hasMultipleUnlinkedStereopermutations(const unsigned nIdenticalLigands)
Calculates whether a shape has multiple stereopermutations.
Definition: Properties.h:917
constexpr ArrayType< unsigned, ShapeClass::rotations.size()> rotationPeriodicitiesImpl(std::index_sequence< Inds...>)
Helper function to calculate all rotation periodicities.
Definition: Properties.h:229
Definition: FloatingPointComparison.h:190
constexpr T reduce(const ArrayType< T, size > &array, T init, BinaryFunction &&reduction)
Reduce an array-like container with a binary function.
Definition: Containers.h:88
constexpr std::enable_if_t< (SymmetryTarget::size<=7 &&(SymmetrySource::size==SymmetryTarget::size||SymmetrySource::size+1==SymmetryTarget::size)), Temple::Optional< MappingsReturnType >> calculateMapping()
If symmetries are adjacent, calculate their shape transition mapping.
Definition: Properties.h:843
unsigned size(const Shape shape)
Fetch the number of vertices of a shape.
constexpr double getTetrahedronVolume(const Temple::Vector &i, const Temple::Vector &j, const Temple::Vector &k, const Temple::Vector &l)
Calculates the volume of a tetrahedron spanned by four positions.
Definition: Properties.h:301
Metafunction calculating the smallest and largest angle that exist in a shape.
Definition: Properties.h:81
AngleFunction angleFunction(const Shape shape)
Gets a shape's angle function.
constexpr double calculateSmallestAngle()
Calculates the minimum angle returned in a shape class.
Definition: Properties.h:59
constexpr ArrayType< unsigned, ShapeClass::size > applyRotation(const ArrayType< unsigned, ShapeClass::size > &indices, const unsigned rotationFunctionIndex)
Applies a shape group rotation to an array of indices.
Definition: Properties.h:170
constexpr bool arraysEqual(const ArrayType< T, size > &a, const ArrayType< T, size > &b)
Array-like container lexicographic equality comparaotr.
Definition: Containers.h:280
Constexpr three-dimensional vector math class.
Definition: Vector.h:25
constexpr unsigned ORIGIN_PLACEHOLDER
A placeholder value for constexpr tetrahedra specification of origin.
Definition: Data.h:24
constexpr bool test(const std::size_t i) const
Test the value at a particular bit.
Definition: Bitset.h:90
constexpr double calculateAngularDistortion(const ArrayType< unsigned, size > &indexMapping, const size_t sourceSymmetrySize, const AngleFunctionPtr sourceAngleFunction, const AngleFunctionPtr targetAngleFunction)
Calculates angular distortion caused by a shape transition mapping.
Definition: Properties.h:326
static constexpr std::pair< double, double > value()
Smallest and largest angles of the ShapeClass.
Definition: Properties.h:86
Coordinates coordinates(const Shape shape)
Fetch a shape's idealized coordiantes.
constexpr auto ligandLossMappings(const unsigned deletedSymmetryPosition)
Find index mappings for ligand loss situations.
Definition: Properties.h:736
constexpr auto symmetryTransitionMappings()
Calculates ideal index mappings for +1, 0 size transitions.
Definition: Properties.h:635
constexpr double smallestAngle[[gnu::unused]]
The smallest angle between ligands in all symmetries.
Definition: PropertyCaching.h:46
constexpr unsigned maxShapeSize
The largest shape size defined in the library.
Definition: Properties.h:275
Calculate the multiplicities of all rotations of a shape.
Definition: Properties.h:253
constexpr unsigned propagateSymmetryPosition(const unsigned symmetryPosition, const ArrayType< unsigned, size > &indexMapping)
Propagates shape positions trhough an index mapping.
Definition: Properties.h:361
constexpr void insert(const T &item)
Insertion an element into the set.
Definition: DynamicSet.h:69
constexpr unsigned maxRotations()
Definition: Properties.h:503
std::size_t permutationIndex(const Container &container)
Calculate the index of permutation of elements in a container.
Definition: Permutations.h:25
Helpers for comparing floating point values.
constexpr auto generateAllRotations(const IndicesList< ShapeClass > &indices)
Generates all rotations of a sequence of indices within a shape group.
Definition: Properties.h:538