16 #ifndef INCLUDED_numeric_deriv_angle_deriv_hh
17 #define INCLUDED_numeric_deriv_angle_deriv_hh
82 static Real
const small_angle(
radians(
Real(0.1) ) );
83 static Real
const big_angle(
radians(
Real(179.9) ) );
84 static Real
const max_x( std::cos( small_angle ));
85 static Real
const min_x( std::cos( big_angle ));
91 Real
const n1( v1.
length() );
92 Real
const n2( v2.
length() );
93 if ( n1 <
Real(1e-9) || n2 <
Real(1e-9) ) {
99 Real
x =
dot(v1,v2)/(n1*n2);
105 Vector f1(0.0),f2(0.0);
108 Real
const f =
Real(1.0) / ( n1 * n2 );
109 helper( p1, f * v2, f1, f2 );
113 Real
const f =
Real(-1.0) * x / ( n1 * n1 );
114 helper( p1, f * v1, f1, f2 );
118 Real
const dtheta_dx =
Real(-1.0) / sqrt(
Real(1.0) - x*x );
123 assert( f1.distance(
cross(f2,p1) ) <
Real(1e-3) &&
169 static Real
const small_angle(
radians(
Real(0.1) ) );
170 static Real
const big_angle(
radians(
Real(179.9) ) );
171 static Real
const max_x( std::cos( small_angle ));
172 static Real
const min_x( std::cos( big_angle ));
174 x =
dot(v1,v2)/(n1*n2);
176 dtheta_dx =
Real(-1.0) / sqrt(
Real(1.0) - x*x );
221 if ( n1 <
Real(1e-9) || n2 <
Real(1e-9) ) {
233 Vector f1(0.0),f2(0.0);
236 Real
const f =
Real(1.0) / ( n1 * n2 );
237 helper( p1, f * v2, f1, f2 );
241 Real
const f =
Real(-1.0) * x / ( n1 * n1 );
242 helper( p1, f * v1, f1, f2 );
305 Vector u1( p1 - p2 );
306 Vector u2( p3 - p2 );
308 if ( n1_n2 <
Real(1e-12) ) {
309 std::cout <<
"AngleConstraint::p1_deriv: short bonds: " << n1_n2 <<
316 Real d(
dot(u1,u2) / n1_n2 );
317 Real
const tol(1.0e-8);
318 if ( d <=
Real(-1.0) + tol ) {
321 }
else if ( d >=
Real(1.0) - tol ) {
361 Vector v1( p1 - p2 );
362 Vector v2( p3 - p2 );
364 if ( v12 <
Real(1e-12) )
return;
382 Real d(
dot(v1,v2) / v12 );
383 Real
const tol(0.001);
384 if ( d <=
Real(-1.0) + tol ) {
387 }
else if ( d >=
Real(1.0) - tol ) {
419 f1_p1 = f2_p1 = f1_p2 = f2_p2 = f1_p3 = f2_p3 =
Real(0.0);
422 Vector v12( p1 - p2 );
423 Vector v32( p3 - p2 );
425 Real
const n12( v12.
length() );
426 Real
const n23( v32.
length() );
428 Real
const n12n23( n12 * n23 );
429 if ( n12n23 <
Real(1e-12) )
return;
431 Real x13, dtheta_dx13;
433 p1_theta_deriv( p1, v12, v32, n12, n23, x13, dtheta_dx13, f1_p1, f2_p1 );
434 p1_theta_deriv( p3, v32, v12, n23, n12, x13, dtheta_dx13, f1_p3, f2_p3 );
446 Vector v21 = -1 * v12;
447 Vector v31 = p3 - p1;
448 Real
const n13 = v31.
length();
449 Real alpha_x, alpha_dtheta_dx;
451 p1_theta_deriv( p2, v21, v31, n12, n13, alpha_x, alpha_dtheta_dx, f1_p2, f2_p2 );
454 Vector v23 = -1 * v32;
455 Vector v13 = -1 * v31;
456 Real beta_x, beta_dtheta_dx;
458 p1_theta_deriv( p2, v23, v13, n23, n13, beta_x, beta_dtheta_dx, f1_p2, f2_p2 );
460 f1_p2 *=
Real( -1.0 );
461 f2_p2 *=
Real( -1.0 );
463 Real d(
dot(v12,v32) / n12n23 );
464 Real
const tol(0.001);
465 if ( d <=
Real(-1.0) + tol ) {
468 }
else if ( d >=
Real(1.0) - tol ) {
void normalized(xyzVector &a) const
Normalized.
cmplx w(cmplx z, double relerr)
#define ASSERT_ONLY(x)
Macro wrapper for paramters that used only indebug_assert(...) statments. Intended to supress 'unused...
Conversions between degrees and radians.
Value length() const
Length.
void p1_theta_deriv(xyzVector< P > const &p1, xyzVector< P > const &p2, xyzVector< P > const &p3, xyzVector< P > &F1, xyzVector< P > &F2)
xyzVector: Fast (x,y,z)-coordinate numeric vector
T abs(T const &x)
std::abs( x ) == | x |
void x_and_dtheta_dx(xyzVector< P > const &v1, xyzVector< P > const &v2, P const n1, P const n2, P &x, P &dtheta_dx)
void angle_p1_p2_p3_deriv(xyzVector< P > const &p1, xyzVector< P > const &p2, xyzVector< P > const &p3, P &theta, xyzVector< P > &f1_p1, xyzVector< P > &f2_p1, xyzVector< P > &f1_p2, xyzVector< P > &f2_p2, xyzVector< P > &f1_p3, xyzVector< P > &f2_p3)
void helper(xyzVector< P > const &M, xyzVector< P > const &w, xyzVector< P > &F1, xyzVector< P > &F2)
xyzTriple< T > cross(xyzTriple< T > const &a, xyzTriple< T > const &b)
Cross product.
ocstream cout(std::cout)
Wrapper around std::cout.
T radians(T const °rees)
Radians of degrees.
void angle_p2_deriv(xyzVector< P > const &p1, xyzVector< P > const &p2, xyzVector< P > const &p3, P &theta, xyzVector< P > &f1, xyzVector< P > &f2)
compute f1/f2 atom derivative vectors for the middle point defining an angle. Templated on the precis...
Fast (x,y,z)-coordinate numeric vector.
T arccos(T const x)
like std::acos but with range checking
T dot(Quaternion< T > const &q1, Quaternion< T > const &q2)
Dot product.
void angle_p1_deriv(xyzVector< P > const &p1, xyzVector< P > const &p2, xyzVector< P > const &p3, P &theta, xyzVector< P > &f1, xyzVector< P > &f2)
compute f1/f2 atom derivative vectors for the first point defining an angle. Templated on the precisi...