1 // Created on: 2005-12-15
2 // Created by: Julia GERASIMOVA
3 // Copyright (c) 2005-2012 OPEN CASCADE SAS
5 // The content of this file is subject to the Open CASCADE Technology Public
6 // License Version 6.5 (the "License"). You may not use the content of this file
7 // except in compliance with the License. Please obtain a copy of the License
8 // at http://www.opencascade.org and read it completely before using this file.
10 // The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
11 // main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
13 // The Original Code and all software distributed under the License is
14 // distributed on an "AS IS" basis, without warranty of any kind, and the
15 // Initial Developer hereby disclaims all such warranties, including without
16 // limitation, any warranties of merchantability, fitness for a particular
17 // purpose or non-infringement. Please see the License for the specific terms
18 // and conditions governing the rights and limitations under the License.
22 #include <math_EigenValuesSearcher.ixx>
24 //==========================================================================
26 // Computation of sqrt(x*x + y*y).
27 //==========================================================================
29 static inline Standard_Real pythag(const Standard_Real x,
30 const Standard_Real y)
32 return Sqrt(x*x + y*y);
35 math_EigenValuesSearcher::math_EigenValuesSearcher(const TColStd_Array1OfReal& Diagonal,
36 const TColStd_Array1OfReal& Subdiagonal)
38 myIsDone = Standard_False;
40 Standard_Integer n = Diagonal.Length();
41 if (Subdiagonal.Length() != n)
42 Standard_Failure::Raise("math_EigenValuesSearcher : dimension mismatch");
44 myDiagonal = new TColStd_HArray1OfReal(1, n);
45 myDiagonal->ChangeArray1() = Diagonal;
46 mySubdiagonal = new TColStd_HArray1OfReal(1, n);
47 mySubdiagonal->ChangeArray1() = Subdiagonal;
49 myEigenValues = new TColStd_HArray1OfReal(1, n);
50 myEigenVectors = new TColStd_HArray2OfReal(1, n, 1, n);
52 Standard_Real* d = new Standard_Real [n+1];
53 Standard_Real* e = new Standard_Real [n+1];
54 Standard_Real** z = new Standard_Real* [n+1];
55 Standard_Integer i, j;
56 for (i = 1; i <= n; i++)
57 z[i] = new Standard_Real [n+1];
59 for (i = 1; i <= n; i++)
60 d[i] = myDiagonal->Value(i);
61 for (i = 2; i <= n; i++)
62 e[i] = mySubdiagonal->Value(i);
63 for (i = 1; i <= n; i++)
64 for (j = 1; j <= n; j++)
65 z[i][j] = (i == j)? 1. : 0.;
67 Standard_Boolean result;
70 Standard_Integer iter;
82 result = Standard_True;
87 for (i = 2; i <= n; i++)
92 for (l = 1; l <= n; l++) {
96 for (m = l; m <= n-1; m++) {
97 dd = Abs(d[m]) + Abs(d[m + 1]);
99 if (Abs(e[m]) + dd == dd)
105 result = Standard_False;
106 break; //return result;
109 g = (d[l + 1] - d[l])/(2.*e[l]);
113 g = d[m] - d[l] + e[l]/(g - r);
115 g = d[m] - d[l] + e[l]/(g + r);
121 for (i = m - 1; i >= l; i--) {
136 r = (d[i] - g)*s + 2.0*c*b;
141 for (k = 1; k <= n; k++) {
143 z[k][i + 1] = s*z[k][i] + c*f;
144 z[k][i] = c*z[k][i] - s*f;
148 if (r == 0 && i >= 1)
157 if (result == Standard_False)
159 } //end of for (l = 1; l <= n; l++)
160 } //end of if (n != 1)
164 for (i = 1; i <= n; i++)
165 myEigenValues->ChangeValue(i) = d[i];
166 for (i = 1; i <= n; i++)
167 for (j = 1; j <= n; j++)
168 myEigenVectors->ChangeValue(i, j) = z[i][j];
175 for (i = 1; i <= n; i++)
180 Standard_Boolean math_EigenValuesSearcher::IsDone() const
185 Standard_Integer math_EigenValuesSearcher::Dimension() const
190 Standard_Real math_EigenValuesSearcher::EigenValue(const Standard_Integer Index) const
192 return myEigenValues->Value(Index);
195 math_Vector math_EigenValuesSearcher::EigenVector(const Standard_Integer Index) const
197 math_Vector theVector(1, myN);
200 for (i = 1; i <= myN; i++)
201 theVector(i) = myEigenVectors->Value(i, Index);