00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031 namespace TooN {
00032
00033 namespace Internal
00034 {
00035
00036
00037
00038
00039 template<int, int, class, int, int, class> struct GenericMBase;
00040
00041
00042
00043
00044
00045 template<int RowStride, int ColStride> struct Slice
00046 {
00047
00048 template<int Rows, int Cols, class Precision> struct MLayout: public GenericMBase<Rows, Cols, Precision, RowStride, ColStride, MatrixSlice<Rows, Cols, Precision> >
00049 {
00050 MLayout(Precision* p, int rows, int cols, int rowstride, int colstride)
00051 :GenericMBase<Rows,Cols,Precision,RowStride,ColStride,MatrixSlice<Rows, Cols, Precision> >(p, rows, cols, rowstride, colstride)
00052 {
00053 }
00054 };
00055 };
00056
00057
00058 template<int Rows, int Cols, bool D = (Rows == Dynamic || Cols == Dynamic)>
00059 struct DiagSize
00060 {
00061 static const int size = Dynamic;
00062 };
00063 template<int Rows, int Cols>
00064 struct DiagSize<Rows, Cols, 0>
00065 {
00066 static const int size = (Rows<Cols?Rows:Cols);
00067 };
00068
00069 template<int Rs, int Cs, bool D = (Rs == Dynamic || Cs == Dynamic)>
00070 struct DiagStride
00071 {
00072 static const int stride = Dynamic;
00073 };
00074 template<int Rs, int Cs>
00075 struct DiagStride<Rs, Cs, 0>
00076 {
00077 static const int stride = Rs + Cs;
00078 };
00079
00080
00081 template<int Rows, int Cols, class Precision, int RowStride, int ColStride, class Mem> struct GenericMBase
00082 : public Mem,
00083 RowStrideHolder<RowStride>,
00084 ColStrideHolder<ColStride>
00085 {
00086
00087 static const int SliceRowStride = RowStride == -2?-1: RowStride;
00088 static const int SliceColStride = ColStride == -2?-1: ColStride;
00089
00090 int rowstride() const {
00091 if(RowStride == -2) {
00092 return num_cols();
00093 } else {
00094 return RowStrideHolder<RowStride>::stride();
00095 }
00096 }
00097
00098 int colstride() const {
00099 if(ColStride == -2) {
00100 return num_rows();
00101 } else {
00102 return ColStrideHolder<ColStride>::stride();
00103 }
00104 }
00105
00106
00107 GenericMBase(){}
00108
00109 GenericMBase(Precision* p)
00110 :Mem(p)
00111 {}
00112
00113
00114 GenericMBase(Precision* p, int r, int c, int rowstride, int colstride)
00115 :Mem(p, r, c),
00116 RowStrideHolder<RowStride>(rowstride),
00117 ColStrideHolder<ColStride>(colstride)
00118 {}
00119
00120 GenericMBase(int r, int c)
00121 :Mem(r, c) {}
00122
00123 template<class Op>
00124 GenericMBase(const Operator<Op>& op)
00125 : Mem(op),
00126 RowStrideHolder<RowStride>(op),
00127 ColStrideHolder<ColStride>(op)
00128 {}
00129
00130 using Mem::my_data;
00131 using Mem::num_cols;
00132 using Mem::num_rows;
00133
00134 Precision& operator()(int r, int c){
00135 Internal::check_index(num_rows(), r);
00136 Internal::check_index(num_cols(), c);
00137 return my_data[r*rowstride() + c*colstride()];
00138 }
00139
00140 const Precision& operator()(int r, int c) const {
00141 Internal::check_index(num_rows(), r);
00142 Internal::check_index(num_cols(), c);
00143 return my_data[r*rowstride() + c*colstride()];
00144 }
00145
00146 Precision& operator[](const std::pair<int, int>& index) {
00147 Internal::check_index(num_rows(), index.first);
00148 Internal::check_index(num_cols(), index.second);
00149 return (*this)(index.first, index.second);
00150 }
00151
00152 const Precision& operator[](const std::pair<int, int>& index) const {
00153 Internal::check_index(num_rows(), index.first);
00154 Internal::check_index(num_cols(), index.second);
00155 return (*this)(index.first, index.second);
00156 }
00157
00158
00159 typedef Vector<Cols, Precision, SliceVBase<SliceColStride> > Vec;
00160
00161 Vec operator[](int r) {
00162 Internal::check_index(num_rows(), r);
00163 return Vec(my_data + rowstride()* r, num_cols(), colstride(), Slicing());
00164 }
00165
00166 const Vec operator[](int r) const {
00167 Internal::check_index(num_rows(), r);
00168 return Vec(const_cast<Precision*>(my_data + rowstride()* r), num_cols(), colstride(), Slicing());
00169 }
00170
00171
00172
00173 template<int Rstart, int Cstart, int Rlength, int Clength>
00174 Matrix<Rlength, Clength, Precision, Slice<SliceRowStride,SliceColStride> > slice(int rs, int cs, int rl, int cl){
00175 Internal::CheckSlice<Rows, Rstart, Rlength>::check(num_rows(), rs, rl);
00176 Internal::CheckSlice<Cols, Cstart, Clength>::check(num_cols(), cs, cl);
00177
00178
00179
00180 return Matrix<Rlength, Clength, Precision, Slice<SliceRowStride,SliceColStride> >(
00181 my_data+rowstride()*(Rstart==Dynamic?rs:Rstart) + colstride()*(Cstart==Dynamic?cs:Cstart),
00182 Rlength==Dynamic?rl:Rlength,
00183 Clength==Dynamic?cl:Clength,
00184 rowstride(), colstride(), Slicing());
00185 }
00186
00187 template<int Rstart, int Cstart, int Rlength, int Clength>
00188 const Matrix<Rlength, Clength, Precision, Slice<SliceRowStride,SliceColStride> > slice(int rs, int cs, int rl, int cl) const{
00189 Internal::CheckSlice<Rows, Rstart, Rlength>::check(num_rows(), rs, rl);
00190 Internal::CheckSlice<Cols, Cstart, Clength>::check(num_cols(), cs, cl);
00191
00192
00193
00194 return Matrix<Rlength, Clength, Precision, Slice<SliceRowStride,SliceColStride> >(
00195 const_cast<Precision*>(my_data)+rowstride()*(Rstart==Dynamic?rs:Rstart) + colstride()*(Cstart==Dynamic?cs:Cstart),
00196 Rlength==Dynamic?rl:Rlength,
00197 Clength==Dynamic?cl:Clength,
00198 rowstride(), colstride(), Slicing());
00199 }
00200
00201
00202 template<int Rstart, int Cstart, int Rlength, int Clength>
00203 Matrix<Rlength, Clength, Precision, Slice<SliceRowStride,SliceColStride> > slice()
00204 {
00205
00206 Internal::CheckSlice<Rows, Rstart, Rlength>::check();
00207 Internal::CheckSlice<Cols, Cstart, Clength>::check();
00208 return slice<Rstart, Cstart, Rlength, Clength>(Rstart, Cstart, Rlength, Clength);
00209 }
00210
00211 template<int Rstart, int Cstart, int Rlength, int Clength>
00212 const Matrix<Rlength, Clength, Precision, Slice<SliceRowStride,SliceColStride> > slice() const
00213 {
00214 Internal::CheckSlice<Rows, Rstart, Rlength>::check();
00215 Internal::CheckSlice<Cols, Cstart, Clength>::check();
00216 return slice<Rstart, Cstart, Rlength, Clength>(Rstart, Cstart, Rlength, Clength);
00217 }
00218
00219 Matrix<-1, -1, Precision, Slice<SliceRowStride,SliceColStride> > slice(int rs, int cs, int rl, int cl){
00220 return slice<Dynamic, Dynamic, Dynamic, Dynamic>(rs, cs, rl, cl);
00221 }
00222
00223 const Matrix<-1, -1, Precision, Slice<SliceRowStride,SliceColStride> > slice(int rs, int cs, int rl, int cl) const {
00224 return slice<Dynamic, Dynamic, Dynamic, Dynamic>(rs, cs, rl, cl);
00225 }
00226
00227
00228 Matrix<Cols, Rows, Precision, Slice<SliceColStride,SliceRowStride> > T(){
00229 return Matrix<Cols, Rows, Precision, Slice<SliceColStride,SliceRowStride> >(my_data, num_cols(), num_rows(), colstride(), rowstride(), Slicing());
00230 }
00231
00232 const Matrix<Cols, Rows, Precision, Slice<SliceColStride,SliceRowStride> > T() const{
00233 return Matrix<Cols, Rows, Precision, Slice<SliceColStride,SliceRowStride> >(const_cast<Precision*>(my_data), num_cols(), num_rows(), colstride(), rowstride(), Slicing());
00234 }
00235
00236 static const int DiagSize = Internal::DiagSize<Rows, Cols>::size;
00237 static const int DiagStride = Internal::DiagStride<SliceRowStride, SliceColStride>::stride;
00238
00239 Vector<DiagSize, Precision, SliceVBase<DiagStride> > diagonal_slice()
00240 {
00241 return Vector<DiagSize, Precision, SliceVBase<DiagStride> >(my_data, std::min(num_cols(), num_rows()), rowstride() + colstride(), Slicing());
00242 }
00243 };
00244
00245 }
00246
00247
00248
00249
00250
00251
00252 struct RowMajor
00253 {
00254 template<int Rows, int Cols, class Precision> struct MLayout: public Internal::GenericMBase<Rows, Cols, Precision, (Cols==-1?-2:Cols), 1, Internal::MatrixAlloc<Rows, Cols, Precision> >
00255 {
00256
00257
00258 MLayout(){}
00259
00260 MLayout(int rows, int cols)
00261 :Internal::GenericMBase<Rows, Cols, Precision, (Cols == -1 ? -2 : Cols), 1, Internal::MatrixAlloc<Rows, Cols, Precision> >(rows, cols)
00262 {}
00263
00264 template<class Op>
00265 MLayout(const Operator<Op>& op)
00266 :Internal::GenericMBase<Rows, Cols, Precision, (Cols == -1 ? -2 : Cols), 1, Internal::MatrixAlloc<Rows, Cols, Precision> >(op)
00267 {}
00268
00269 };
00270 };
00271
00272 struct ColMajor
00273 {
00274 template<int Rows, int Cols, class Precision> struct MLayout: public Internal::GenericMBase<Rows, Cols, Precision, 1, (Rows==-1?-2:Rows), Internal::MatrixAlloc<Rows, Cols, Precision> >
00275 {
00276
00277
00278 MLayout(){}
00279
00280 MLayout(int rows, int cols)
00281 :Internal::GenericMBase<Rows, Cols, Precision, 1, (Rows == -1 ? -2 : Rows), Internal::MatrixAlloc<Rows, Cols, Precision> >(rows, cols)
00282 {}
00283
00284 template<class Op>
00285 MLayout(const Operator<Op>& op)
00286 :Internal::GenericMBase<Rows, Cols, Precision, 1, (Rows == -1 ? -2 : Rows), Internal::MatrixAlloc<Rows, Cols, Precision> >(op)
00287 {}
00288
00289 };
00290 };
00291
00292 }
00293