ProSHADE  0.7.6.2 (DEC 2021)
Protein Shape Detection
ProSHADE_symmetry.cpp File Reference

This source file contains all the functions required to detect symmetry axes and types from the inverse SOFT map. More...

Go to the source code of this file.

Functions

proshade_double determinePeakThreshold (std::vector< proshade_double > inArr, proshade_double noIQRsFromMedian)
 This function takes a vector of values and determines the threshold for removing noise from it. More...
 
bool sortProSHADESymmetryByPeak (proshade_double *a, proshade_double *b)
 This function allows using std::sort to sort vectors of ProSHADE symmetry format.. More...
 
std::vector< std::pair< proshade_unsign, proshade_unsign > > findBestIcosDihedralPair (std::vector< proshade_double * > *CSymList, proshade_double minPeakHeight, proshade_double axErr)
 This function finds all the pairs of axes conforming to the icosahedron dihedral angle. More...
 
std::pair< proshade_unsign, proshade_unsign > findBestOctaDihedralPair (std::vector< proshade_double * > *CSymList, proshade_double minPeakHeight, proshade_double axErr)
 This function finds the best pair of axes conforming to the octahedron dihedral angle. More...
 
std::pair< proshade_unsign, proshade_unsign > findBestTetraDihedralPair (std::vector< proshade_double * > *CSymList, proshade_double minPeakHeight, proshade_double axErr)
 This function finds the best pair of axes conforming to the tetrahedron dihedral angle. More...
 

Detailed Description

This source file contains all the functions required to detect symmetry axes and types from the inverse SOFT map.

The functions in this source file are required to allow detection of symmetry axes and symmetries from the inverse SOFT map. The currect functionality can detect C, D, T, O and I symmetries with the C and D symmetries having their fold automatically detected as well.

Copyright by Michal Tykac and individual contributors. All rights reserved.

Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1) Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2) Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3) Neither the name of Michal Tykac nor the names of this code's contributors may be used to endorse or promote products derived from this software without specific prior written permission.

This software is provided by the copyright holder and contributors "as is" and any express or implied warranties, including, but not limitted to, the implied warranties of merchantibility and fitness for a particular purpose are disclaimed. In no event shall the copyright owner or the contributors be liable for any direct, indirect, incidental, special, exemplary, or consequential damages (including, but not limitted to, procurement of substitute goods or services, loss of use, data or profits, or business interuption) however caused and on any theory of liability, whether in contract, strict liability or tort (including negligence or otherwise) arising in any way out of the use of this software, even if advised of the possibility of such damage.

Author
Michal Tykac
Garib N. Murshudov
Version
0.7.6.2
Date
DEC 2021

Definition in file ProSHADE_symmetry.cpp.

Function Documentation

◆ determinePeakThreshold()

proshade_double determinePeakThreshold ( std::vector< proshade_double >  inArr,
proshade_double  noIQRsFromMedian 
)

This function takes a vector of values and determines the threshold for removing noise from it.

Parameters
[in]inArrA vector of values for which the threshold is to be determined.
[out]retThe threshold.

Definition at line 71 of file ProSHADE_symmetry.cpp.

72 {
73  //================================================ Initialise variables
74  proshade_double ret = 0.0;
75  proshade_double rmsd = 0.0;
76  size_t vecSize = inArr.size();
77 
78  //================================================ Deal with low number of input cases
79  if ( vecSize == 0 ) { return ( ret ); } // Return 0
80  if ( vecSize <= 4 ) { ret = std::accumulate ( inArr.begin(), inArr.end(), 0.0 ) / static_cast< proshade_double > ( vecSize ); return ( ret ); } // Return mean
81 
82  //================================================ Deal with reasonable number in input cases
83  else
84  {
85  //============================================ Find mean
86  ret = std::accumulate ( inArr.begin(), inArr.end(), 0.0 ) / static_cast< proshade_double > ( vecSize );
87 
88  //============================================ Get the RMS distance
89  for ( size_t i = 0; i < vecSize; i++ )
90  {
91  rmsd += std::pow ( ret - inArr.at(i), 2.0 );
92  }
93  rmsd = std::sqrt ( rmsd );
94 
95  //============================================ Get the threshold
96  ret = ret + ( noIQRsFromMedian * rmsd );
97  }
98 
99  //================================================ Sanity checks
100  if ( ret > *( std::max_element ( inArr.begin(), inArr.end() ) ) )
101  {
102  ret = *( std::max_element ( inArr.begin(), inArr.end() ) );
103  }
104 
105  //================================================ Done
106  return ( ret );
107 
108 }

◆ findBestIcosDihedralPair()

std::vector< std::pair< proshade_unsign, proshade_unsign > > findBestIcosDihedralPair ( std::vector< proshade_double * > *  CSymList,
proshade_double  minPeakHeight,
proshade_double  axErr 
)

This function finds all the pairs of axes conforming to the icosahedron dihedral angle.

Parameters
[in]CSymListA vector containing the already detected Cyclic symmetries.
[in]minPeakHeightThe minimum average peak height for axis to be considered.
[in]axErrThe error tolerance on angle matching.
[out]retVector of pairs containing the indices of all axes conforming to the required icosahedron dihedral angle.

Definition at line 2091 of file ProSHADE_symmetry.cpp.

2092 {
2093  //================================================ Initialise variables
2094  std::vector < std::pair< proshade_unsign, proshade_unsign > > ret;
2095  std::vector< proshade_unsign > C5List;
2096  proshade_double dotProduct;
2097 
2098  //================================================ Find all C5 symmetries
2099  for ( proshade_unsign cSym = 0; cSym < static_cast<proshade_unsign> ( CSymList->size() ); cSym++ ) { const FloatingPoint< proshade_double > lhs1 ( CSymList->at(cSym)[0] ), rhs1 ( 5.0 ); if ( lhs1.AlmostEquals ( rhs1 ) && CSymList->at(cSym)[5] >= minPeakHeight ) { ProSHADE_internal_misc::addToUnsignVector ( &C5List, cSym ); } }
2100 
2101  //================================================ For each unique pair of C5 and C3
2102  for ( proshade_unsign c5 = 0; c5 < static_cast<proshade_unsign> ( C5List.size() ); c5++ )
2103  {
2104  for ( proshade_unsign cSym = 0; cSym < static_cast<proshade_unsign> ( CSymList->size() ); cSym++ )
2105  {
2106  //======================================== Compare only C3s to the C5List and only with decent average peak height
2107  const FloatingPoint< proshade_double > lhs1 ( CSymList->at(cSym)[0] ), rhs1 ( 3.0 );
2108  if ( !lhs1.AlmostEquals ( rhs1 ) ) { continue; }
2109  if ( CSymList->at(cSym)[5] < minPeakHeight ) { continue; }
2110 
2111  //======================================== Check the angle between the C5 and C3 axes
2112  dotProduct = ProSHADE_internal_maths::computeDotProduct ( &CSymList->at(C5List.at(c5))[1],
2113  &CSymList->at(C5List.at(c5))[2],
2114  &CSymList->at(C5List.at(c5))[3],
2115  &CSymList->at(cSym)[1],
2116  &CSymList->at(cSym)[2],
2117  &CSymList->at(cSym)[3] );
2118 
2119  //======================================== Is the angle approximately the dihedral angle?
2120  if ( std::abs ( std::abs( std::sqrt ( ( 1.0 + 2.0 / std::sqrt ( 5.0 ) ) / 3.0 ) ) - std::abs( dotProduct ) ) < axErr )
2121  {
2122  std::pair< proshade_unsign, proshade_unsign > hlp;
2123  hlp.first = C5List.at(c5);
2124  hlp.second = cSym;
2125  ret.emplace_back ( hlp );
2126  }
2127  }
2128  }
2129 
2130  //================================================ Done
2131  return ( ret );
2132 }

◆ findBestOctaDihedralPair()

std::pair< proshade_unsign, proshade_unsign > findBestOctaDihedralPair ( std::vector< proshade_double * > *  CSymList,
proshade_double  minPeakHeight,
proshade_double  axErr 
)

This function finds the best pair of axes conforming to the octahedron dihedral angle.

Parameters
[in]CSymListA vector containing the already detected Cyclic symmetries.
[in]minPeakHeightThe minimum average peak height for axis to be considered.
[in]axErrThe error tolerance on angle matching.
[out]retThe pair of axes with closest angle to the required icosahedron dihedral angle.

Definition at line 2270 of file ProSHADE_symmetry.cpp.

2271 {
2272  //================================================ Initialise variables
2273  std::pair< proshade_unsign, proshade_unsign > ret;
2274  std::vector< proshade_unsign > C4List;
2275  proshade_double bestHeightSum = 0.0;
2276  proshade_double dotProduct;
2277 
2278  //================================================ Find all C5 symmetries
2279  for ( proshade_unsign cSym = 0; cSym < static_cast<proshade_unsign> ( CSymList->size() ); cSym++ ) { const FloatingPoint< proshade_double > lhs1 ( CSymList->at(cSym)[0] ), rhs1 ( 4.0 ); if ( lhs1.AlmostEquals ( rhs1 ) && CSymList->at(cSym)[5] >= minPeakHeight ) { ProSHADE_internal_misc::addToUnsignVector ( &C4List, cSym ); } }
2280 
2281  //================================================ For each unique pair of C5 and C3
2282  for ( proshade_unsign c4 = 0; c4 < static_cast<proshade_unsign> ( C4List.size() ); c4++ )
2283  {
2284  for ( proshade_unsign cSym = 0; cSym < static_cast<proshade_unsign> ( CSymList->size() ); cSym++ )
2285  {
2286  //======================================== Compare only C3s to the C5List and only with decent average peak height
2287  const FloatingPoint< proshade_double > lhs1 ( CSymList->at(cSym)[0] ), rhs1 ( 3.0 );
2288  if ( !lhs1.AlmostEquals ( rhs1 ) ) { continue; }
2289  if ( CSymList->at(cSym)[5] < minPeakHeight ) { continue; }
2290 
2291  //======================================== Check the angle between the C5 and C3 axes
2292  dotProduct = ProSHADE_internal_maths::computeDotProduct ( &CSymList->at(C4List.at(c4))[1],
2293  &CSymList->at(C4List.at(c4))[2],
2294  &CSymList->at(C4List.at(c4))[3],
2295  &CSymList->at(cSym)[1],
2296  &CSymList->at(cSym)[2],
2297  &CSymList->at(cSym)[3] );
2298 
2299  //======================================== Is the angle approximately the dihedral angle?
2300  if ( ( ( 1.0 / sqrt ( 3.0 ) ) > ( std::abs( dotProduct ) - axErr ) ) && ( ( 1.0 / sqrt ( 3.0 ) ) < ( std::abs( dotProduct ) + axErr ) ) )
2301  {
2302  if ( bestHeightSum < ( CSymList->at(C4List.at(c4))[5] + CSymList->at(cSym)[5] ) )
2303  {
2304  bestHeightSum = ( CSymList->at(C4List.at(c4))[5] + CSymList->at(cSym)[5] );
2305  ret.first = C4List.at(c4);
2306  ret.second = cSym;
2307  }
2308  }
2309  }
2310  }
2311 
2312  //================================================ Done
2313  return ( ret );
2314 
2315 }

◆ findBestTetraDihedralPair()

std::pair< proshade_unsign, proshade_unsign > findBestTetraDihedralPair ( std::vector< proshade_double * > *  CSymList,
proshade_double  minPeakHeight,
proshade_double  axErr 
)

This function finds the best pair of axes conforming to the tetrahedron dihedral angle.

Parameters
[in]CSymListA vector containing the already detected Cyclic symmetries.
[in]minPeakHeightThe minimum average peak height for axis to be considered.
[in]axErrThe error tolerance on angle matching.
[out]retThe pair of axes with closest angle to the required icosahedron dihedral angle.

Definition at line 3444 of file ProSHADE_symmetry.cpp.

3445 {
3446  //================================================ Initialise variables
3447  std::pair< proshade_unsign, proshade_unsign > ret;
3448  std::vector< proshade_unsign > C3List;
3449  proshade_double bestHeightSum = 0.0;
3450  proshade_double dotProduct;
3451 
3452  //================================================ Find all C3 symmetries
3453  for ( proshade_unsign cSym = 0; cSym < static_cast<proshade_unsign> ( CSymList->size() ); cSym++ ) { const FloatingPoint< proshade_double > lhs1 ( CSymList->at(cSym)[0] ), rhs1 ( 3.0 ); if ( lhs1.AlmostEquals ( rhs1 ) && CSymList->at(cSym)[5] >= minPeakHeight ) { ProSHADE_internal_misc::addToUnsignVector ( &C3List, cSym ); } }
3454 
3455  //================================================ For each unique pair of C3 and C2
3456  for ( proshade_unsign c3 = 0; c3 < static_cast<proshade_unsign> ( C3List.size() ); c3++ )
3457  {
3458  for ( proshade_unsign cSym = 0; cSym < static_cast<proshade_unsign> ( CSymList->size() ); cSym++ )
3459  {
3460  //======================================== Compare only C2s to the C3List and only with decent average peak height
3461  const FloatingPoint< proshade_double > lhs1 ( CSymList->at(cSym)[0] ), rhs1 ( 2.0 );
3462  if ( !lhs1.AlmostEquals ( rhs1 ) ) { continue; }
3463  if ( CSymList->at(cSym)[5] < minPeakHeight ) { continue; }
3464 
3465  //======================================== Check the angle between the C5 and C3 axes
3466  dotProduct = ProSHADE_internal_maths::computeDotProduct ( &CSymList->at(C3List.at(c3))[1],
3467  &CSymList->at(C3List.at(c3))[2],
3468  &CSymList->at(C3List.at(c3))[3],
3469  &CSymList->at(cSym)[1],
3470  &CSymList->at(cSym)[2],
3471  &CSymList->at(cSym)[3] );
3472 
3473  //======================================== Is the angle approximately the dihedral angle?
3474  if ( ( ( 1.0 / sqrt ( 3.0 ) ) > ( std::abs( dotProduct ) - axErr ) ) && ( ( 1.0 / sqrt ( 3.0 ) ) < ( std::abs( dotProduct ) + axErr ) ) )
3475  {
3476  if ( bestHeightSum < ( CSymList->at(C3List.at(c3))[5] + CSymList->at(cSym)[5] ) )
3477  {
3478  bestHeightSum = CSymList->at(C3List.at(c3))[5] + CSymList->at(cSym)[5];
3479  ret.first = C3List.at(c3);
3480  ret.second = cSym;
3481  }
3482  }
3483  }
3484  }
3485 
3486  //================================================ Done
3487  return ( ret );
3488 
3489 }

◆ sortProSHADESymmetryByPeak()

bool sortProSHADESymmetryByPeak ( proshade_double *  a,
proshade_double *  b 
)

This function allows using std::sort to sort vectors of ProSHADE symmetry format..

Parameters
[in]aPointer to a ProSHADE symmetry formatted array.
[in]bPointer to a ProSHADE symmetry formatted array.
[out]XBoolean whether a is larger than b.

Definition at line 2886 of file ProSHADE_symmetry.cpp.

2887 {
2888  //================================================ Done
2889  return ( a[5] > b[5] );
2890 
2891 }
ProSHADE_internal_maths::computeDotProduct
proshade_double computeDotProduct(proshade_double *x1, proshade_double *y1, proshade_double *z1, proshade_double *x2, proshade_double *y2, proshade_double *z2)
Simple 3D vector dot product computation.
Definition: ProSHADE_maths.cpp:1788
ProSHADE_internal_misc::addToUnsignVector
void addToUnsignVector(std::vector< proshade_unsign > *vecToAddTo, proshade_unsign elementToAdd)
Adds the element to the vector.
Definition: ProSHADE_misc.cpp:99