00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014 #ifndef BOOST_NUMERIC_BINDINGS_LAPACK_ORMQR_HPP
00015 #define BOOST_NUMERIC_BINDINGS_LAPACK_ORMQR_HPP
00016
00017 #include <complex>
00018 #include <boost/numeric/bindings/traits/traits.hpp>
00019 #include <boost/numeric/bindings/lapack/lapack.h>
00020 #include <boost/numeric/bindings/lapack/workspace.hpp>
00021 #include <boost/numeric/bindings/traits/detail/array.hpp>
00022
00023
00024 #ifndef BOOST_NUMERIC_BINDINGS_NO_STRUCTURE_CHECK
00025 # include <boost/static_assert.hpp>
00026 # include <boost/type_traits.hpp>
00027 #endif
00028
00029
00030 namespace boost { namespace numeric { namespace bindings {
00031
00032 namespace lapack {
00033
00035
00036
00037
00038
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066 namespace detail {
00067
00068 inline
00069 void ormqr (char const side, char const trans, int const m, int const n,
00070 int const k, const float* a, int const lda,
00071 const float* tau, float* c,
00072 int const ldc, float* work, int const lwork,
00073 int& info)
00074 {
00075 LAPACK_SORMQR (&side, &trans, &m, &n, &k,
00076 a, &lda,
00077 tau,
00078 c, &ldc,
00079 work, &lwork,
00080 &info);
00081 }
00082
00083 inline
00084 void ormqr (char const side, char const trans, int const m, int const n,
00085 int const k, const double* a, int const lda,
00086 const double* tau, double* c,
00087 int const ldc, double* work, int const lwork,
00088 int& info)
00089 {
00090 LAPACK_DORMQR (&side, &trans, &m, &n, &k,
00091 a, &lda,
00092 tau,
00093 c, &ldc,
00094 work, &lwork,
00095 &info);
00096 }
00097
00098 inline
00099 void ormqr (char const side, char const trans, int const m, int const n,
00100 int const k, const traits::complex_f* a, int const lda,
00101 const traits::complex_f* tau, traits::complex_f* c,
00102 int const ldc, traits::complex_f* work, int const lwork,
00103 int& info)
00104 {
00105 LAPACK_CUNMQR (&side, &trans, &m, &n, &k,
00106 traits::complex_ptr(a), &lda,
00107 traits::complex_ptr(tau),
00108 traits::complex_ptr(c), &ldc,
00109 traits::complex_ptr(work), &lwork,
00110 &info);
00111 }
00112
00113 inline
00114 void ormqr (char const side, char const trans, int const m, int const n,
00115 int const k, const traits::complex_d* a, int const lda,
00116 const traits::complex_d* tau, traits::complex_d* c,
00117 int const ldc, traits::complex_d* work, int const lwork,
00118 int& info)
00119 {
00120 LAPACK_ZUNMQR (&side, &trans, &m, &n, &k,
00121 traits::complex_ptr(a), &lda,
00122 traits::complex_ptr(tau),
00123 traits::complex_ptr(c), &ldc,
00124 traits::complex_ptr(work), &lwork,
00125 &info);
00126 }
00127
00128
00129 template <typename A, typename Tau, typename C, typename Work>
00130 inline
00131 int ormqr (char side, char trans, const A& a, const Tau& tau, C& c,
00132 Work& work) {
00133
00134 #ifndef BOOST_NUMERIC_BINDINGS_NO_STRUCTURE_CHECK
00135 BOOST_STATIC_ASSERT((boost::is_same<
00136 typename traits::matrix_traits<A>::matrix_structure,
00137 traits::general_t
00138 >::value));
00139 BOOST_STATIC_ASSERT((boost::is_same<
00140 typename traits::matrix_traits<C>::matrix_structure,
00141 traits::general_t
00142 >::value));
00143 #endif
00144
00145 int const m = traits::matrix_size1 (c);
00146 int const n = traits::matrix_size2 (c);
00147 int const k = traits::vector_size (tau);
00148 int const lwork = traits::vector_size (work);
00149
00150 assert ( side=='L' || side=='R' );
00151 assert ( trans=='N' || trans=='C' || trans=='T' );
00152 assert ( (side=='L' ? m >= k : n >= k ) );
00153
00154 assert ( (side=='L' ?
00155 m == traits::matrix_size1 (a) :
00156 n == traits::matrix_size1 (a) ) );
00157 assert (traits::matrix_size2 (a)==k);
00158
00159 assert ( (side=='L' ?
00160 lwork >= n : lwork >= m ) );
00161
00162 int info;
00163 ormqr (side, trans, m, n, k,
00164 traits::matrix_storage (a),
00165 traits::leading_dimension (a),
00166 traits::vector_storage (tau),
00167 traits::matrix_storage (c),
00168 traits::leading_dimension (c),
00169 traits::vector_storage (work),
00170 lwork,
00171 info);
00172 return info;
00173 }
00174 }
00175
00176
00177
00178 template <typename A, typename Tau, typename C>
00179 inline
00180 int ormqr (char side, char trans, const A& a, const Tau& tau, C& c, optimal_workspace ) {
00181 typedef typename A::value_type value_type ;
00182
00183 int const n_w = (side=='L' ? traits::matrix_size2 (c)
00184 : traits::matrix_size1 (c) );
00185
00186 traits::detail::array<value_type> work( std::max(1,n_w*32) );
00187
00188 return detail::ormqr( side, trans, a, tau, c, work );
00189 }
00190
00191
00192
00193 template <typename A, typename Tau, typename C>
00194 inline
00195 int ormqr (char side, char trans, const A& a, const Tau& tau, C& c, minimal_workspace ) {
00196 typedef typename A::value_type value_type ;
00197
00198 int const n_w = (side=='L' ? traits::matrix_size2 (c)
00199 : traits::matrix_size1 (c) );
00200
00201 traits::detail::array<value_type> work( std::max(1,n_w) );
00202
00203 return detail::ormqr( side, trans, a, tau, c, work );
00204 }
00205
00206
00207
00208
00209
00210 template <typename A, typename Tau, typename C, typename Work>
00211 inline
00212 int ormqr (char side, char trans, const A& a, const Tau& tau, C& c, detail::workspace1<Work> workspace ) {
00213 typedef typename A::value_type value_type ;
00214
00215 return detail::ormqr( side, trans, a, tau, c, workspace.w_ );
00216 }
00217
00218 }
00219
00220 }}}
00221
00222 #endif