Commit 2c774914 by Maarten L. Hekkelman

cleaner implementation of matrices

parent be19e4a9
...@@ -33,10 +33,7 @@ namespace mmcif ...@@ -33,10 +33,7 @@ namespace mmcif
{ {
// -------------------------------------------------------------------- // --------------------------------------------------------------------
// uBlas compatible matrix types // We're using expression templates here
// matrix is m x n, addressing i,j is 0 <= i < m and 0 <= j < n
// element m i,j is mapped to [i * n + j] and thus storage is row major
template <typename M> template <typename M>
class MatrixExpression class MatrixExpression
...@@ -56,6 +53,10 @@ class MatrixExpression ...@@ -56,6 +53,10 @@ class MatrixExpression
} }
}; };
// --------------------------------------------------------------------
// matrix is m x n, addressing i,j is 0 <= i < m and 0 <= j < n
// element m i,j is mapped to [i * n + j] and thus storage is row major
class Matrix : public MatrixExpression<Matrix> class Matrix : public MatrixExpression<Matrix>
{ {
public: public:
...@@ -63,8 +64,8 @@ class Matrix : public MatrixExpression<Matrix> ...@@ -63,8 +64,8 @@ class Matrix : public MatrixExpression<Matrix>
Matrix(const MatrixExpression<M2> &m) Matrix(const MatrixExpression<M2> &m)
: m_m(m.dim_m()) : m_m(m.dim_m())
, m_n(m.dim_n()) , m_n(m.dim_n())
, m_data(m_m * m_n)
{ {
m_data = new double[m_m * m_n];
for (uint32_t i = 0; i < m_m; ++i) for (uint32_t i = 0; i < m_m; ++i)
{ {
for (uint32_t j = 0; j < m_n; ++j) for (uint32_t j = 0; j < m_n; ++j)
...@@ -72,46 +73,19 @@ class Matrix : public MatrixExpression<Matrix> ...@@ -72,46 +73,19 @@ class Matrix : public MatrixExpression<Matrix>
} }
} }
Matrix() Matrix(size_t m, size_t n, double v = 0)
: m_data(nullptr)
, m_m(0)
, m_n(0)
{
}
Matrix(const Matrix &m)
: m_m(m.m_m)
, m_n(m.m_n)
{
m_data = new double[m_m * m_n];
std::copy(m.m_data, m.m_data + (m_m * m_n), m_data);
}
Matrix &operator=(const Matrix &m)
{
double *t = new double[m.m_m * m.m_n];
std::copy(m.m_data, m.m_data + (m.m_m * m.m_n), t);
delete[] m_data;
m_data = t;
m_m = m.m_m;
m_n = m.m_n;
return *this;
}
Matrix(uint32_t m, uint32_t n, double v = 0)
: m_m(m) : m_m(m)
, m_n(n) , m_n(n)
, m_data(m_m * m_n)
{ {
m_data = new double[m_m * m_n]; std::fill(m_data.begin(), m_data.end(), v);
std::fill(m_data, m_data + (m_m * m_n), v);
} }
~Matrix() Matrix() = default;
{ Matrix(Matrix &&m) = default;
delete[] m_data; Matrix(const Matrix &m) = default;
} Matrix &operator=(Matrix &&m) = default;
Matrix &operator=(const Matrix &m) = default;
uint32_t dim_m() const { return m_m; } uint32_t dim_m() const { return m_m; }
uint32_t dim_n() const { return m_n; } uint32_t dim_n() const { return m_n; }
...@@ -131,8 +105,8 @@ class Matrix : public MatrixExpression<Matrix> ...@@ -131,8 +105,8 @@ class Matrix : public MatrixExpression<Matrix>
} }
private: private:
double *m_data; uint32_t m_m = 0, m_n = 0;
uint32_t m_m, m_n; std::vector<double> m_data;
}; };
// -------------------------------------------------------------------- // --------------------------------------------------------------------
...@@ -142,16 +116,16 @@ class SymmetricMatrix : public MatrixExpression<SymmetricMatrix> ...@@ -142,16 +116,16 @@ class SymmetricMatrix : public MatrixExpression<SymmetricMatrix>
public: public:
SymmetricMatrix(uint32_t n, double v = 0) SymmetricMatrix(uint32_t n, double v = 0)
: m_n(n) : m_n(n)
, m_data((m_n * (m_n + 1)) / 2)
{ {
uint32_t N = (m_n * (m_n + 1)) / 2; std::fill(m_data.begin(), m_data.end(), v);
m_data = new double[N];
std::fill(m_data, m_data + N, v);
} }
~SymmetricMatrix() SymmetricMatrix() = default;
{ SymmetricMatrix(SymmetricMatrix &&m) = default;
delete[] m_data; SymmetricMatrix(const SymmetricMatrix &m) = default;
} SymmetricMatrix &operator=(SymmetricMatrix &&m) = default;
SymmetricMatrix &operator=(const SymmetricMatrix &m) = default;
uint32_t dim_m() const { return m_n; } uint32_t dim_m() const { return m_n; }
uint32_t dim_n() const { return m_n; } uint32_t dim_n() const { return m_n; }
...@@ -172,8 +146,8 @@ class SymmetricMatrix : public MatrixExpression<SymmetricMatrix> ...@@ -172,8 +146,8 @@ class SymmetricMatrix : public MatrixExpression<SymmetricMatrix>
} }
private: private:
double *m_data;
uint32_t m_n; uint32_t m_n;
std::vector<double> m_data;
}; };
class IdentityMatrix : public MatrixExpression<IdentityMatrix> class IdentityMatrix : public MatrixExpression<IdentityMatrix>
...@@ -260,8 +234,10 @@ MatrixMultiplication<M> operator*(const MatrixExpression<M> &m, double v) ...@@ -260,8 +234,10 @@ MatrixMultiplication<M> operator*(const MatrixExpression<M> &m, double v)
// -------------------------------------------------------------------- // --------------------------------------------------------------------
template<class M1> template<class M1>
void cofactors(const M1& m, SymmetricMatrix& cf) Matrix Cofactors(const M1& m)
{ {
Matrix cf(m.dim_m(), m.dim_m());
const size_t ixs[4][3] = const size_t ixs[4][3] =
{ {
{ 1, 2, 3 }, { 1, 2, 3 },
...@@ -274,7 +250,7 @@ void cofactors(const M1& m, SymmetricMatrix& cf) ...@@ -274,7 +250,7 @@ void cofactors(const M1& m, SymmetricMatrix& cf)
{ {
const size_t* ix = ixs[x]; const size_t* ix = ixs[x];
for (size_t y = x; y < 4; ++y) for (size_t y = 0; y < 4; ++y)
{ {
const size_t* iy = ixs[y]; const size_t* iy = ixs[y];
...@@ -290,6 +266,8 @@ void cofactors(const M1& m, SymmetricMatrix& cf) ...@@ -290,6 +266,8 @@ void cofactors(const M1& m, SymmetricMatrix& cf)
cf(x, y) *= -1; cf(x, y) *= -1;
} }
} }
return cf;
} }
// -------------------------------------------------------------------- // --------------------------------------------------------------------
...@@ -494,14 +472,13 @@ Quaternion AlignPoints(const std::vector<Point>& pa, const std::vector<Point>& p ...@@ -494,14 +472,13 @@ Quaternion AlignPoints(const std::vector<Point>& pa, const std::vector<Point>& p
(N(0,2) * N(1,3) - N(2,1) * N(0,3)) * (N(0,2) * N(1,3) - N(2,1) * N(0,3)); (N(0,2) * N(1,3) - N(2,1) * N(0,3)) * (N(0,2) * N(1,3) - N(2,1) * N(0,3));
// solve quartic // solve quartic
double lm = LargestDepressedQuarticSolution(C, D, E); double lambda = LargestDepressedQuarticSolution(C, D, E);
// calculate t = (N - λI) // calculate t = (N - λI)
Matrix t = N - IdentityMatrix(4) * lm; Matrix t = N - IdentityMatrix(4) * lambda;
// calculate a Matrix of cofactors for t, since N is symmetric, t must be symmetric as well and so will be cf // calculate a Matrix of cofactors for t, since N is symmetric, t must be symmetric as well and so will be cf
SymmetricMatrix cf(4); Matrix cf = Cofactors(t);
cofactors(t, cf);
int maxR = 0; int maxR = 0;
for (int r = 1; r < 4; ++r) for (int r = 1; r < 4; ++r)
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment