// Software License for MTL // // Copyright (c) 2007 The Trustees of Indiana University. // 2008 Dresden University of Technology and the Trustees of Indiana University. // 2010 SimuNova UG (haftungsbeschränkt), www.simunova.com. // All rights reserved. // Authors: Peter Gottschling and Andrew Lumsdaine // // This file is part of the Matrix Template Library // // See also license.mtl.txt in the distribution. #ifndef MTL_VECTOR_CROSS_INCLUDE #define MTL_VECTOR_CROSS_INCLUDE #include <boost/numeric/mtl/concept/std_concept.hpp> #include <boost/numeric/mtl/vector/dense_vector.hpp> #include <boost/numeric/mtl/interface/vpt.hpp> namespace mtl { namespace vector { namespace detail { // Result type of cross product template <typename Vector1, typename Vector2> struct cross_result { typedef typename Multiplicable<typename Collection<Vector1>::value_type, typename Collection<Vector2>::value_type>::result_type value; typedef dense_vector<value> type; }; } /// Cross product /** Only exists for 3 and 7 dimensions. Consider specialization for fixed-size types **/ template <typename Vector1, typename Vector2> typename detail::cross_result<Vector1, Vector2>::type inline cross(const Vector1& v1, const Vector2& v2) { vampir_trace<2002> tracer; MTL_THROW_IF((size(v1) != 3 && size(v1) != 7 ) || size(v1) != size(v2), incompatible_size()); typename detail::cross_result<Vector1, Vector2>::type result(size(v1)); if (size(v1) == 3) for (unsigned i= 0; i < 3; i++) { unsigned k= (i+1) % 3, l= (i+2) % 3; result[i]= v1[k] * v2[l] - v1[l] * v2[k]; } else // must be 7 thus for (unsigned i= 0; i < 7; i++) { unsigned k= (i+1) % 7, l= (i+3) % 7; result[i]= v1[k] * v2[l] - v1[l] * v2[k]; k= (i+2) % 7, l= (i+6) % 7; result[i]+= v1[k] * v2[l] - v1[l] * v2[k]; k= (i+4) % 7, l= (i+5) % 7; result[i]+= v1[k] * v2[l] - v1[l] * v2[k]; } return result; } }} // namespace mtl::vector #endif // MTL_VECTOR_CROSS_INCLUDE