Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-09-13 08:50:03

0001 #ifndef BOOST_QVM_DETAIL_DETERMINANT_IMPL_HPP_INCLUDED
0002 #define BOOST_QVM_DETAIL_DETERMINANT_IMPL_HPP_INCLUDED
0003 
0004 // Copyright 2008-2024 Emil Dotchevski and Reverge Studios, Inc.
0005 // Distributed under the Boost Software License, Version 1.0. (See accompanying
0006 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
0007 
0008 #include <boost/qvm/config.hpp>
0009 #include <boost/qvm/mat_traits_array.hpp>
0010 #include <boost/qvm/static_assert.hpp>
0011 
0012 namespace boost { namespace qvm {
0013 
0014 namespace
0015 qvm_detail
0016     {
0017     template <int N>
0018     struct
0019     det_size
0020         {
0021         };
0022 
0023     template <class M>
0024     BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0025     typename mat_traits<M>::scalar_type
0026     determinant_impl_( M const & a, det_size<2> )
0027         {
0028         return
0029             mat_traits<M>::template read_element<0,0>(a) * mat_traits<M>::template read_element<1,1>(a) -
0030             mat_traits<M>::template read_element<1,0>(a) * mat_traits<M>::template read_element<0,1>(a);
0031         }
0032 
0033     template <class M,int N>
0034     BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_RECURSION
0035     typename mat_traits<M>::scalar_type
0036     determinant_impl_( M const & a, det_size<N> )
0037         {
0038         typedef typename mat_traits<M>::scalar_type T;
0039         T m[N-1][N-1];
0040         T det=T(0);
0041         for( int j1=0; j1!=N; ++j1 )
0042             {
0043             for( int i=1; i!=N; ++i )
0044                 {
0045                 int j2 = 0;
0046                 for( int j=0; j!=N; ++j )
0047                     {
0048                     if( j==j1 )
0049                         continue;
0050                     m[i-1][j2] = mat_traits<M>::read_element_idx(i,j,a);
0051                     ++j2;
0052                     }
0053                 }
0054             T d=determinant_impl_(m,det_size<N-1>());
0055             if( j1&1 )
0056                 d=-d;
0057             det += mat_traits<M>::read_element_idx(0,j1,a) * d;
0058             }
0059         return det;
0060         }
0061 
0062     template <class M>
0063     BOOST_QVM_CONSTEXPR BOOST_QVM_INLINE_TRIVIAL
0064     typename mat_traits<M>::scalar_type
0065     determinant_impl( M const & a )
0066         {
0067         BOOST_QVM_STATIC_ASSERT(mat_traits<M>::rows==mat_traits<M>::cols);
0068         return determinant_impl_(a,det_size<mat_traits<M>::rows>());
0069         }
0070     }
0071 
0072 } }
0073 
0074 #endif