0

I am writing a code, which would input a vector ri and calculate the angles it makes with x, y and z axis. This way I will know the direction of the vector and be able to calculate the components of the force (which I calculate separately) in that direction. alfa is the angle between the vector and z axis, beta is the angle between the vector and x axis, gamma is the angle between the vector and y axis.

Here is the code that does that:

long double length_of_vector, alfa, betta, gamma, x_force, y_force, z_force;

vector<double> ri = {0, -3.85443e-07, 5.98761e-06} ;

length_of_vector = sqrt(pow(ri[0],2)+pow(ri[1],2)+pow(ri[2],2)) ;

    alfa = acos(ri[2]/length_of_vector);  //angle with z axis

    betta = acos ( ri[0] / (length_of_vector * sin(alfa)) ) ; //angle with x axis

    gamma = acos ( ri[1] / (length_of_vector * sin(alfa)) ) ; //angle with y axis

    cout<< "alfa is: " << alfa * 180/M_PI << endl ;
    cout<< "betta is: " << betta * 180/M_PI<< endl ;
    cout<< "gamma is: " << gamma* 180/M_PI << endl ;
    cout<< "length is: " << length_of_vector << endl ;
    //------------------------------------------------END OF ANGLE CALCULATIONS

    if ((ri[1] == 0)&&(ri[2]==0)) {
    x_forces += length_of_vector * sin(alfa) * cos(betta) ;
    }
    else if ((ri[0] == 0)&&(ri[2]==0)) {
        y_forces += length_of_vector * sin(alfa) * cos(gamma) ;
    }
    else if ((ri[0] == 0)&&(ri[1]==0)) {
        z_forces += length_of_vector * cos(alfa) ;
    }
    else if (ri[0] == 0) {
        y_forces += length_of_vector * sin(alfa) * cos(gamma) ;
        z_forces += length_of_vector * cos(alfa) ;
    }
    else if (ri[1] == 0) {
        x_forces += length_of_vector * sin(alfa) * cos(betta) ;
        z_forces += length_of_vector * cos(alfa) ;
    }
    else if (ri[2] == 0) {
        x_forces += length_of_vector * sin(alfa) * cos(betta) ;
        y_forces += length_of_vector * sin(alfa) * cos(gamma) ;
    }
    else {
        x_forces += length_of_vector * sin(alfa) * cos(betta) ;
        y_forces += length_of_vector * sin(alfa) * cos(gamma) ;
        z_forces += length_of_vector * cos(alfa) ;
    }

As you can see here, instead of length_of_vector in the if statements I must insert the magnitude of force, which will get summed into x_force, y_force and z_force. However, for validation purposes I put length_of_vector there. Thus, the answer that I receive must represent the components of the vector that I initially inputted.

I input ri (which is a vector<double>) as {0, -3.85443e-07, 5.98761e-06}. This is what I get:

x_force = 0
y_force = nan
z_force = 5.98761e-06

As can be seen, I get that y_force gets calculated as nan. I traced the code, I realized that it is nan because the value of gamma becomes nan, while trying to calculate that angle.

If I change the value of the y component of ri to -3.85443e-05 , I will get the correct answer but everything smaller than that value will give me gamma = nan. I do not understand why this is happening at all. Does that mean that the vector {0, -3.85443e-07, 5.98761e-06} does not exist? Please help!

Ruffi
  • 23
  • 5
  • What are the inputs to the `gamma` calculation when you trace it? – JohnFilleau Apr 12 '20 at 20:05
  • The formulas you use don't look right to me. The problem statement is symmetrical in x, y and z, so it doesn't look right that `alfa` is calculated differently from `betta` and `gamma`. I don't think `sin(alfa)` is supposed to be there. – Igor Tandetnik Apr 12 '20 at 20:09
  • @IgorTandetnik I believe they are correct and can be easily derived by drawing a cartesian space (x y and z axis) with a vector coming out from the origin. Then, using the definition of alfa, betta and gamma from the question, use trigonometry to find vector projections on each individual axis. – Ruffi Apr 12 '20 at 20:13
  • 1
    If you have a vector with `ri[2] == 0`, then `alfa` is zero, `sin(alfa)` is zero and you attempt to delete by zero. – Igor Tandetnik Apr 12 '20 at 20:15
  • @IgorTandetnik I used the spherical coordinates principle: https://images.app.goo.gl/7ckxKREADxkF2YtEA – Ruffi Apr 12 '20 at 20:16
  • @IgorTandetnik If ri[2] == 0, then alfa is 90 degrees or pi/2 in radians. – Ruffi Apr 12 '20 at 20:18
  • 1
    Your formula for `length_of_vector` assumes components of `ri` are cartesian coordinates. – Igor Tandetnik Apr 12 '20 at 20:18
  • 1
    In cartesian system, the cosine of the angle between two vectors is their scalar product divided by the product of their lengths: `cos(theta) = u*v/(|u|*|v|)`. Axes are simply vectors (1, 0, 0), (0, 1, 0) and (0, 0, 1), and the scalar product with a given axis is simply the corresponding component of the vector. Thus, `cos(angle_i) = v_i / length(v)` – Igor Tandetnik Apr 12 '20 at 20:24
  • 1
    If components of `ri` are meant to be interpreted as spherical coordinates, then one of them is the length; your formula for `length_of_vector` then doesn't make sense. – Igor Tandetnik Apr 12 '20 at 20:25
  • Let us [continue this discussion in chat](https://chat.stackoverflow.com/rooms/211507/discussion-between-ruffi-and-igor-tandetnik). – Ruffi Apr 12 '20 at 21:38

0 Answers0