Disposable<Matrix> inverse(const Matrix& m) { #if !defined(QL_NO_UBLAS_SUPPORT) QL_REQUIRE(m.rows() == m.columns(), "matrix is not square"); boost::numeric::ublas::matrix<Real> a(m.rows(), m.columns()); std::copy(m.begin(), m.end(), a.data().begin()); boost::numeric::ublas::permutation_matrix<Size> pert(m.rows()); // lu decomposition const Size singular = lu_factorize(a, pert); QL_REQUIRE(singular == 0, "singular matrix given"); boost::numeric::ublas::matrix<Real> inverse = boost::numeric::ublas::identity_matrix<Real>(m.rows()); // backsubstitution boost::numeric::ublas::lu_substitute(a, pert, inverse); Matrix retVal(m.rows(), m.columns()); std::copy(inverse.data().begin(), inverse.data().end(), retVal.begin()); return retVal; #else QL_FAIL("this version of gcc does not support " "the Boost uBLAS library"); #endif }
// floating reference date, fixed market data SwaptionVolatilityHullWhite::SwaptionVolatilityHullWhite(const Real reversion, const Handle<YieldTermStructure>& yts, const boost::shared_ptr<SwapIndex> indexBase, const Calendar& cal, BusinessDayConvention bdc, const std::vector<Period>& optionT, const std::vector<Period>& swapT, const Matrix& vols, const DayCounter& dc) : reversion_(reversion),yts_(yts),indexBase_(indexBase),SwaptionVolatilityDiscrete(optionT, swapT, 0, cal, bdc, dc), volHandles_(vols.rows()), hwsigmas_(vols.rows(), vols.columns()), volatilities_(vols.rows(), vols.columns()) { checkInputs(vols.rows(), vols.columns()); // fill dummy handles to allow generic handle-based // computations later on for (Size i=0; i<vols.rows(); ++i) { volHandles_[i].resize(vols.columns()); for (Size j=0; j<vols.columns(); ++j) volHandles_[i][j] = Handle<Quote>(boost::shared_ptr<Quote>(new SimpleQuote(vols[i][j]))); } interpolation_ = BilinearInterpolation(swapLengths_.begin(), swapLengths_.end(), optionTimes_.begin(), optionTimes_.end(), volatilities_); interpolationSigma_ = BilinearInterpolation(swapLengths_.begin(), swapLengths_.end(), optionTimes_.begin(), optionTimes_.end(), hwsigmas_); }
int Munkres::step5(void) { /* New Zero Manufactures 1. Let h be the smallest uncovered entry in the (modified) distance matrix. 2. Add h to all covered rows. 3. Subtract h from all uncovered columns 4. Return to Step 3, without altering stars, primes, or covers. */ double h = 0; for ( int row = 0 ; row < matrix.rows() ; row++ ) { if ( !row_mask[row] ) { for ( int col = 0 ; col < matrix.columns() ; col++ ) { if ( !col_mask[col] ) { if ( (h > matrix(row,col) && matrix(row,col) != 0) || h == 0 ) { h = matrix(row,col); } } } } } for ( int row = 0 ; row < matrix.rows() ; row++ ) for ( int col = 0 ; col < matrix.columns() ; col++ ) { if ( row_mask[row] ) matrix(row,col) += h; if ( !col_mask[col] ) matrix(row,col) -= h; } return 3; }
// fixed reference date, fixed market data SwaptionVolatilityMatrix::SwaptionVolatilityMatrix( const Date& refDate, const Calendar& cal, BusinessDayConvention bdc, const std::vector<Period>& optionT, const std::vector<Period>& swapT, const Matrix& vols, const DayCounter& dc) : SwaptionVolatilityDiscrete(optionT, swapT, refDate, cal, bdc, dc), volHandles_(vols.rows()), volatilities_(vols.rows(), vols.columns()) { checkInputs(vols.rows(), vols.columns()); // fill dummy handles to allow generic handle-based // computations later on for (Size i=0; i<vols.rows(); ++i) { volHandles_[i].resize(vols.columns()); for (Size j=0; j<vols.columns(); ++j) volHandles_[i][j] = Handle<Quote>(boost::shared_ptr<Quote>(new SimpleQuote(vols[i][j]))); } interpolation_ = BilinearInterpolation(swapLengths_.begin(), swapLengths_.end(), optionTimes_.begin(), optionTimes_.end(), volatilities_); }
int Munkres::step2(void) { int covercount = 0; for ( int row = 0 ; row < matrix.rows() ; row++ ) for ( int col = 0 ; col < matrix.columns() ; col++ ) if ( mask_matrix(row,col) == Z_STAR ) { col_mask[col] = true; covercount++; } int k = matrix.minsize(); if ( covercount >= k ) { #ifdef DEBUG std::cout << "Final cover count: " << covercount << std::endl; #endif return 0; } #ifdef DEBUG std::cout << "Munkres matrix has " << covercount << " of " << k << " Columns covered:" << std::endl; for ( int row = 0 ; row < matrix.rows() ; row++ ) { for ( int col = 0 ; col < matrix.columns() ; col++ ) { std::cout.width(8); std::cout << matrix(row,col) << ","; } std::cout << std::endl; } std::cout << std::endl; #endif return 3; }
RatePseudoRootJacobianAllElements::RatePseudoRootJacobianAllElements(const Matrix& pseudoRoot, Size aliveIndex, Size numeraire, const std::vector<Time>& taus, const std::vector<Spread>& displacements) : pseudoRoot_(pseudoRoot), aliveIndex_(aliveIndex), taus_(taus), displacements_(displacements), factors_(pseudoRoot.columns()), // bumpedRates_(taus.size()), e_(pseudoRoot.rows(), pseudoRoot.columns()), ratios_(taus_.size()) { Size numberRates= taus.size(); QL_REQUIRE(aliveIndex == numeraire, "we can do only do discretely compounding MM acount so aliveIndex must equal numeraire"); QL_REQUIRE(pseudoRoot_.rows()==numberRates, "pseudoRoot_.rows()<> taus.size()"); QL_REQUIRE(displacements_.size()==numberRates, "displacements_.size()<> taus.size()"); }
void minimize_along_direction(Matrix<double> &matrix, bool over_columns) { const unsigned int outer_size = over_columns ? matrix.columns() : matrix.rows(), inner_size = over_columns ? matrix.rows() : matrix.columns(); // Look for a minimum value to subtract from all values along // the "outer" direction. for ( unsigned int i = 0 ; i < outer_size ; i++ ) { double min = over_columns ? matrix(0, i) : matrix(i, 0); // As long as the current minimum is greater than zero, // keep looking for the minimum. // Start at one because we already have the 0th value in min. for ( unsigned int j = 1 ; j < inner_size && min > 0 ; j++ ) { min = std::min<double>( min, over_columns ? matrix(j, i) : matrix(i, j)); } if ( min > 0 ) { for ( unsigned int j = 0 ; j < inner_size ; j++ ) { if ( over_columns ) { matrix(j, i) -= min; } else { matrix(i, j) -= min; } } } } }
Real determinant(const Matrix& m) { #if !defined(QL_NO_UBLAS_SUPPORT) QL_REQUIRE(m.rows() == m.columns(), "matrix is not square"); boost::numeric::ublas::matrix<Real> a(m.rows(), m.columns()); std::copy(m.begin(), m.end(), a.data().begin()); // lu decomposition boost::numeric::ublas::permutation_matrix<Size> pert(m.rows()); /* const Size singular = */ lu_factorize(a, pert); Real retVal = 1.0; for (Size i=0; i < m.rows(); ++i) { if (pert[i] != i) retVal *= -a(i,i); else retVal *= a(i,i); } return retVal; #else QL_FAIL("this version of gcc does not support " "the Boost uBLAS library"); #endif }
Disposable<Matrix> getCovariance(DataIterator stdDevBegin, DataIterator stdDevEnd, const Matrix& corr, Real tolerance = 1.0e-12){ Size size = std::distance(stdDevBegin, stdDevEnd); QL_REQUIRE(corr.rows() == size, "dimension mismatch between volatilities (" << size << ") and correlation rows (" << corr.rows() << ")"); QL_REQUIRE(corr.columns() == size, "correlation matrix is not square: " << size << " rows and " << corr.columns() << " columns"); Matrix covariance(size,size); Size i, j; DataIterator iIt, jIt; for (i=0, iIt=stdDevBegin; i<size; ++i, ++iIt){ for (j=0, jIt=stdDevBegin; j<i; ++j, ++jIt){ QL_REQUIRE(std::fabs(corr[i][j]-corr[j][i]) <= tolerance, "correlation matrix not symmetric:" << "\nc[" << i << "," << j << "] = " << corr[i][j] << "\nc[" << j << "," << i << "] = " << corr[j][i]); covariance[i][i] = (*iIt) * (*iIt); covariance[i][j] = (*iIt) * (*jIt) * 0.5 * (corr[i][j] + corr[j][i]); covariance[j][i] = covariance[i][j]; } QL_REQUIRE(std::fabs(corr[i][i]-1.0) <= tolerance, "invalid correlation matrix, " << "diagonal element of the " << io::ordinal(i+1) << " row is " << corr[i][i] << " instead of 1.0"); covariance[i][i] = (*iIt) * (*iIt); } return covariance; }
void Matrix::equal_size(Matrix & B) { if (rows() != B.rows() || columns() != B.columns()) { fprintf(stderr, "Incompatible Matrix sizes: %d,%d * %d,%d", rows(), columns(), B.rows(), B.columns()); // int crash = 1/0; exit(1); } return; }
inline const Disposable<Array> operator*(const Matrix& m, const Array& v) { QL_REQUIRE(v.size() == m.columns(), "vectors and matrices with different sizes (" << v.size() << ", " << m.rows() << "x" << m.columns() << ") cannot be multiplied"); Array result(m.rows()); for (Size i=0; i<result.size(); i++) result[i] = std::inner_product(v.begin(),v.end(),m.row_begin(i),0.0); return result; }
bool almostEqual(const Matrix& a, const Matrix& b, double max_error) { if (a.rows() != b.rows() || a.columns() != b.columns()) return false; Matrix diff = a - b; for (int i = 0; i < diff.size(); ++i) if (std::fabs(diff(i)) > max_error) return false; return true; }
/** * Corre deflacion sobre la matriz, devuelve una nueva matriz, que retiene los autovectores de la matriz A, excepto por * el autovector de autovalor dominante. * * @param A matriz inicial para la deflacion * @param eigen par de autovalor y autovector * @return nueva matriz con las caracteristicas anunciadas */ void deflation(Matrix &A, const EigenPair &eigen) { if (A.columns() != A.rows()) { throw new std::runtime_error("La matriz no es cuadrada en el método de deflación"); } Timer timer("Deflation Timer"); for (int i = 0; i < A.rows(); ++i) { for (int j = 0; j < A.columns(); ++j) { A(i, j) -= eigen.first * eigen.second[i] * eigen.second[j]; } } }
Cell exit(Matrix & a) { for (unsigned int i = 0; i < a.columns(); i++) { if (a[i][a.rows()-1] == 1) { return Cell(i,a.rows()-1); } } for (unsigned int i = 0; i < a.rows(); i++) { if (a[a.columns()-1][i] == 1) { return Cell(a.columns()-1,i); } } return Cell(-1,-1); }
Matrix& Matrix::blkDiag(const Matrix& mx_in) { Matrix old = *this; Matrix mx_in_ = mx_in; resizeAndFill(m_nrows + mx_in_.rows(), m_ncols + mx_in_.columns(), 0); if (old.rows() != 0 && old.columns() != 0) set(0, old.rows() - 1, 0, old.columns() - 1, old); set(old.rows(), old.rows() + mx_in_.rows() - 1, old.columns(), old.columns() + mx_in_.columns() - 1, mx_in_); return *this; }
inline const Disposable<Matrix> operator-(const Matrix& m1, const Matrix& m2) { QL_REQUIRE(m1.rows() == m2.rows() && m1.columns() == m2.columns(), "matrices with different sizes (" << m1.rows() << "x" << m1.columns() << ", " << m2.rows() << "x" << m2.columns() << ") cannot be " "subtracted"); Matrix temp(m1.rows(),m1.columns()); std::transform(m1.begin(),m1.end(),m2.begin(),temp.begin(), std::minus<Real>()); return temp; }
void PseudoInverter::init (const Matrix& inv, const Matrix& src) { if (singular_values) { delete singular_values; singular_values = NULL; } if (SVD_work) { delete SVD_work; SVD_work = NULL; } if (SVD_V) { delete SVD_V; SVD_V = NULL; } if (SVD_U) { delete SVD_U; SVD_U = NULL; } if (SVD_Ut) { delete SVD_Ut; SVD_Ut = NULL; } if (SVD_S) { delete SVD_S; SVD_S = NULL; } if (SVD_D) { delete SVD_D; SVD_D = NULL; } SVD_V = SVD_U = SVD_Ut = SVD_S = SVD_D = NULL; if (src.rows() < src.columns()) throw Exception ("Cannot invert MxN matrix when M < N"); singular_values = gsl_vector_alloc(src.columns()); SVD_work = gsl_vector_alloc(src.columns()); SVD_U = new Matrix(src.rows(), src.columns()); SVD_Ut = new Matrix(src.columns(), src.rows()); SVD_V = new Matrix(src.columns(), src.columns()); SVD_S = new Matrix(src.columns(), src.columns()); SVD_D = new Matrix(src.columns(), src.rows()); SVD_S->zero(); }
RatePseudoRootJacobian::RatePseudoRootJacobian(const Matrix& pseudoRoot, Size aliveIndex, Size numeraire, const std::vector<Time>& taus, const std::vector<Matrix>& pseudoBumps, const std::vector<Spread>& displacements) : pseudoRoot_(pseudoRoot), aliveIndex_(aliveIndex), taus_(taus), pseudoBumps_(pseudoBumps), displacements_(displacements), numberBumps_(pseudoBumps.size()), factors_(pseudoRoot.columns()), // bumpedRates_(taus.size()), e_(pseudoRoot.rows(), pseudoRoot.columns()), ratios_(taus_.size()) { Size numberRates= taus.size(); QL_REQUIRE(aliveIndex == numeraire, "we can do only do discretely compounding MM acount so aliveIndex must equal numeraire"); QL_REQUIRE(pseudoRoot_.rows()==numberRates, "pseudoRoot_.rows()<> taus.size()"); QL_REQUIRE(displacements_.size()==numberRates, "displacements_.size()<> taus.size()"); for (Size i=0; i < pseudoBumps.size(); ++i) { QL_REQUIRE(pseudoBumps[i].rows()==numberRates, "pseudoBumps[i].rows()<> taus.size() with i =" << i); QL_REQUIRE(pseudoBumps[i].columns()==factors_, "pseudoBumps[i].columns()<> factors with i = " << i); } for (Size i=0; i < numberRates; ++i) { allDerivatives_.push_back(Matrix(numberRates,factors_)); } }
int Munkres::step3(void) { /* Main Zero Search 1. Find an uncovered Z in the distance matrix and prime it. If no such zero exists, go to Step 5 2. If No Z* exists in the row of the Z', go to Step 4. 3. If a Z* exists, cover this row and uncover the column of the Z*. Return to Step 3.1 to find a new Z */ if ( find_uncovered_in_matrix(0, saverow, savecol) ) { mask_matrix(saverow,savecol) = PRIME; // prime it. } else { return 5; } for ( unsigned int ncol = 0 ; ncol < matrix.columns() ; ncol++ ) { if ( mask_matrix(saverow,ncol) == STAR ) { row_mask[saverow] = true; //cover this row and col_mask[ncol] = false; // uncover the column containing the starred zero return 3; // repeat } } return 4; // no starred zero in the row containing this primed zero }
int Munkres::step2(void) { const unsigned int rows = matrix.rows(), columns = matrix.columns(); unsigned int covercount = 0; for ( unsigned int row = 0 ; row < rows ; row++ ) for ( unsigned int col = 0 ; col < columns ; col++ ) if ( STAR == mask_matrix(row, col) ) { col_mask[col] = true; covercount++; } if ( covercount >= matrix.minsize() ) { #ifdef DEBUG std::cout << "Final cover count: " << covercount << std::endl; #endif return 0; } #ifdef DEBUG std::cout << "Munkres matrix has " << covercount << " of " << matrix.minsize() << " Columns covered:" << std::endl; for ( unsigned int row = 0 ; row < rows ; row++ ) { for ( unsigned int col = 0 ; col < columns ; col++ ) { std::cout.width(8); std::cout << matrix(row, col) << ","; } std::cout << std::endl; } std::cout << std::endl; #endif return 3; }
int Munkres::step1(void) { const unsigned int rows = matrix.rows(), columns = matrix.columns(); for ( unsigned int row = 0 ; row < rows ; row++ ) { for ( unsigned int col = 0 ; col < columns ; col++ ) { if ( 0 == matrix(row, col) ) { bool isstarred = false; for ( unsigned int nrow = 0 ; nrow < rows ; nrow++ ) if ( STAR == mask_matrix(nrow,col) ) { isstarred = true; break; } if ( !isstarred ) { for ( unsigned int ncol = 0 ; ncol < columns ; ncol++ ) if ( STAR == mask_matrix(row, ncol) ) { isstarred = true; break; } } if ( !isstarred ) { mask_matrix(row,col) = STAR; } } } } return 2; }
Disposable<Array> qrSolve(const Matrix& a, const Array& b, bool pivot, const Array& d) { const Size m = a.rows(); const Size n = a.columns(); QL_REQUIRE(b.size() == m, "dimensions of A and b don't match"); QL_REQUIRE(d.size() == n || d.empty(), "dimensions of A and d don't match"); Matrix q(m, n), r(n, n); std::vector<Size> lipvt = qrDecomposition(a, q, r, pivot); boost::scoped_array<int> ipvt(new int[n]); std::copy(lipvt.begin(), lipvt.end(), ipvt.get()); Matrix rT = transpose(r); boost::scoped_array<Real> sdiag(new Real[n]); boost::scoped_array<Real> wa(new Real[n]); Array ld(n, 0.0); if (!d.empty()) { std::copy(d.begin(), d.end(), ld.begin()); } Array x(n); Array qtb = transpose(q)*b; MINPACK::qrsolv(n, rT.begin(), n, ipvt.get(), ld.begin(), qtb.begin(), x.begin(), sdiag.get(), wa.get()); return x; }
vector<vector<ObjectHandler::property_t> > browseCmsMarket(const Matrix& cmsMarket) { Size numberOfColumn = 14; Size numberOfRows = cmsMarket.rows()+1; vector<vector<ObjectHandler::property_t> > result(numberOfRows, vector<ObjectHandler::property_t>(numberOfColumn)); result[0][ 0] = std::string("SwapIndex"); result[0][ 1] = std::string("Maturity"); result[0][ 2] = std::string("Mkt Bid - Spread (bps)"); result[0][ 3] = std::string("Mkt Ask - Spread (bps)"); result[0][ 4] = std::string("Mkt Mid - Spread (bps)"); result[0][ 5] = std::string("Model Mid - Spread (bps)"); result[0][ 6] = std::string("Error - Spread (bps)"); result[0][ 7] = std::string("Outside bid/ask (bps)"); result[0][ 8] = std::string("Mkt mid - Spot price"); result[0][ 9] = std::string("Model mid - Spot price"); result[0][10] = std::string("Error - Spot price"); result[0][11] = std::string("Mkt mid - Fwd price"); result[0][12] = std::string("Model mid - Fwd price"); result[0][13] = std::string("Error - Fwd price"); for (Size i=0; i<cmsMarket.rows(); ++i) for(Size j=0; j<cmsMarket.columns(); ++j) result[i+1][j] = cmsMarket[i][j]; return result; }
void RebonatoAngle::calculateAngleFromBMatrix(const Matrix& BMatrix) { if(BMatrix.rows() != matrixSize_ || BMatrix.columns() != rank_) throw("Error matrix size dismatch."); Matrix m(BMatrix); size_t k = 0; // angle index for(size_t i=0; i<matrixSize_; ++i) { Real sinProduct = 1.0; for(size_t j=0; j<rank_-1; ++j) { m[i][j] /= sinProduct; angles_[k] = std::acos(m[i][j]); sinProduct *= std::sin(angles_[k]); ++k; } //! last one need to check the sign if(m[i][rank_-1]*sinProduct < 0) // i.e test if original sinProduct and this->sinProduct () has the same sign! ---- their differenc is the last angle! angles_[k-1] += 2*(PI-angles_[k-1]); } //! check the result. if(!checkAngle(angles_)) throw("Angles are not all in [0,PI]"); }
Matrix& Matrix::horzCat(const Matrix& mx_in) { if (m_nrows != mx_in.m_nrows && m_nrows != 0 && m_ncols != 0) throw Error("invalid index"); Matrix old = *this; // <=> Matrix old(*this); Matrix mx_in_ = mx_in; resizeAndFill(mx_in_.rows(), m_ncols + mx_in.columns(), 0); if (old.rows() != 0 && old.columns() != 0) set(0, old.rows() - 1, 0, old.columns() - 1, old); set(0, mx_in_.rows() - 1, old.columns(), old.columns() + mx_in_.columns() - 1, mx_in_); return *this; }
void pathFinder(Matrix & a) { Cell start = entrance(a); Cell finish = exit(a); std::cout << "Entrance: " << start << std::endl;; std::cout << "Exit: " << finish << std::endl;; solove(start, finish, a); for (unsigned int i = 0; i < a.columns(); i++) { for (unsigned int j = 0; j < a.rows(); j++) { switch (a[i][j]) { case 0: std::cout << '#'; break; // case 1: // break; case 2: std::cout << 'x'; break; case 3: std::cout << '.'; break; default: std::cout << ' '; break; } } std::cout << std::endl; } }
CMSMMDriftCalculator::CMSMMDriftCalculator( const Matrix& pseudo, const std::vector<Spread>& displacements, const std::vector<Time>& taus, Size numeraire, Size alive, Size spanningFwds) : numberOfRates_(taus.size()), numberOfFactors_(pseudo.columns()), isFullFactor_(numberOfFactors_==numberOfRates_ ? true : false), numeraire_(numeraire), alive_(alive), displacements_(displacements), oneOverTaus_(taus.size()), pseudo_(pseudo), tmp_(taus.size(), 0.0), PjPnWk_(numberOfFactors_,1+taus.size()), wkaj_(numberOfFactors_, taus.size()), wkajN_(numberOfFactors_, taus.size()), downs_(taus.size()), ups_(taus.size()), spanningFwds_(spanningFwds) { // Check requirements QL_REQUIRE(numberOfRates_>0, "Dim out of range"); QL_REQUIRE(displacements.size() == numberOfRates_, "Displacements out of range"); QL_REQUIRE(pseudo.rows()==numberOfRates_, "pseudo.rows() not consistent with dim"); QL_REQUIRE(pseudo.columns()>0 && pseudo.columns()<=numberOfRates_, "pseudo.rows() not consistent with pseudo.columns()"); QL_REQUIRE(alive<numberOfRates_, "Alive out of bounds"); QL_REQUIRE(numeraire_<=numberOfRates_, "Numeraire larger than dim"); QL_REQUIRE(numeraire_>=alive, "Numeraire smaller than alive"); // Precompute 1/taus for (Size i=0; i<taus.size(); ++i) oneOverTaus_[i] = 1.0/taus[i]; // Compute covariance matrix from pseudoroot const Disposable<Matrix> pT = transpose(pseudo_); C_ = pseudo_*pT; // Compute lower and upper extrema for (non reduced) drift calculation for (Size i=alive_; i<numberOfRates_; ++i) { downs_[i] = std::min(i+1, numeraire_); ups_[i] = std::max(i+1, numeraire_); } }
inline const Disposable<Matrix> operator*(const Matrix& m1, const Matrix& m2) { QL_REQUIRE(m1.columns() == m2.rows(), "matrices with different sizes (" << m1.rows() << "x" << m1.columns() << ", " << m2.rows() << "x" << m2.columns() << ") cannot be " "multiplied"); Matrix result(m1.rows(),m2.columns(),0.0); for (Size i=0; i<result.rows(); ++i) { for (Size k=0; k<m1.columns(); ++k) { for (Size j=0; j<result.columns(); ++j) { result[i][j] += m1[i][k]*m2[k][j]; } } } return result; }
std::vector<double> operator*(const Matrix &m, const std::vector<double> &n) { if (m.columns() > n.size()) { std::stringstream fmt; fmt << "Tamaño de matriz M es " << m.columns() << ", mientras que vector n es " << n.size(); throw new std::out_of_range(fmt.str()); } std::vector<double> output(m.rows(), 0.0); for (int i = 0; i < m.rows(); ++i) { for (int j = 0; j < m.columns(); ++j) { output[i] += m(i, j) * n[j]; } } return output; }
inline const Disposable<Matrix> transpose(const Matrix& m) { Matrix result(m.columns(),m.rows()); #if defined(QL_PATCH_MSVC) && defined(QL_DEBUG) if (!m.empty()) #endif for (Size i=0; i<m.rows(); i++) std::copy(m.row_begin(i),m.row_end(i),result.column_begin(i)); return result; }