MyraMath
sseidel_symmetry


Source: tests/iterative/stationary_symmetry.cpp

1 // ========================================================================= //
2 // This file is part of MyraMath, copyright (c) 2014-2019 by Ryan A Chilton //
3 // and distributed by MyraCore, LLC. See LICENSE.txt for license terms. //
4 // ========================================================================= //
5 
11 // Containers.
13 #include <myramath/dense/Vector.h>
15 #include <myramath/dense/Matrix.h>
21 
22 // Algorithms.
27 
28 // Reporting.
29 #include <tests/myratest.h>
30 
31 using namespace myra;
32 
33 namespace {
34 
35 // Action that applies seidel()
36 template<class Precision> class seidel_Action
37  {
38  public:
39 
40  // Required typedef.
41  typedef Precision Number;
42 
44  seidel_Action(const CSparseMatrixRange<Precision>& in_At, Precision in_tol, int in_iter)
45  : At(in_At), tol(in_tol), iter(in_iter) { }
46 
48  std::pair<int,int> size() const
49  { return At.size(); }
50 
52  void multiply (const CMatrixRange<Precision>& B, const MatrixRange<Precision>& X) const
53  {
54  X.zero();
55  for (int j = 0; j < B.J; ++j)
56  seidel(At,B.vector(j),X.vector(j),tol,iter);
57  }
58 
59  private:
60 
61  // Captured environment for seidel()
63  Precision tol;
64  int iter;
65 
66  };
67 
68 // Action that applies sseidel()
69 template<class Precision> class sseidel_Action
70  {
71  public:
72 
73  // Required typedef.
74  typedef Precision Number;
75 
77  sseidel_Action(const CSparseMatrixRange<Precision>& in_At, Precision in_tol, int in_iter)
78  : At(in_At), tol(in_tol), iter(in_iter) { }
79 
81  std::pair<int,int> size() const
82  { return At.size(); }
83 
85  void multiply (const CMatrixRange<Precision>& B, const MatrixRange<Precision>& X) const
86  {
87  X.zero();
88  for (int j = 0; j < B.J; ++j)
89  sseidel(At,B.vector(j),X.vector(j),tol,iter);
90  }
91 
92  private:
93 
94  // Captured environment for sseidel()
96  Precision tol;
97  int iter;
98 
99  };
100 
101 // Tests seidel() and sseidel()
102 template<class Precision> void test1(int I, int J, Precision tol)
103  {
104  auto A = laplacian2<Precision>(I,J);
105  // Look at the assymetry of seidel()
106  Action<Precision> S = make_UserAction( seidel_Action<Precision>(A,0.0,10) );
107  Matrix<Precision> S0 = S.make_Matrix();
108  Precision seidel_assymetry = frobenius(S0-transpose(S0));
109  myra::out() << "| seidel - seidel'| = " << seidel_assymetry << std::endl;
110  // Verify that sseidel() is a symmetric Action.
111  Action<Precision> SS = make_UserAction( sseidel_Action<Precision>(A,0.0,10) );
112  Matrix<Precision> SS0 = SS.make_Matrix();
113  Precision sseidel_assymetry = frobenius(SS0-transpose(SS0));
114  myra::out() << "|sseidel - sseidel'| = " << sseidel_assymetry << std::endl;
115  REQUIRE( sseidel_assymetry < tol );
116  }
117 
118 // Action that applies sor()
119 template<class Precision> class sor_Action
120  {
121  public:
122 
123  // Required typedef.
124  typedef Precision Number;
125 
127  sor_Action(const CSparseMatrixRange<Precision>& in_At, Precision in_omega, Precision in_tol, int in_iter)
128  : At(in_At), omega(in_omega), tol(in_tol), iter(in_iter) { }
129 
131  std::pair<int,int> size() const
132  { return At.size(); }
133 
135  void multiply (const CMatrixRange<Precision>& B, const MatrixRange<Precision>& X) const
136  {
137  X.zero();
138  for (int j = 0; j < B.J; ++j)
139  sor(At,B.vector(j),X.vector(j),omega,tol,iter);
140  }
141 
142  private:
143 
144  // Captured environment for sor()
146  Precision omega;
147  Precision tol;
148  int iter;
149 
150  };
151 
152 // Action that applies ssor()
153 template<class Precision> class ssor_Action
154  {
155  public:
156 
157  // Required typedef.
158  typedef Precision Number;
159 
161  ssor_Action(const CSparseMatrixRange<Precision>& in_At, Precision in_omega, Precision in_tol, int in_iter)
162  : At(in_At), omega(in_omega), tol(in_tol), iter(in_iter) { }
163 
165  std::pair<int,int> size() const
166  { return At.size(); }
167 
169  void multiply (const CMatrixRange<Precision>& B, const MatrixRange<Precision>& X) const
170  {
171  X.zero();
172  for (int j = 0; j < B.J; ++j)
173  ssor(At,B.vector(j),X.vector(j),omega,tol,iter);
174  }
175 
176  private:
177 
178  // Captured environment for ssor()
180  Precision omega;
181  Precision tol;
182  int iter;
183 
184  };
185 
186 // Tests sor() and ssor()
187 template<class Precision> void test2(int I, int J, Precision tol)
188  {
189  auto A = laplacian2<Precision>(I,J);
190  Precision omega(1.5);
191  // Look at the assymetry of sor()
192  Action<Precision> S = make_UserAction( sor_Action<Precision>(A,omega,0.0,10) );
194  Precision sor_assymetry = frobenius(S0-transpose(S0));
195  myra::out() << "| sor - sor'| = " << sor_assymetry << std::endl;
196  // Verify that ssor() is a symmetric Action.
197  Action<Precision> SS = make_UserAction( ssor_Action<Precision>(A,omega,0.0,10) );
198  Matrix<Precision> SS0 = SS.make_Matrix();
199  Precision ssor_assymetry = frobenius(SS0-transpose(SS0));
200  myra::out() << "|ssor - ssor'| = " << ssor_assymetry << std::endl;
201  REQUIRE( ssor_assymetry < tol );
202  }
203 
204 
205 } // namespace
206 
207 ADD_TEST("sseidel_symmetry","[iterative]")
208  {
209  test1<float>(20,20,1.0e-5f);
210  test1<double>(20,20,1.0e-12);
211  }
212 
213 ADD_TEST("ssor_symmetry","[iterative]")
214  {
215  test2<float>(20,20,1.0e-5f);
216  test2<double>(20,20,1.0e-12);
217  }
218 
Action< typename UserClass::Number > make_UserAction(const UserClass &u)
Helper function to adapt some user code (encapsulated in a class) into an Action. ...
Definition: UserAction.h:61
Interface class for representing subranges of dense Matrix&#39;s.
Implementations of classical stationary iterations: jacobi(), seidel(), sor() and ssor() ...
Interface class for representing subranges of dense Vector&#39;s.
Applies the "Action" of a linear operator, b := A*x, used in iterative solution algorithms.
Routines for computing Frobenius norms of various algebraic containers.
General purpose compressed-sparse-column (CSC) container.
CVectorRange< Number > vector(int j) const
Returns the j&#39;th column as a CVectorRange.
Definition: MatrixRange.cpp:608
Definition: syntax.dox:1
Represents a const MatrixRange.
Definition: bothcat.h:22
Adapts user code (encapsulated in a class) into an Action.
Returns a transposed copy of a Matrix. The inplace version only works on a square operand...
Various utility functions/classes related to scalar Number types.
VectorRange< Number > vector(int j) const
Returns the j&#39;th column as a VectorRange.
Definition: MatrixRange.cpp:247
int J
---------— Data members, all public ----------------—
Definition: MatrixRange.h:241
Represents a mutable MatrixRange.
Definition: conjugate.h:26
General purpose dense matrix container, O(i*j) storage.
Represents a const SparseMatrixRange.
Definition: bothcat.h:24
Applies the "Action" of a linear operator, b := A*x.
Definition: Action.h:29
Container for either a column vector or row vector (depends upon the usage context) ...
Matrix< Number > make_Matrix() const
Tabulates *this into a dense Matrix.
Definition: Action.cpp:71
void zero() const
Assigns zero to every entry.
Definition: MatrixRange.cpp:362
Helper routines for reordering/filling 2D structured grids. Used by many unit tests.
Range/Iterator types associated with SparseMatrix.


Results: [PASS]

| seidel - seidel'| = 0.0376709
|sseidel - sseidel'| = 3.23786e-07
| seidel - seidel'| = 0.0376727
|sseidel - sseidel'| = 6.37134e-16


Go back to Summary of /test programs.