📄 mmat_10.cc
字号:
// file: $isip/class/math/matrix/MMatrix/mmat_10.cc// version: $Id: mmat_10.cc,v 1.30 2002/02/27 20:54:28 alphonso Exp $//// isip include files//#include "MMatrixMethods.h"#include "MMatrix.h"//#include <VectorLong.h>// method: getValue//// arguments:// const MMatrix<TScalar, TIntegral>& this: (output) class operand// TScalar& value: (output) value at the given position// long row_index: (input) row_index// long col_index: (input) col_index//// return: a TIntegral value at the given position of the matrix//// this method gets the value at the specified position in the matrix//template<class TScalar, class TIntegral>boolean MMatrixMethods::getValue(const MMatrix<TScalar, TIntegral>& this_a, TScalar& value_a, long row_index_a, long col_index_a) { // type: DIAGONAL // the general idea is that we output the value of diagonal element for // diagonal position, otherwise, we output zero. // if (this_a.type_d == Integral::DIAGONAL) { // return zero for non-diagonal elements // if (row_index_a != col_index_a) { value_a = TScalar((TIntegral)0); } // return diagonal element // else { value_a = TScalar(this_a.m_d(row_index_a)); } } // type: FULL // the general idea is that we simply output the value of corresponding // position. // else if (this_a.type_d == Integral::FULL) { // return the value at specified row and column index // value_a = TScalar(this_a.m_d(this_a.index(row_index_a, col_index_a))); } // type: SYMMETRIC // the general idea is that we simply output the value of lower triangular // element, but for upper triangular element, we output the corresponding // element in lower triangular part, that is a(i, j) = a(j, i). // else if (this_a.type_d == Integral::SYMMETRIC) { // return the element in lower triangle // if (row_index_a >= col_index_a) { value_a = TScalar(this_a.m_d(this_a.index(row_index_a, col_index_a))); } // for upper triangular elements also output corresponding element // in lower triangle // else { value_a = TScalar(this_a.m_d(this_a.index(col_index_a, row_index_a))); } } // type: LOWER_TRIANGULAR // the general idea is that we output the value of lower triangular element, // otherwise, output zero for upper triangular element. // else if (this_a.type_d == Integral::LOWER_TRIANGULAR) { // return the element in lower triangle // if (row_index_a >= col_index_a) { value_a = TScalar(this_a.m_d(this_a.index(row_index_a, col_index_a))); } // return zero for upper triangular values // else { value_a = TScalar((TIntegral)0); } } // type: UPPER_TRIANGULAR // the general idea is that we output the value of upper triangular element // and output zero for lower triangular element // else if (this_a.type_d == Integral::UPPER_TRIANGULAR) { // return the element in upper triangle // if (row_index_a <= col_index_a) { value_a = TScalar(this_a.m_d(this_a.index(row_index_a, col_index_a))); } // return zero for lower triangular values // else { value_a = TScalar((TIntegral)0); } } // type: SPARSE // the general idea is that we loop through all the elements on the storage // vector. // else if (this_a.type_d == Integral::SPARSE) { // if the storage vector does not have the element corresponding // to that row and column index then it must be zero. // value_a = TScalar((TIntegral)0); // return the element on the storage vector if it is a non-zero element // for (long index = 0; index < this_a.m_d.length(); index++) { if ((row_index_a == this_a.row_index_d(index)) && (col_index_a == this_a.col_index_d(index))) { value_a = (TScalar)this_a.m_d(index); } } } // exit gracefully // return true;}// explicit instantiations//template booleanMMatrixMethods::getValue<ISIP_TEMPLATE_TARGET>(const MMatrix<ISIP_TEMPLATE_TARGET>&, ISIP_TEMPLATE_T0&, long, long);// method: getValue//// arguments:// const MMatrix<TScalar, TIntegral>& this: (output) class operand// long row_index: (input) row_index// long col_index: (input) col_index//// return: a TIntegral value at the given position of the matrix//// this method gets the value at the specified position//template<class TScalar, class TIntegral>TIntegral MMatrixMethods::getValue(const MMatrix<TScalar, TIntegral>& this_a, long row_index_a, long col_index_a) { // type: DIAGONAL // the general idea is that we return the value of diagonal element for // diagonal position, otherwise, we return zero. // if (this_a.type_d == Integral::DIAGONAL) { // return zero for non-diagonal elements // if (row_index_a != col_index_a) { return (TIntegral)0; } // return diagonal element // else { return (TIntegral)this_a.m_d(row_index_a); } } // type: FULL // the general idea is that we simply return the value of corresponding // position. // else if (this_a.type_d == Integral::FULL) { // return the value at specified row and column index // return (TIntegral)(this_a.m_d(this_a.index(row_index_a, col_index_a))); } // type: SYMMETRIC // the general idea is that we simply return the value of lower triangular // element, but for upper triangular element, we return the corresponding // element in lower triangular part, that is a(i, j) = a(j, i). // else if (this_a.type_d == Integral::SYMMETRIC) { // return the element in lower triangle // if (row_index_a >= col_index_a) { return (TIntegral)(this_a.m_d(this_a.index(row_index_a, col_index_a))); } // for upper triangular elements also return corresponding element // in lower triangle // else { return (TIntegral)(this_a.m_d(this_a.index(col_index_a, row_index_a))); } } // type: LOWER_TRIANGULAR // the general idea is that we return the value of lower triangular element, // otherwise, output zero for upper triangular element. // else if (this_a.type_d == Integral::LOWER_TRIANGULAR) { // return the element in lower triangle // if (row_index_a >= col_index_a) { return (TIntegral)(this_a.m_d(this_a.index(row_index_a, col_index_a))); } // return zero for upper triangular values // else { return (TIntegral)0; } } // type: UPPER_TRIANGULAR // the general idea is that we return the value of upper triangular element // and return zero for lower triangular element // else if (this_a.type_d == Integral::UPPER_TRIANGULAR) { // return the element in upper triangle // if (row_index_a <= col_index_a) { return (TIntegral)(this_a.m_d(this_a.index(row_index_a, col_index_a))); } // return zero for lower triangular values // else { return (TIntegral)0; } } // type: SPARSE // the general idea is that we loop through all the elements on the storage // vector. // else if (this_a.type_d == Integral::SPARSE) { // return the element on the storage vector if it is a non-zero element // for (long index = 0; index < this_a.m_d.length(); index++) { if ((row_index_a == (long)this_a.row_index_d(index)) && (col_index_a == (long)this_a.col_index_d(index))) { return (TIntegral)this_a.m_d(index); } } // if the storage vector does not have the element corresponding // to that row and column index then it must be zero. // return (TIntegral)0; } else { this_a.debug(L"this_a"); return Error::handle(name(), L"getValue", MMatrix<TScalar, TIntegral>::ERR_UNKTYP, __FILE__, __LINE__); }}// explicit instantiations//template ISIP_TEMPLATE_T1MMatrixMethods::getValue<ISIP_TEMPLATE_TARGET>(const MMatrix<ISIP_TEMPLATE_TARGET>&, long, long);// method: getRow//// arguments:// const MMatrix<TScalar, TIntegral>& this: (output) class operand// MVector<TScalar, TIntegral>& vector: (output) a row vector at the given row// long row_index: (input) row_index//// return: a boolean value indicating status//// this method gets the row vector at the specified row//template<class TScalar, class TIntegral>boolean MMatrixMethods::getRow(const MMatrix<TScalar, TIntegral>& this_a, MVector<TScalar, TIntegral>& vector_a, long row_index_a) { // check the argument // if ((row_index_a < 0) || (row_index_a > this_a.nrows_d)) { this_a.debug(L"this_a"); vector_a.debug(L"vector_a"); return Error::handle(name(), L"getRow", Error::ARG, __FILE__, __LINE__); } // get the number of columns // long ncols = this_a.getNumColumns(); // create space for the output vector // vector_a.setLength(ncols, false); // type: FULL // the general idea is that we assign the row vector to the output vector // which can be easily done by calling move method for the storage vector. // if (this_a.type_d == Integral::FULL) { vector_a.move(this_a.m_d, ncols, row_index_a * ncols, 0); } // type: DIAGONAL // the general idea is that we copy the diagonal element for the row at // appropriate index in the vector and put zeros at other places. // else if (this_a.type_d == Integral::DIAGONAL) { // zero the non-diagonal components // vector_a.clear(Integral::RETAIN); // copy the diagonal element at the appropriate row // vector_a(row_index_a) = this_a.m_d(row_index_a); } // type: SYMMETRIC // the general idea is that we copy the elements in the lower triangular // part of the row in sequence, and fetch the upper triangular part // using the index function. // else if (this_a.type_d == Integral::SYMMETRIC) { // copy the lower triangular part // long index = this_a.index(row_index_a, 0); for (long col = 0; col < row_index_a; col++) { vector_a(col) = this_a.m_d(index++); } // copy the diagonal part // vector_a(row_index_a) = this_a.m_d(index); // copy the upper triangular part // for (long col = row_index_a + 1; col < ncols; col++) { vector_a(col) = this_a.getValue(row_index_a, col); } } // type: LOWER_TRIANGULAR // the general idea is that we copy the elements in lower triangular part // of the row at appropriate indices in the vector and put zeros at // upper triangular part of the row. // else if (this_a.type_d == Integral::LOWER_TRIANGULAR) { // loop over all columns // long index = this_a.index(row_index_a, 0); for (long col = 0; col < row_index_a; col++) { vector_a(col) = this_a.m_d(index++); vector_a(ncols - 1 - col) = (TIntegral)0; } vector_a(row_index_a) = this_a.m_d(index); } // type: UPPER_TRIANGULAR // the general idea is that we copy the elements in upper triangular part // of the row at appropriate indices in the vector and put zeros at // lower triangular part of the row. since upper triangular is stored // in a column-oriented format, we must do this through the indexing // function. // else if (this_a.type_d == Integral::UPPER_TRIANGULAR) { // compute the start column of upper triangular part of the row // long start_column = this_a.startColumn(row_index_a, this_a.type_d); // for the lower triangular part, place zeroes // for (long col = 0; col < start_column; col++) { vector_a(col) = (TIntegral)0; } // for the upper triangular part, copy the corresponding elements // for (long col = start_column; col < ncols; col++) { vector_a(col) = this_a.m_d(this_a.index(row_index_a, col)); } } // type: SPARSE // we only copy the non-zero elements in that row to the output vector, // but if there is no non-zero element, we will output an all-zero vector. // also, note that since elements in a sparse matrix are stored in // sequential order, we can avoid looping over all elements. // else if (this_a.type_d == Integral::SPARSE) { // set all elements to zeros // vector_a.clear(Integral::RETAIN); // find the start of the row // long num_elements = this_a.m_d.length(); long index = 0; while ((index < num_elements) && (this_a.row_index_d(index) != row_index_a)) { index++; } // copy element by element // while ((index < num_elements) && (this_a.row_index_d(index) == row_index_a)) { vector_a(this_a.col_index_d(index)) = this_a.m_d(index); index++; } } // exit gracefully // return true;}// explicit instantiations//template booleanMMatrixMethods::getRow<ISIP_TEMPLATE_TARGET>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -