www.pudn.com > AdaBoost_weaklearner_1.rar > matrix.cpp
#include "matrix.h" #include#include #include #include #define AS_ZERO 0.0001 Matrix::Matrix(int r, int c) { rows = r; cols = c; alloc(); // initialize all elements to zero toZero(); } // copy constructor // Matrix::Matrix(const Matrix& m) { rows = m.rows; cols = m.cols; alloc(); for (int i = 0; i < rows; i++) for (int j = 0; j < cols; j++) element[i][j] = m.element[i][j]; } // destructor // Matrix::~Matrix(void) { release(); // cout << "Matrix is: " << this << endl; // cout << "destructor called" << endl; } // allocate memory on heap // void Matrix::alloc(void) { element = new T* [rows]; for (int i = 0; i < rows; i++) element[i] = new T [cols]; } // free heap memory // void Matrix::release(void) { for (int i = 0; i < rows; i++) { delete [] element[i]; element[i]=0; } delete [] element; element=0; } void Matrix::toZero(void) { for (int i = 0; i < rows; i++) for (int j = 0; j < cols; j++) element[i][j] = 0; } void Matrix::zeros(int i, int j) { for (int ii = 0; ii < rows; ii++) for (int jj = 0; jj < cols; jj++) element[ii][jj] = 0; } void Matrix::toOne(void) { for (int i = 0; i < rows; i++) for (int j = 0; j < cols; j++) element[i][j] = 1; } void Matrix::ones(int i, int j, T val, int scaler) { for (int ii = 0; ii < i; ii++) for (int jj = 0; jj < j; jj++) element[ii][jj] = val / scaler; } void Matrix::print(void) const { cout << *this; // w/ << overloaded // // for (int i = 0; i < rows; i++) // { // for (int j = 0; j < cols; j++) // cout << element[i][j] << '\t'; // cout << endl; // } } void Matrix::set (int i, int j, T val) { //if(i>rows-1 || j>cols-1) // reptError("Matrix subscript out of bound, set(i,j) failed!"); i=i-1; element[i][j]=val; } void Matrix::setValue (int tt, T val) { tt=tt-1; element[tt][0] = val; } // Get Value from matrix int Matrix::getValue(int j,double *val, Matrix& m) const { j=j-1; (*val) = m.element[0][j]; return (0); } // Get Value from matrix int Matrix::getValueSpecific(int i, int j,double *val, Matrix& m) const { (*val) = m.element[i][j]; return (0); } // overload subscript operator to access element[i][j] // T Matrix::operator () (int i, int j) const { if(i>rows-1 || j>cols-1) reptError("Matrix subscript out of bound, () failed!"); return element[i][j]; } // Take only part from the matrix void Matrix::partOfMatrix(int r, int c, Matrix& m) const { for (int i = 0; i < row(); i++) for (int j = 0; j < col()-1; j++) element[i][j] = m.element[i][j]; } void Matrix::partOfMatrixNext(int r, int c, int step, Matrix& m) const { int k=0; int i = step - r; for (i; i < step; i++){ for (int j = 0; j < col()-1; j++){ element[k][j] = m.element[i][j]; } k++; } } // Take only part from the matrix from end void Matrix::partOfMatrixFromEnd(int r_train,int step,int c,Matrix& m) const { int k=0; int i=r_train - step; for (i; i < r_train; i++){ for (int j = 0; j < col()-1; j++){ element[k][j] = m.element[i][j]; } k++; } } // This function return the matrix size void Matrix::matrixSize(int *i, int *j, Matrix& m) const { (*i) = m.rows; (*j) = m.cols; } // scalar minus matrix void Matrix::ScalarMinusMatrix(double k, Matrix& m) const { int r=rows; int c=m.col(); for (int i=0; i < r; i++) for (int j=0; j < c; j++) element[i][j] = k - m.element[i][j]; } //&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& // Take a specific part (coloum) from the matrix void Matrix::specificPartOfMatrix(Matrix& m,int r, int c) { //Matrix temp(r,r); int j = c; int k=0; for (int i = 0; i < row(); i++) element[i][k] = m.element[i][j]; } //&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&& // From matrix (Vector) to Array void Matrix::matrixToArray(double array[10], Matrix& m) const { int r=rows; int c=cols; for (int i = 0; i < r; i++) for (int j=0; j < c; j++) array[i]=m.element[i][j]; // return array[10]; } // From matrix (Vector) to Array void Matrix::matrixToArrayold(double array[10], Matrix& m) const { int r=rows; int c=m.col(); int i = 0; for (int j=0; j < c; j++) array[j]=m.element[i][j]; // return array[10]; } void Matrix::matrixExp(Matrix& m) const { double dVal; int r=rows; int c=m.col(); for (int i = 0; i < r; i++){ for (int j = 0; j < c; j++){ dVal = m.element[i][j]; //dValue = fabs(dVal); element[i][j] = exp(dVal); } } } void Matrix::matrixLog(Matrix& m) const { double dVal; int r=rows; int c=m.col(); for (int i = 0; i < r; i++){ for (int j = 0; j < c; j++){ dVal = m.element[i][j]; //dValue = fabs(dVal); element[i][j] = log(dVal); } } } void Matrix::matrixAbs(Matrix& m) const { double dVal; //double dValue; for (int i = 0; i < row(); i++){ for (int j = 0; j < col()-1; j++){ dVal = m.element[i][j]; //dValue = fabs(dVal); element[i][j] = fabs(dVal); } } } int Matrix::matrixSumCol(double *sum, Matrix& m) const { int r=rows; int c=cols; for (int i = 0; i < r; i++) for (int j = 0; j < c-1; j++) (*sum) += m.element[i][j]; return (0); } int Matrix::matrixSumRow(double *sum, Matrix& m) const { int r=rows; int c=cols; for (int j = 0; j < c; j++){ for (int i = 0; i < r; i++){ (*sum) += m.element[i][j]; } } return (0); } // Compare between the current value and the perivues value int Matrix::matrixCompareAndSet(int *i_index, int c_train, Matrix& m) const { int r=rows; int c=m.col(); Matrix temp(r, c); for (int i = 1; i < r; i++){ for (int j = 0; j < c; j++){ temp.element[i][j] = (m.element[i][j] - m.element[i-1][j]); if ((temp.element[i][j] == 0) && (m.element[i][j] > 0)) { *i_index=*i_index+1; if (*i_index > (c_train -2)) { *i_index=1; } } else { *i_index=*i_index; } } } return *i_index; } // Compare between the current value and the perivues value int Matrix::matrixCompareAndSetfor_t(int k, int *t_index, int c_train, Matrix& m) const { //int r=rows; int c=m.col(); Matrix temp(k, c); for (int i = 1; i < k; i++){ for (int j = 0; j < c; j++){ temp.element[i][j] = (m.element[i][j] - m.element[i-1][j]); if ((temp.element[i][j] == 0) || (temp.element[i][j] == 1) && (m.element[i][j] > 0)) { *t_index=*t_index-5; if (*t_index > 130) { *t_index=73; } if (*t_index < 70) { *t_index=127; } } else { *t_index=*t_index; } } } return *t_index; } // Find the max value of the matrix int Matrix::matrixMax(double *val, int *index, Matrix& m) const { int r=rows; int c=m.col(); Matrix temp(r, c); int j,i; for (i = 0; i < r; i++){ for (j = 0; j < c-1; j++){ if (m.element[i][j] > m.element[i][j+1]) { temp.element[i][j] = m.element[i][j]; m.element[i][j]=m.element[i][j+1]; m.element[i][j+1]=temp.element[i][j]; if (m.element[i][j+1] > (*val)) { (*val) = m.element[i][j+1]; (*index) = j; } //temp.element[i][j] = m.element[i][j]; //(*val) = m.element[i][j]; //(*index) = j; } // else // { // temp.element[i][j] = m.element[i][j+1]; // (*val) = m.element[i][j]; // (*index) = j; // } } } return (0); } Matrix& Matrix::operator= (const Matrix& m) { if(rows != m.row() || cols != m.col()) reptError("Matrix dimensions differ, assignment failed!"); for (int i = 0; i < m.row(); i++) for (int j = 0; j < m.col(); j++) element[i][j] = m.element[i][j]; return *this; } istream& operator>> (istream& is, Matrix& m) { for (int i=0; i < m.row(); i++) for (int j=0; j < m.col(); j++) is >> m.element[i][j]; return is; } ostream& operator<< (ostream& os, const Matrix& m) { for (int i=0; i 1) c = c-1; else c = c; Matrix temp(r, c); for (int i=0; i < r; i++) { for (int j=0; j < c; j++) { temp.element[i][j] = element[i][j] - m.element[i][j]; } } return temp; // if(rows != m.row() || cols != m.col()) // reptError("Matrix sizes mismatch, subtraction failed!"); /* Matrix temp(rows, cols); temp = *this; temp -= m; return temp; */ } // compare the correct label matrix and scaler Matrix Matrix::operator> (const T& c) const { Matrix temp(rows, cols); temp = *this; temp >= c; return temp; } // combined scalar multiplication and assignment operator // Matrix& Matrix::operator>= (const T& c) { for (int j = 0; j < cols; j++){ for (int i = 0; i < rows; i++){ if (element[i][j] > c) element[i][j]=1; else element[i][j]=0; } } return *this; } // scale a matrix by a constant c // Matrix Matrix::operator* (const T& c) const { Matrix temp(rows, cols); temp = *this; temp *= c; return temp; } // two matrix multiplication // Matrix Matrix::operator* (const Matrix& m) const { // if(cols != m.row()) // reptError("Matrix dimensions error, multiplication failed!"); int r=rows; int c=m.col(); Matrix temp(r, c); for (int i=0; i < r; i++) { for (int j=0; j < c; j++) { for (int k=0; k < cols; k++) { temp.element[i][j] += element[i][k] * m.element[k][j]; if(fabs(temp.element[i][j])<=AS_ZERO) temp.element[i][j]=0; // round small # to zero } } } return temp; } void Matrix::scalarDivisonScalar(double scalar_1, double scalar_2, const Matrix& m) const { int r=rows;; int c=m.col(); for (int i=0; i < r; i++) for (int j=0; j < c; j++) element[i][j] = scalar_1 / scalar_2; } void Matrix::matrixdDivisonScalar(double scalar, const Matrix& m) const { int r=rows; int c=m.col(); // Matrix temp(r, c); for (int i=0; i < r; i++){ for (int j=0; j < c; j++){ element[i][j] = m.element[i][j] / scalar; //if(fabs(temp.element[i][j])<=AS_ZERO) // temp.element[i][j]=0; // round small # to zero } } // return temp; } // divison matrix by scaler Matrix Matrix::operator / (const Matrix& m) const { // if(cols != m.row()) // reptError("Matrix dimensions error, multiplication failed!"); int r=rows; int c=m.col(); Matrix temp(r, c); for (int i=0; i < r; i++) { for (int j=0; j < c; j++) { temp.element[i][j] = element[i][j] / m.element[i][j]; if(fabs(temp.element[i][j])<=AS_ZERO) temp.element[i][j]=0; // round small # to zero } } return temp; } // set a matrix to an identity matrix // void Matrix::toUnit(void) { if (!isSquare()) reptError("No identity matrix for a non-square matrix!"); for (int i = 0; i < rows; i++) for (int j = 0; j < cols; j++) element[i][j]=(i==j) ? (T) 1 : (T) 0; } void Matrix::reptError (char* errorMsg) const { cerr << errorMsg << endl; exit(1); } // compute the transpose matrix // void Matrix::matrixTranspose (int r, int c, const Matrix& m) const { for (int i = 0; i < r; i++) for (int j = 0; j < c; j++) element[j][i] = m.element[i][j]; } // compute the transpose matrix // Matrix Matrix::transpose (void) const { int r=rows; int c=cols; Matrix temp(c, r); for (int i = 0; i < r; i++) for (int j = 0; j < c; j++) temp.element[j][i] = element[i][j]; return temp; } // copy the matrix void Matrix::copy (int tt, Matrix& m) const { int r=rows; int i = 0; int j = tt; double val; val = m.element[0][0]; element[i][tt] = val; } // copy matrix to matrix void Matrix::copyMatrixToMatrix (Matrix& m) { int r=rows; int c=cols; for (int i = 0; i < r; i++) for (int j = 0; j < c; j++) element[i][j] = m.element[i][j]; } void Matrix::copyToMatrix(int tt, Matrix& m) const { double val; tt=tt-1; //for (int i=0; i < tt; i++){ val = m.element[0][tt]; element[tt][0] = val; //} } // minor() returns the minior of an element (r, c) // void Matrix::minor(int r, int c, Matrix& m) const { // precondition: a square matrix & the calling matrix with // dimension >= 3 // int k, l; for(int i = 0; i < rows-1; i++) { k=(i>=r) ? (i+1):i; for(int j = 0; j < cols-1; j++) { l=(j>=c) ? (j+1):j; m.element[i][j]=element[k][l]; } } } // cofact() calculates the cofactor of an element at (r, c) // T Matrix::cofact(int r, int c) const { // precondition: a square matrix & the calling matrix with // dimension >= 3 // T cof; Matrix temp(rows-1, cols-1); minor(r, c, temp); // cout << endl; // temp.print(); cof=(T) pow(-1, r+c)*temp.det(); return cof; } // computes the adjoin matrix of a given matrix // void Matrix::adjoin(Matrix& m) const { int dim=rows; // rows=cols if (!isSquare()) reptError("No adjoin matrix for a non-square matrix!"); if(m.row() != rows || m.col() != cols) reptError("Non square adjoin matrix defined!"); for(int i = 0; i < dim; i++) for(int j = 0; j < dim; j++) m.element[i][j]=cofact(i, j); // cout << endl; // m.print(); m=m.transpose(); // cout << endl; // m.print(); } // calculates the determinant of a matrix by first changing it // to a upper triangular matrix // T Matrix::det(void) const { if (!isSquare()) reptError("No determinant for a non-square matrix!"); T determinant=1; Matrix temp(rows, cols); temp=*this; // cout << endl; // temp.print(); temp.toUpper(); // cout << endl; // temp.print(); for (int i = 0; i < rows; i++) determinant *= temp.element[i][i]; // m(n, n) could be 0 if(fabs(determinant)<=AS_ZERO) // if too small, set to zero determinant=0; return determinant; } // covert to upper triangular matrix // void Matrix::toUpper(void) { // precondition: a square matrix // int i, j, k, dim=rows; for (j = 0; j < dim-1; j++) { // check if the diagonal element is zero // if(fabs(element[j][j])<=AS_ZERO) { element[j][j]=0; for(i = j+1; i < dim; i++) { if(element[i][j] != 0) { swapRow(i, j, dim); break; } } if(i>=dim) // every element=0 // { cout << "Cann't convert to upper triangular matrix, "; cout << "Error in column No. j=" << j << endl; reptError("Every element in column j is zero!"); } } // convert to upper triangular matrix // for (i = j+1; i < dim; i++) { if(element[i][j]==0) continue; for(k = j+1; k < dim; k++) element[i][k]=element[i][k]-element[j][k]*element[i][j]/element[j][j]; element[i][j]=0; } } } // swap 2 lines, each has c columns // Matrix& Matrix::swapRow(int r1, int r2, int c) { T temp; for (int j=0; j =9 && ch<=13)) // skip whitespace // { is.get(); continue; } if (ch=='#') { is.ignore(1000,'\n'); // skip comment line // continue; } for(j=0; j > element[i][j]; i++; } is.close(); // if(i != rows) // reptError("File row# != rows!"); } void Matrix::writeFile (char* file_name) { ofstream fos; fos.open(file_name, ios::out, filebuf::sh_none); if(fos.fail()) { cout << "File name = " << file_name << endl; reptError("Open file to write failed!"); } fos << *this; // for(int i=0; i