-
Notifications
You must be signed in to change notification settings - Fork 6
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Rotor Inaccuracies - Exp Bug #21
Comments
I believe I had made a mistake in using Making this change, however, yields even stranger results:
EDIT:
With the result being the following:
|
Hi @Tannz0rz, I believe you have found a bug in the exp function. The result is correct when the rotor is set to: float alpha = 3.141592f * 0.5f;
auto rotor = cos(alpha / 2) - sin(alpha / 2) * (e1 ^ e2); Please, find below a cleaner and commented version of the source code: #include <gatl/ga3h.hpp>
using namespace ga3h;
int main(int argc, char **argv)
{
float alpha = 3.141592f * 0.5f;
auto const right = 1.0f * e1 + 0.0f * e2 + 0.0f * e3; // The function `euclidean_vector(1.0f, 0.0f, 0.0f)` is a shortcut for defining vectors with homogeneous coordinates equals to zero. It is faster because it applies lazy evaluation.
auto const forward = 0.0f * e1 + 1.0f * e2 + 0.0f * e3;
auto const up = 0.0f * e1 + 0.0f * e2 + 1.0f * e3;
auto rotor_exp = exp((-alpha / 2) * (e1 ^ e2));
std::cout << "Rotor using exp(): " << rotor_exp << " (Reverse Norm: " << rnorm(rotor_exp) << ")" << std::endl; // This rotor is not correct (it seems a bug in the exp function).
std::cout << std::endl;
auto rotor = cos(alpha / 2) - sin(alpha / 2) * (e1 ^ e2);
std::cout << "Rotor: " << rotor << " (Reverse Norm: " << rnorm(rotor) << ")" << std::endl; // This rotor is correct.
std::cout << std::endl;
auto const right_rotated = apply_rotor(rotor, right); // Equivalent to `rotor * right * inv(rotor)` and `rotor * right * ~rotor`, but faster because it explores lazy evaluation.
auto const forward_rotated = apply_rotor(rotor, forward);
auto const up_rotated = apply_rotor(rotor, up);
std::cout << "Right: " << right_rotated << std::endl; // Use the << operator to print multivectors.
std::cout << "Forward: " << forward_rotated << std::endl;
std::cout << "Up: " << up_rotated << std::endl;
return EXIT_SUCCESS;
} I will investigate and fix the cause of the problem. But at the moment I'm swamped with work and so I won't be able to dedicate myself to it until next weekend. Thank you for pointing out this issue. About the float alpha = 3.141592f * 0.5f;
auto rotor = cos(alpha / 2) - sin(alpha / 2) * (e1 ^ e3);
auto x = 10.0f * e1;
auto x_ = apply_rotor(rotor, x); // x_ = 3.8147e-06 * <e1> + 10 * <e3>
auto y = 10.0f * e1 + 0.0f * e2;
auto y_ = apply_rotor(rotor, x); // y_ = 3.8147e-06 * <e1> + 0 * <e2> + 10 * <e3> Notice that |
Understood regarding your workload. Is there a way to provide these resulting rotated vectors with the explicit type of |
The option in that case is to declare the variable as #include <gatl/ga3h.hpp>
using namespace ga3h;
int main(int argc, char **argv)
{
float alpha = 3.141592f * 0.5f;
auto rotor = cos(alpha / 2) - sin(alpha / 2) * (e1 ^ e3);
auto x = 10.0f * e1;
full_vector_t<float, 4> r_;
trivial_copy(apply_rotor(rotor, x), r_);
std::cout << r_ << std::endl;
return EXIT_SUCCESS;
} |
Could the |
Ok, I will do (almost) that with the For performance purposes, I strongly suggest avoiding these copies, as it is possible to extract the coefficients (even the zeros) from the result inferred by |
One last semi-related question Dr. Fernandes. How would I approach the explicit type declaration of a rotor/quaternion, which is equivalent to declaring a multivector consisting of a scalar part and three bivector parts in G^{3}? I understand your feelings with regard to the use of EDIT: Furthermore, I would like to pass these rotor/quaternion types (for which I believe there are 8 possible permutations of multivectors in G^{3}, including the identity) to a member function using SFINAE e.g. |
The dirty trick uses the using rotor_t = decltype(float() + float() * (e1^e2) + float() * (e1^e3) + float() * (e2^e3)); You can do that to deduce the resulting type of any C++ expression. It is part of the language, not the library. So, by defining an expression with the components you want, you get the multivector type. The order of the elements is important for GATL. Using the expression presented above, you will get the only permutation that GATL accepts as valid. That is part of the library, so it can not be changed. It means that using rotor1_t = decltype(float() + float() * (e1^e2) + float() * (e1^e3) + float() * (e2^e3));
using rotor2_t = decltype(float() + float() * (e1^e2) + float() * (e2^e3) + float() * (e1^e3)); Using the |
I wanted to update you with what I have been doing exactly. I made a I deliberately keep the rotors and translators separate in case the user may wish to set a global rotor while retaining a local translator, for example. As you can see there are a few instances where I do not believe I can avoid using All-in-all, I want to say thank you so much for this library Dr. Fernandes, I am really enjoying it so far. This is how math in C++ should be. It is time to move away from Eigen and onto GATL! Could you perhaps review my code and make suggestions? I wish I could move the |
Hello Dr. Fernandes,
In the example below I rotate the "right" (+x), "forward" (+y), and "up" (+z) vectors by a 90-degree rotor about the
e1^e2
bivector.This outputs are the following:
The rotated "up" is as expected, resulting in the same vector. However, the rotated "right" is not, where the expected result would be the "forward" (+y) vector of
0.0f * e1 + 1.0f * e2 + 0.0f * e3
. While the coefficient ofe2
is certainly close to1.0f
, the coefficient ofe1
is much larger than it should be. The result is similar for "forward".Am I doing something wrong here? I am still in the process of learning Geometric Algebra, so perhaps I am misunderstanding something.
Additionally, in the above example how would I replace all of the
auto
keywords with their explicit types? I understand that "right", "forward", and "up" should be of typefull_kvector_t<float, 3, 1>
, but I am uncertain what the type of "rotor" and the rotated vectors should be.Regards,
Casey
The text was updated successfully, but these errors were encountered: